Link to home
Start Free TrialLog in
Avatar of sunhux
sunhux

asked on

Windows Batch or VB script to return the directory holding a given file name

Hi,

There are over 1000 files in our shared drive / folder ;  though there's certain naming
convention, I still find it tough to trace which folder holds say a given filename.

Suppose I want a filename which has the term/text "contacts" in it (as I want to update
person's contact info of a Word Doc), I would normally do  at Windows MSDOS prompt :
a) dir/s z:\ > c:\temp\shdrv.txt
b) use Wordpad to search for the string "contacts"

Now, since I have a scheduled task to update shdrv.txt daily to my c:\temp
I'll need a script that could help me read the file shdrv.txt & then return all
the various occurrences of the filenames (with their date of creation/modification)
with the string "xxxxxxx" plus the directories that hold each of the filenames that
contain the string "xxxxxxx".

Using "find/I "string" shdrv.txt" returns the filenames but is missing on the
directories that hold the files
Avatar of Meir Rivkin
Meir Rivkin
Flag of Israel image

change MATCH_TOKEN to whatever required.
the search is case-insensitive, to change it to case sensitive, set CASE_SENSITIVE to true.
const MATCH_TOKEN = "crypto"
const CASE_SENSITIVE = false
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objInputFile = objFSO.OpenTextFile("c:\temp\shdrv.txt", 1)

for each file in Split(objInputFile.ReadAll, vbCrLf)
	
	if MatchFileName(file) = true then
		Set objFile = objFSO.GetFile(file)
		Wscript.Echo "Name: " & objFile.Name
		Wscript.Echo "Date created: " & objFile.DateCreated
		Wscript.Echo "Date last accessed: " & objFile.DateLastAccessed
		Wscript.Echo "Date last modified: " & objFile.DateLastModified
		Wscript.Echo "Drive: " & objFile.Drive
		Wscript.Echo "Parent folder: " & objFile.ParentFolder
		Wscript.Echo "Path: " & objFile.Path
		Wscript.Echo "Short name: " & objFile.ShortName
		Wscript.Echo "Short path: " & objFile.ShortPath
		Wscript.Echo "Size: " & objFile.Size
		Wscript.Echo "Type: " & objFile.Type
		Wscript.Echo
	end if
Next

Function MatchFileName(file)

if CASE_SENSITIVE = false then
	MatchFileName = InStr(UCase(file), UCase(MATCH_TOKEN)) > 0 
else
	MatchFileName = InStr(file, MATCH_TOKEN) > 0 
end if

End Function

Open in new window

strRootFolder = "Z:\"
str = "test"

Set objWshShell = WScript.CreateObject("WScript.Shell")
Set objFileSystem = WScript.CreateObject("Scripting.FileSystemObject")
Set objTxtFile = objFileSystem.CreateTextFile("C:\temp\temp.txt", True)
Set objRootFolder = objFileSystem.getFolder(strRootFolder)

FindFilesInFolder(objRootFolder)

objTxtFile.Close
Set objTxtFile = Nothing

Sub FindFilesInFolder(objFolder)
      For Each objFile in objFolder.Files
            If Instr(LCase(objFile.Name), str) Then
                  objTxtFile.WriteLine objFile.Name & "      " & objFolder.Path & 

"      " & objFile.DateLastModified
            End If
      Next

      For Each objSubFolder In objFolder.SubFolders
            FindFilesInFolder(objSubFolder)
      Next
End Sub

SOLUTION
Avatar of Peter Kwan
Peter Kwan
Flag of Hong Kong image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
another method

copy the code to notepad and save with vbs extension

change line 1 for file name and path to extrect data
line 2 folder to check for files

notice: the script will do the "dir" part for you and in the same time
will check if there is contacs in file name and extrect only the one that match

if the file not exist the script will create if exist the script will append to existing file

test and see
strFile = "c:\shdrv.txt"
objStartFolder = "c:\folder_to_check"

set objShell = CreateObject("wscript.Shell")
Set objFSO = CreateObject("Scripting.FileSystemObject")
If Not objfso.FileExists(strFile) then
Set objlog = objfso.CreateTextFile(strFile,True)
Else
Set objlog = objfso.OpenTextFile(strFile,8)
End If

'objlog.WriteLine "Name" & vbTab & "Path" & vbTab & "DateCreated" & vbTab & "DateLastModified"

Set objFolder = objFSO.GetFolder(objStartFolder)
Set colFiles = objFolder.Files
For Each objFile in colFiles
    If InStr(objFile.Name,"contacts") Then 
            objlog.WriteLine objFile.Name & vbTab & objfile.Path & vbTab & objFile.DateCreated & vbTab & objfile.DateLastModified
    End if
Next
Wscript.Echo

ShowSubfolders objFSO.GetFolder(objStartFolder)

objlog.Close

objshell.Popup "done",5

