{"id":64163,"date":"2007-08-24T01:41:00","date_gmt":"2007-08-24T01:41:00","guid":{"rendered":"https:\/\/blogs.technet.microsoft.com\/heyscriptingguy\/2007\/08\/24\/how-can-i-delete-the-oldest-file-from-a-folder-if-and-when-that-folder-exceeds-a-specified-size\/"},"modified":"2007-08-24T01:41:00","modified_gmt":"2007-08-24T01:41:00","slug":"how-can-i-delete-the-oldest-file-from-a-folder-if-and-when-that-folder-exceeds-a-specified-size","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/scripting\/how-can-i-delete-the-oldest-file-from-a-folder-if-and-when-that-folder-exceeds-a-specified-size\/","title":{"rendered":"How Can I Delete the Oldest File From a Folder If and When That Folder Exceeds a Specified Size?"},"content":{"rendered":"<p><IMG class=\"nearGraphic\" title=\"Hey, Scripting Guy! Question\" height=\"34\" alt=\"Hey, Scripting Guy! Question\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/q-for-powertip.jpg\" width=\"34\" align=\"left\" border=\"0\"> \n<P>Hey, Scripting Guy! I need to check the size of a folder once every hour; if the folder has exceeded a specified size, I then need to delete the oldest file in that folder. How can I do that?<BR><BR>&#8212; JC <\/P><IMG height=\"5\" alt=\"Spacer\" src=\"https:\/\/devblogs.microsoft.com\/scripting\/wp-content\/uploads\/sites\/29\/2019\/05\/spacer.gif\" width=\"5\" border=\"0\"><IMG class=\"nearGraphic\" title=\"Hey, Scripting Guy! Answer\" height=\"34\" alt=\"Hey, Scripting Guy! Answer\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/29\/2019\/02\/a-for-powertip.jpg\" width=\"34\" align=\"left\" border=\"0\"><A href=\"http:\/\/go.microsoft.com\/fwlink\/?linkid=68779&amp;clcid=0x409\"><IMG class=\"farGraphic\" title=\"Script Center\" height=\"288\" alt=\"Script Center\" src=\"http:\/\/img.microsoft.com\/library\/media\/1033\/technet\/images\/scriptcenter\/ad.jpg\" width=\"120\" align=\"right\" border=\"0\"><\/A> \n<P>Hey, JC. You know, a lot of you are thinking, \u201cGee, I wonder what was the very best, very coolest thing that the Scripting Guy who writes that column saw on his recent trip to Italy?\u201d As it turns out, that\u2019s an easy question to answer: the very best, very coolest thing that the Scripting Guy who writes this column saw on his recent trip to Italy was housed at the Vatican Museum and \u2013 What\u2019s that? The Sistine Chapel? Oh, is that at the Vatican? Well, what do you know? No, the \u2013 the Raphael Rooms? Sorry; never heard of them. At any rate, without a doubt the very best, very coolest thing the Scripting Guy who writes this column saw on his recent tip to Italy was housed at the Vatican Museum: a Pepsi-Cola!<\/P>\n<P>You heard right: a Pepsi-Cola. The Scripting Guy who writes this column had been to Europe a couple times prior to his recent vacation, and never once had he even <I>seen<\/I> a Pepsi, let alone have the opportunity to drink one. But after completing their tour of the Museum the Scripting Family stopped off at the Museum cafeteria to get something to drink. And there it was: a can of Pepsi. <\/P>\n<P>Needless to say, it was a profoundly moving experience, at least for a Scripting Guy who doesn\u2019t really like Coca-Cola all that much.<\/P>\n<TABLE class=\"dataTable\" id=\"EBD\" cellSpacing=\"0\" cellPadding=\"0\">\n<THEAD><\/THEAD>\n<TBODY>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P class=\"lastInCell\"><B>Scripting Dad and Scripting Son note<\/B>. As we mentioned, the family stopped off in the cafeteria just to get something to drink. Eat lunch there? Oh, please, not in a museum cafeteria. But then, just as the Scripting Dad and Scripting Son were reaching for their drinks, a cafeteria worker came by and plopped down a huge tub of pasta, pasta completely smothered with broiled cheese. For some reason, eating lunch at a museum cafeteria no longer seemed like such a bad idea after all.<\/P><\/TD><\/TR><\/TBODY><\/TABLE>\n<DIV class=\"dataTableBottomMargin\"><\/DIV>\n<P>Of course, it goes without saying that drinking a Pepsi, in Europe, mind you, is an experience that will never be topped. So then what was the second-best and second-coolest thing the Scripting Guy who writes this column saw in Italy? That would have to be this vintage Italian script (made by artisans using the same materials and techniques Italian scripters have used for hundreds of years), a script that can check to see if a folder has exceeded a specified size and, if it has, delete the oldest file in that folder:<\/P><PRE class=\"codeSample\">strOldestFile = &#8220;&#8221;\ndtmOldestDate = Now<\/p>\n<p>Set objFSO = CreateObject(&#8220;Scripting.FileSystemObject&#8221;)\nSet objFolder = objFSO.GetFolder(&#8220;C:\\Scripts&#8221;)<\/p>\n<p>intFolderSize = Int((objFolder.Size \/ 1024) \/ 1024)<\/p>\n<p>If intFolderSize &gt;= 25 Then\n    Set colFiles = objFolder.Files<\/p>\n<p>    For Each objFile in colFiles\n        strFile = objFile.Path\n        dtmFileDate = objFile.DateCreated\n        If dtmFileDate &lt; dtmOldestDate Then\n            dtmOldestDate = dtmFileDate\n            strOldestFile = strFile\n        End If\n    Next<\/p>\n<p>    objFSO.DeleteFile(strOldestFile) \nEnd If\n<\/PRE>\n<P>A couple quick notes before we begin. First, this script is designed to run only on the local computer. Why? Well, to run against a remote computer, the obvious technology of choice would be WMI. Unfortunately, though, there\u2019s a bug in WMI\u2019s Win32_Directory class: any time you retrieve the size of a folder the size comes back as 0 bytes. (If only we all had bathroom scales that worked in similar fashion!) That makes WMI a somewhat less-than-ideal technology for any task involving folder sizes. <I>Could<\/I> we perform this task remotely, even if that involves using a work-around or two? Yes we can, and that\u2019s something we\u2019ll take up in a future column, if anyone\u2019s interested.<\/P>\n<P>Second, this script is designed to run once and then stop. But wait, you say, didn\u2019t JC need the script to check the folder size <I>every hour<\/I>? That\u2019s correct. However, rather than add in code that pauses the script for an hour we recommend that you set up a scheduled task and have that task run the script once an hour. That\u2019s a much better, much easier, and much more foolproof approach to getting a script to run once every hour.<\/P>\n<TABLE class=\"dataTable\" id=\"EYD\" cellSpacing=\"0\" cellPadding=\"0\">\n<THEAD><\/THEAD>\n<TBODY>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P class=\"lastInCell\"><B>Note<\/B>. Why foolproof? Well, suppose something happens and the script process terminates (e.g., the command window in which the script is running is closed). In that case, you\u2019ve lost your ability to monitor the folder, at least until you restart the script. With a scheduled task, you don\u2019t ever have to worry about things like processes terminating prematurely and needing to be restarted.<\/P><\/TD><\/TR><\/TBODY><\/TABLE>\n<DIV class=\"dataTableBottomMargin\"><\/DIV>\n<P>OK, so much for all that; let\u2019s see if we can figure out how the script actually works. To begin with, we assign values to a pair of variables, strOldestFile and dtmOldestDate:<\/P><PRE class=\"codeSample\">strOldestFile = &#8220;&#8221;\ndtmOldestDate = Now\n<\/PRE>\n<P>We\u2019re going to use the variable strOldestFile to keep track of the path to the oldest file in the folder C:\\Scripts. Of course, at the beginning of the script we don\u2019t <I>know<\/I> the path to the oldest file in the folder, so we simply assign this variable an empty string (\u201c\u201d). <\/P>\n<P>Now, how are we going to determine which file <I>is<\/I> the oldest file in the folder? Well, we <I>could<\/I> figure that out by using some sort of complicated WMI query and sorting algorithm. However, we opted to do something a little easier: we\u2019re simply going to assign a beginning value to the variable dtmOldestDate (in this case, that value being the current date and time, something we can calculate by using the VBScript <B>Now<\/B> function). After that, we\u2019ll just loop through the collection of files found in the folder C:\\Scripts. For each file, we\u2019ll check to see if the file creation date is older than the value stored in dtmOldestDate. If it is, then we\u2019ll assign the file path of that file to strOldestFile and the file creation date to dtmOldestDate. If it isn\u2019t, well, then we\u2019ll simply move on and repeat the process with the next file in the collection.<\/P>\n<P>But more on that in a minute.<\/P>\n<P>After initializing our variables we create an instance of the <B>Scripting.FileSystemObject<\/B>, then use the <B>GetFolder<\/B> method to bind us to the folder C:\\Scripts; that\u2019s what we do with this block of code:<\/P><PRE class=\"codeSample\">Set objFSO = CreateObject(&#8220;Scripting.FileSystemObject&#8221;)\nSet objFolder = objFSO.GetFolder(&#8220;C:\\Scripts&#8221;)\n<\/PRE>\n<P>Once we\u2019ve created an object reference (objFolder) to C:\\Scripts we then use this line of code to store the size of that folder in the variable intFolderSize:<\/P><PRE class=\"codeSample\">intFolderSize = Int((objFolder.Size \/ 1024) \/ 1024)\n<\/PRE>\n<P>You know, you\u2019re right: that <I>is<\/I> a somewhat-complicated looking bit of code, isn\u2019t it? And, to be honest, there\u2019s no need for it to <I>be<\/I> that complicated; instead, we could have simply assigned the value of the <B>Size<\/B> property to the variable intFolderSize, like so:<\/P><PRE class=\"codeSample\">intFolderSize = objFolder.Size\n<\/PRE>\n<P>So then why didn\u2019t we just do that? Well, as it turns out, folder sizes are returned in bytes; that means a 25-megabyte folder will have a size equal to this:<\/P><PRE class=\"codeSample\">26214400\n<\/PRE>\n<P>There\u2019s nothing wrong with that, but very few people (or, at least, very few Scripting Guys) can glance at the number 26214400 and immediately think, \u201cOh, 25 megabytes, eh?\u201d Therefore, we did a little bit of math: we took the value of the Size property and divided it by 1024, giving us the size in kilobytes. We then took <I>that<\/I> value and divided it by 1024 once more, thus giving us a size (e.g., 25.1637182137) in megabytes. Finally, and because we really don\u2019t care about the .1637182137, we used the <B>Int<\/B> function to strip off the decimal places.<\/P>\n<P>The net result? We end up assigning a nice, clean value (25) to the variable intFolderSize. Because, as we all know, cleanliness <I>is<\/I> next to godliness.<\/P>\n<TABLE class=\"dataTable\" id=\"E3F\" cellSpacing=\"0\" cellPadding=\"0\">\n<THEAD><\/THEAD>\n<TBODY>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P><B>Scripting Guys trivia<\/B>. Contrary to popular belief, the phrase \u201cCleanliness is next to godliness\u201d does <I>not<\/I> appear in the Bible. Instead, the quote comes from a sermon by John Wesley, founder of the Methodist church: \u201cLet it be observed, that slovenliness is no part of religion; that neither this, nor any text of Scripture, condemns neatness of apparel. Certainly this is a duty, not a sin. Cleanliness is, indeed, next to godliness.&#8221;<\/P>\n<P>If <I>that<\/I> information doesn\u2019t win you a bunch of bar room bets, well, you\u2019re obviously hanging out in the wrong bar rooms.<\/P><\/TD><\/TR><\/TBODY><\/TABLE>\n<DIV class=\"dataTableBottomMargin\"><\/DIV>\n<P>OK, back to work. (After all, idle hands <I>are<\/I> the Devil\u2019s plaything.) As soon as we know the folder size we can use code like this to determine if that size is greater than or equal to a specified value (in this case, 25 megabytes):<\/P><PRE class=\"codeSample\">If intFolderSize &gt;= 25 Then\n<\/PRE>\n<P>If the size is <I>less<\/I> than 25 megabytes, then we\u2019re done; because the size is within the allowed limits we don\u2019t have to delete anything. If the size is greater than (or equal to) 25 megabytes, however, our next step is to use this line of code to retrieve a collection of all the files in the folder:<\/P><PRE class=\"codeSample\">Set colFiles = objFolder.Files\n<\/PRE>\n<P>Once we have the collection in hand we set up a For Each loop to loop through each and every file in the folder. Inside the loop, the first thing we do is assign the file <B>Path<\/B> to a variable named strFile, then assign the file creation date and time (the <B>DateCreated<\/B> property) to a variable named dtmFileDate:<\/P><PRE class=\"codeSample\">strFile = objFile.Path\ndtmFileDate = objFile.DateCreated\n<\/PRE>\n<P>So far so good, right? We then compare the value of dtmFileDate to the variable dtmOldestDate:<\/P><PRE class=\"codeSample\">If dtmFileDate &lt; dtmOldestDate Then\n<\/PRE>\n<P>If the value of dtmFileDate (for example, 1\/1\/2007) is less than the value of dtmOldestDate (for example, 2\/2\/2007) that can mean only one thing: this particular file is \u2013 so far anyway \u2013 the oldest file in the folder. Therefore, we assign the file\u2019s creation date to dtmOldestDate, and assign the file path to a variable named strOldestFile:<\/P><PRE class=\"codeSample\">dtmOldestDate = dtmFileDate\nsttrOldestFile = strFile\n<\/PRE>\n<P>See what we\u2019re doing there? That\u2019s right: we\u2019re just using these two variables to keep track of the oldest file in the folder, replacing the values of the two variables each and every time we run into a file older than any other file we\u2019ve looked at.<\/P>\n<P>After that we loop around and repeat the process with the next file in the collection. When we\u2019re done, the path to the oldest file in the collection will be stored in the variable strOldestFile. In turn, that means we can delete the oldest file in the folder simply by passing that variable to the <B>DeleteFile<\/B> method:<\/P><PRE class=\"codeSample\">objFSO.DeleteFile(strOldestFile)\n<\/PRE>\n<P>And that should do it.<\/P>\n<P>Incidentally, it should be obvious which side the Scripting Guy who writes this column takes in the great Pepsi vs. Coke debate. However, even though he doesn\u2019t like Coke very much, the Scripting Guy who writes this column would never disparage anyone who <I>does<\/I> prefer Coke over Pepsi. The truth is, he refuses to say anything bad about Coke at all, even though the fact that Pepsi is sold at the Vatican Museum <I>does<\/I> suggest that Pepsi is the official soft drink of heaven.<\/P>\n<P>Not that Coke drinkers have to worry much about making it to heaven, mind you. <\/P>\n<TABLE class=\"dataTable\" id=\"EZH\" cellSpacing=\"0\" cellPadding=\"0\">\n<THEAD><\/THEAD>\n<TBODY>\n<TR class=\"record\" vAlign=\"top\">\n<TD class=\"\">\n<P><B>Legal and theological disclaimer<\/B>. The preceding statements do not represent the opinions of Microsoft, Pepsi-Cola, Coca-Cola, the Vatican Museum, or heaven. Although the Scripting Editor does seem to think that the Scripting Guy who writes this column is really on to something.<\/P>\n<P>Oops; never mind. Turns out that that the Scripting Editor thinks that the Scripting Guy who writes this column is <I>on<\/I> something. That\u2019s a little different.<\/P><\/TD><\/TR><\/TBODY><\/TABLE><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Hey, Scripting Guy! I need to check the size of a folder once every hour; if the folder has exceeded a specified size, I then need to delete the oldest file in that folder. How can I do that?&#8212; JC Hey, JC. You know, a lot of you are thinking, \u201cGee, I wonder what was [&hellip;]<\/p>\n","protected":false},"author":595,"featured_media":87096,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[38,11,3,12,5],"class_list":["post-64163","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-scripting","tag-files","tag-folders","tag-scripting-guy","tag-storage","tag-vbscript"],"acf":[],"blog_post_summary":"<p>Hey, Scripting Guy! I need to check the size of a folder once every hour; if the folder has exceeded a specified size, I then need to delete the oldest file in that folder. How can I do that?&#8212; JC Hey, JC. You know, a lot of you are thinking, \u201cGee, I wonder what was [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts\/64163","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/users\/595"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/comments?post=64163"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/posts\/64163\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/media\/87096"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/media?parent=64163"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/categories?post=64163"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/scripting\/wp-json\/wp\/v2\/tags?post=64163"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}