Rob Moore
Rob Moore

Reputation: 146

VBScript read text file created in windows terminal substitutes characters

In a windows cmd terminal I am using something like dir *.mp3 *.wma *.m4a /s /b > c:\temp\random.tmp to save filenames with paths to the text file c:\temp\random.tmp. It works really well and is fast from inside of vbscript. The problem that I am having is that the text file is saved with a code page of 437 not the windows default. I have tried changing the code page in the command terminal before i redirect the folder contents into the text file and that does not seem to work.

In the windows cmd terminal if I type the text file I see "Beyoncé - Trust In Me.mp3", in vbscript i see "Beyonc, - Trust In Me.mp3", and if i open the text file in windows i see "Beyonc, - Trust In Me.mp3".

If I set the cmd terminal code page to 1252 then the "é" is only replaced with a "," in vbscript. I have tried using adodb with all of its character set and nothing seems to work.

here is my code, can someone help?

'dim MediaExtensions
'MediaExtensions = Array("mp3", "wma", "m4a")
'SourcePath = "C:\Users\Rob\Desktop\Script Project\work in progress\Jukebox\mp3\"
'wscript.echo ListMediaFiles(SourcePath, MediaExtensions)

Function ListMediaFiles(SourcePath, MediaExtensions)
Dim ListFiles, MediaFSO, MediaPath, TempFile, CMDShell, OpenFile, x, objShell 'declare variables"
Const ForReading = 1, ForWriting = 2, ForAppending = 8
Const TristateUseDefault = -2, TristateTrue = -1, TristateFalse = 0

Set MediaFSO = CreateObject("Scripting.FileSystemObject") 'create FileSystemObject MediaFSO

Set CMDShell = CreateObject("WScript.Shell") 
strFolder = CMDShell.CurrentDirectory 

TempFile = MediaFSO.GetTempName 'Create unique (random) name for the TempFile
MediaPath = MediaFSO.GetSpecialFolder(2) 'the 2 = the system temp folder. in this case it is c:\temp
TempFile = MediaPath & "\" & TempFile 'join the MediaPath and TempFile to create a complete path to file. c:\temp\random.tmp

For each x in MediaExtensions ' create search string from SourcePath and MediaExtensions 
FileExtentions = FileExtentions & Chr(34) & lcase(trim(SourcePath)) & "*." & x & Chr(34) & " " 'the x is each element in the MediaExtensions array
Next    
ListFiles = "dir " & FileExtentions & " /s /b" 'create search string. using the example above the search string = dir  *.mp3 *.wma *.m4a /s /b. We can use the dos dir command to search for more than one extension at the same time. The /s means search all sub folders. The /b is to return only the path and filename.
CMDShell.Run "%comspec% /c " & ListFiles & " >" & TempFile, 0, True 'Gather file names using CMDShell to run "dir  *.mp3 *.wma *.m4a /s /b" and saved in "c:\temp\random.tmp."
'CMDShell.Run "%comspec% /k " & ListFiles & " >" & TempFile, 3, True ' use this if you need to trouble shoot the command line, it will not show you the command line but if there is an error your will see it
'chcp 1252&

set CheckFile = MediaFSO.GetFile(TempFile)
If CheckFile.Size > 0 then
'*********************************************
'Dim objStream
'Set objStream = CreateObject("ADODB.Stream")
'objStream.CharSet = "iso-8859-1"
'objStream.Open
'objStream.LoadFromFile(TempFile)
'ListMediaFiles = objStream.ReadText()
'objStream.Close
'msgbox ListMediaFiles
'*********************************************        

'cint(objFile.Size / bytesToKb)
Set OpenFile = MediaFSO.OpenTextFile(TempFile,ForReading,False,TristateUseDefault) 'Open as text "c:\temp\random.tmp"
ListMediaFiles = OpenFile.Readall 'read the whole "c:\temp\random.tmp" into memory 
OpenFile.Close 'close "c:\temp\random.tmp"
msgbox ListMediaFiles
Else
Msgbox "No Media Found in " & SourcePath
End if
MediaFSO.DeleteFile TempFile 'Delete "c:\temp\random.tmp"
End Function