Sub ShowSubFolders(Folder)
    For Each Subfolder in Folder.SubFolders
        Set objFolder = objFSO.GetFolder(Subfolder.Path)
        Set colFiles = objFolder.Files
        For Each objFile in colFiles
            If InStr(objFile.Name,"contacts") Then 
            objlog.WriteLine objFile.Name & vbTab & objfile.Path & vbTab & objFile.DateCreated & vbTab & objfile.DateLastModified
            End if
        Next
        Wscript.Echo
        ShowSubFolders Subfolder
    Next
End Sub

Open in new window

forgot to remove something use this
strFile = "c:\shdrv.txt"
objStartFolder = "c:\folder_to_check"

set objShell = CreateObject("wscript.Shell")
Set objFSO = CreateObject("Scripting.FileSystemObject")
If Not objfso.FileExists(strFile) then
Set objlog = objfso.CreateTextFile(strFile,True)
Else
Set objlog = objfso.OpenTextFile(strFile,8)
End If

'objlog.WriteLine "Name" & vbTab & "Path" & vbTab & "DateCreated" & vbTab & "DateLastModified"

Set objFolder = objFSO.GetFolder(objStartFolder)
Set colFiles = objFolder.Files
For Each objFile in colFiles
    If InStr(objFile.Name,"contacts") Then 
            objlog.WriteLine objFile.Name & vbTab & objfile.Path & vbTab & objFile.DateCreated & vbTab & objfile.DateLastModified
    End if
Next


ShowSubfolders objFSO.GetFolder(objStartFolder)

objlog.Close

objshell.Popup "done",5

Sub ShowSubFolders(Folder)
    For Each Subfolder in Folder.SubFolders
        Set objFolder = objFSO.GetFolder(Subfolder.Path)
        Set colFiles = objFolder.Files
        For Each objFile in colFiles
            If InStr(objFile.Name,"contacts") Then 
            objlog.WriteLine objFile.Name & vbTab & objfile.Path & vbTab & objFile.DateCreated & vbTab & objfile.DateLastModified
            End if
        Next
        ShowSubFolders Subfolder
    Next
End Sub

Open in new window

@yehudaha, @pkwan

i might be wrong but according to @sunhux, the scheduler task already generates shdrv.txt contains list of all files which needed to be lookup for match string.
so no need to iterate files in folders etc.

>>I'll need a script that could help me read the file shdrv.txt & then return all the various occurrences of the file ...

see what @sunhux have to say about it...
Avatar of sunhux
sunhux

ASKER


Yes, sedgwick is right, I already have a scheduled job myself daily to generate shdrv.txt


Hi sedgwick,

What's  "const MATCH_TOKEN = "crypto"  "  for?
What other values I can change it to?  Sorry, I'm VB illiterate
MATCH_TOKEN is the variable u want to change for the matched string.
if u look for "contact" in the files names, change the value of MATCH_TOKEN to "contact", simple as that.

the other value u can change is CASE_SENSITIVE.
the default (as u can see in the script) is false, which means that if you set MATCH_TOKEN to "contact" and the file name is ConTact123.txt, the script will output this file as well.
if you change this value to true, that means the search is case-sensitive and it look for exact phrase in the file name.
so ConTact123.txt will not be output by the script.
sorry about the confusion, "crypto"  was just an example when i tested the script in my machine.
so whats the probelm to run scheduled job on my script ?

all the work in one place insted to split it
Avatar of sunhux

ASKER


When I ran Sedgwick's vbs script (I name it as filedir.vbs), I got "file not found"
I ran the script as follows :
d:\shareware\filedir.vbs "contact"



For Yehudaha's script, I need to pass the parameter "contacts" ie part of the file name
as parameter & not hardcode into the script  & the script should not need to search
the entire folder "objStartFolder = "z:\"   anymore as this is time-consuming/slow.
Just need to search c:\temp\shdrv.txt
Avatar of sunhux

ASKER



Similar comments for pkwan's scripts (as mentioned for Yehudaha's script)
Avatar of sunhux

ASKER


Oh, btw, since there's 3 VB experts in this thread, may I request all of you to take
a look at another EE thread  ID: 32791511  which is also VB related as the other
expert is now stuck
@sunhux

i didn't say that u need to pass a parameter to the script.
the "contact" you wish to look, should be placed in the script itself (MATCH_TOKEN) as i explained in my previous post.

here's a modified script which accept parameter to look for in file names, so u can use either scripts.


const CASE_SENSITIVE = true
MATCH_TOKEN = Wscript.Arguments(0)
Wscript.Echo "Lookup token: " & MATCH_TOKEN
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objInputFile = objFSO.OpenTextFile("c:\temp\shdrv.txt", 1)

for each file in Split(objInputFile.ReadAll, vbCrLf)
	
	if MatchFileName(file) = true then
		Set objFile = objFSO.GetFile(file)
		Wscript.Echo "Name: " & objFile.Name
		Wscript.Echo "Date created: " & objFile.DateCreated
		Wscript.Echo "Date last accessed: " & objFile.DateLastAccessed
		Wscript.Echo "Date last modified: " & objFile.DateLastModified
		Wscript.Echo "Drive: " & objFile.Drive
		Wscript.Echo "Parent folder: " & objFile.ParentFolder
		Wscript.Echo "Path: " & objFile.Path
		Wscript.Echo "Short name: " & objFile.ShortName
		Wscript.Echo "Short path: " & objFile.ShortPath
		Wscript.Echo "Size: " & objFile.Size
		Wscript.Echo "Type: " & objFile.Type
		Wscript.Echo
	end if