Upvotes: 0

Views: 426

Answers (2)

Kul-Tigin
Kul-Tigin

Reputation: 16950

First, you need to specify /u parameter for cmd.exe to generate unicode output.
Then open the file as Unicode if it is by specifying TristateMixed.
So, you need to modfiy these two lines:

Const TristateMixed = -2
CMDShell.Run "cmd.exe /u /c " & ListFiles & " >" & TempFile, 0, True
Set OpenFile = MediaFSO.OpenTextFile(TempFile, ForReading, False, TristateMixed)

Upvotes: 2

Rob Moore
Rob Moore

Reputation: 146

Ok so I have not really answered my own question, but I have a workaround for this one character.

After the random.tmp file is closed I replace chr(130) with Chr(233).

Chr(130) is "é" in dos code page 437 Chr(233) is "é" in 28592 / ISO-8859-2 windows default.

with ISO-8859-2 Chr(130) is "‚" which is not the same as Chr(44) "," even thought they look the same.

I did try to use chcp 28592 before the dos redirect to a temp file but end up with the same result which leads me to believe that the chcp command has no effect on redirection

I am sure I will end up having other issues in the future with dos vs windows code pages. But for now I will be using the replace command.

here is the command I used

ListMediaFiles = replace(ListMediaFiles,Chr(130),Chr(233))

Here is the complete code

'dim MediaExtensions
'MediaExtensions = Array("mp3", "wma", "m4a")
'SourcePath = "C:\Users\Rob\Desktop\Script Project\work in progress\Jukebox\mp3\"
'wscript.echo ListMediaFiles(SourcePath, MediaExtensions)

Function ListMediaFiles(SourcePath, MediaExtensions)
Dim ListFiles, MediaFSO, MediaPath, TempFile, CMDShell, OpenFile, x, objShell 'declare variables"

Set MediaFSO = CreateObject("Scripting.FileSystemObject") 'create FileSystemObject MediaFSO

Set CMDShell = CreateObject("WScript.Shell") 
strFolder = CMDShell.CurrentDirectory 

TempFile = MediaFSO.GetTempName 'Create unique (random) name for the TempFile
MediaPath = MediaFSO.GetSpecialFolder(2) 'the 2 = the system temp folder. in this case it is c:\temp
TempFile = MediaPath & "\" & TempFile 'join the MediaPath and TempFile to create a complete path to file. c:\temp\random.tmp

For each x in MediaExtensions ' create search string from SourcePath and MediaExtensions 
FileExtentions = FileExtentions & Chr(34) & trim(SourcePath) & "*." & x & Chr(34) & " " 'the x is each element in the MediaExtensions array
Next    
ListFiles = "dir " & FileExtentions & " /s /b" 'create search string. using the example above the search string = dir  *.mp3 *.wma *.m4a /s /b. We can use the dos dir command to search for more than one extension at the same time. The /s means search all sub folders. The /b is to return only the path and filename.
CMDShell.Run "%comspec% /c " & ListFiles & " >" & TempFile, 0, True 'Gather file names using CMDShell to run "dir  *.mp3 *.wma *.m4a /s /b" and saved in "c:\temp\random.tmp."

set CheckFile = MediaFSO.GetFile(TempFile)
If CheckFile.Size > 0 then
Set OpenFile = MediaFSO.OpenTextFile(TempFile) 'Open as text "c:\temp\random.tmp"
ListMediaFiles = OpenFile.Readall 'read the whole "c:\temp\random.tmp" into memory 
OpenFile.Close 'close "c:\temp\random.tmp"

ListMediaFiles = replace(ListMediaFiles,Chr(130),Chr(233))

Else
Msgbox "No Media Found in " & SourcePath
End if
MediaFSO.DeleteFile TempFile 'Delete "c:\temp\random.tmp"
End Function

Upvotes: 0

Related Questions