Next

Function MatchFileName(file)

if CASE_SENSITIVE = false then
	MatchFileName = InStr(UCase(file), UCase(MATCH_TOKEN)) > 0 
else
	MatchFileName = InStr(file, MATCH_TOKEN) > 0 
end if

End Function

Open in new window

the usage is as follow:

:\shareware\filedir.vbs "contact"
hey

this will read your file from c:\temp\shdrv.txt
and output the directory with matching file name to the string to search

run from cmd for example:

cscript script_name.vbs contacts

where contacts is the string to search

you can change file location in line 13
If WScript.Arguments.Count = 0 Then
MsgBox "No Argument"
WScript.Quit
End If


Const ForReading = 1

Set objRegEx = CreateObject("VBScript.RegExp")
objRegEx.Pattern = WScript.Arguments.Item(0)

Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objFile = objFSO.OpenTextFile("c:\temp\shdrv.txt", ForReading)

Do Until objFile.AtEndOfStream
strSearchString = objFile.ReadLine
if instr(strSearchString,"Directory") Then
strPath = strSearchString
End If
    Set colMatches = objRegEx.Execute(strSearchString)  
    If colMatches.Count > 0 Then
        For Each strMatch in colMatches
            WScript.Echo strPath   
            Wscript.Echo strSearchString 
            WScript.Echo
        Next
    End If

Loop

objFile.Close

Open in new window

@sunhux

>>a look at another EE thread  ID: 32791511  which is also VB related as the other
can u post the link to the thead?
Avatar of sunhux

ASKER


sedgwick's script still has an error :
I ran it as follows:
  d:\shareware\filedir.vbs "contact"
It 1st gave a popup saying "Lookup token : contact" & after I click OK,
it gave a "File not found" error popup indicating Line 10, Char 3 :
see attached screen shot


Just to illustrate what I wanted using find command,

D:\shareware>find/I "contact" c:\temp\shdrv.txt | more
---------- C:\TEMP\SHDRV.TXT
10/15/2007  06:36 PM           491,008 Update Subcontractor Leave Contact Number.doc
12/01/2008  11:01 AM            76,288 Contact List 01122008_v28.0.xls
. . .

So what I wanted your VB scripts to do is to list out the following outputs:

Directory of Z:\Operations\Vendors\
10/15/2007  06:36 PM           491,008 Update Subcontractor Leave Contact Number.doc

Directory of Z:\DR\Year2008
12/01/2008  11:01 AM            76,288 Contact List 01122008_v28.0.xls



Will test yehudaha's script
Filedirerrscrdmp.doc
Avatar of sunhux

ASKER


yedudaha's script works fine.


Anybody care to take up another challenge in another post which I've put up :
... may I request all of you to take a look at another EE thread  ID: 32791511
  which is also VB related as the other expert is now stuck
Avatar of sunhux

ASKER


Oh, I just realize Yedudaha's script search for a case-sensitive string (say "contact").

Care to make it case-insensitive ?
glad it helped don't forget to close the question :-)

and post the full link to your question
ASKER CERTIFIED SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
@sunhux

the reason of the error is because the file it tried to open is not accessible.
if the only thing u need is compare the file name + log the parent directory, use the following script.


const CASE_SENSITIVE = true
const SOURCE_FILE = "c:\temp\shdrv.txt"
MATCH_TOKEN = Wscript.Arguments(0)

Wscript.Echo "Source file: " & SOURCE_FILE
Wscript.Echo "Lookup token: " & MATCH_TOKEN

Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objInputFile = objFSO.OpenTextFile(SOURCE_FILE, 1)

Do Until objInputFile.AtEndOfStream
	file = objInputFile.ReadLine	
	
	if MatchFileName(file) = true then
		path = Mid(file, 1, InStrRev(file, "\"))
		fileName = Replace(file,path,"")
		Wscript.Echo "Directory of " & path
		Wscript.Echo Date & " " & Time & " " & fileName
		
	end if
Loop

objInputFile.Close

Function MatchFileName(file)

if CASE_SENSITIVE = false then
	MatchFileName = InStr(UCase(file), UCase(MATCH_TOKEN)) > 0 
else
	MatchFileName = InStr(file, MATCH_TOKEN) > 0 
end if

End Function

Open in new window

the output is in the form u requested.
btw, what is the meaning of the number preceeding the file name in your example?

Directory of Z:\DR\Year2008
12/01/2008  11:01 AM            76,288 Contact List 01122008_v28.0.xls

what 76,288 refer to??
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of sunhux

ASKER


Both sedgwick & yedudaha's latest scripts work as per what I needed.

Thanks
please first close this thread.

cheers