Brian Madden Logo
Your independent source for application and desktop virtualization.
advertisement

Script for replacing appsrv and pn ini files (and limited content) during client upgrade, in the Client / End User Issues forum on BrianMadden.com

rated by 0 users
This post has 2 Replies | 1 Follower

Top 500 Contributor
Points 510
Ben Moore Posted: Tue, May 6 2008 9:00 AM
I wrote this script (which I package in an MSI and deploy via GP with my ICA Client) to force a replacement of the appsrv and pn ini files after a client upgrade. Originally, I wrote it to fix the "Failed to set event logging" message I was seeing during an ICA client upgrade when the INI files were not replaced.

I'm not a coding genius, but it's functional! I hope it can be useful to someone else.

This script does three things:

Replaces the user's \Application Data\ copies of the INI files with the "good" versions from the \Program Files\Citrix\ICA Client\ directory

Replaces the "Username=" line in pn.ini with the old version (so users won't get confused after the upgrade)

Replaces the Logfile=, LogfileWin32= and PersistentCachePath= values with locations that are writable to a user who's logged into a secured PC.

Save As whatever.vbs


'//////////////////////////\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'
'///////////INI Parse, Replace, Merge script\\\\\\\\\\\\'
'/////////////////moore.ben@gmail.com\\\\\\\\\\\\\\\\\\\'
'//////////////////////05/06/08\\\\\\\\\\\\\\\\\\\\\\\\\'
'///////////////////////Rev 1.1\\\\\\\\\\\\\\\\\\\\\\\\\'
'///////\\\\\\\\\\\\\\\\\\\////////////////////\\\\\\\\\'

'On Error Resume Next
strComputer = "."
Const ForReading = 1
Const ForWriting = 2
Const OverwriteExisting = TRUE

Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objShell = WScript.CreateObject("WScript.Shell")
Set objDictionary = CreateObject("Scripting.Dictionary")

strSourcePN = "c:\program files\citrix\ica client\pn.ini"
strSourceAP = "c:\program files\citrix\ica client\appsrv.ini"
strDrive = objShell.ExpandEnvironmentStrings("%HOMEDRIVE%")
ProfileFolder = strDrive & "\Documents and Settings\"
GetSubFolders objFso.GetFolder(ProfileFolder)

For Each strKey in objDictionary.Keys

strDestPN = objDictionary.Item(strKey) & "pn.ini"
strINIUsername = ReadINI(strDestPN)
strNewUsernameLoc = ReadINI(strSourcePN)
Do Until True
'//////If no source username string (IE, File is missing, app not installed)...\\\\\\'
If (strNewUsernameLoc = "") Then
wscript.quit
End If
'//////If no initial username value, and New value is good...\\\\\\'
If (strINIUsername = "" AND strNewUsernameLoc <> "") Then
strReplaceError = ReplaceINI(strDestPN,strSourcePN,strError)
Exit Do
End If
'//////If initial and replacement values are good...\\\\\\'
If (strINIUsername <> "" AND strNewUSernameLoc <> "") Then
strReplaceError = ReplaceINI(strDestPN,strSourcePN,strError)
Else
Exit Do
End If
'//////If replacement of INI files succeeded...\\\\\\'
If strError = "" Then
strNewUsernameLocLC = LCase(strNewUsernameLoc)
If Left(strNewUsernameLocLC, 9) = "username=" Then
strReplaceUserName = ReplaceUserName(strDestPN,strNewUsernameLoc,strINIUsername)
Else
wscript.quit
End If
Else
wscript.quit
End If
Loop
strDestAP = objDictionary.Item(strKey) & "appsrv.ini"
strReplaceError = ReplaceINI(strDestAP,strSourceAP,strError)
strReplacePaths = ReplacePaths(strDestAP)
Next

'//////Reads all subdirectories of \Documents and Settings\ and adds path if there's valid INI files present\\\\\\'
Sub GetSubFolders (Folder)
For Each Subfolder in Folder.SubFolders
If InStr(Subfolder.Path, "Administrator") Or InStr(Subfolder.Path, "All Users") Or InStr(Subfolder.Path, "Default User") Or InStr(Subfolder.Path, "LocalService") Or InStr(Subfolder.Path, "NetworkService") Then
Else
If objFSO.FileExists(Subfolder.Path & "\Application Data\ICAClient\appsrv.ini") Or objFSO.FileExists(Subfolder.Path & "\Application Data\ICAClient\pn.ini") Then
objDictionary.Add Subfolder.Path,(Subfolder.Path & "\Application Data\ICAClient\")
End If
End If
Next
End Sub

'//////Reads original INI files for existing usernames\\\\\\'
Function ReadINI(strINIPath)
If objFSO.FileExists(strINIPath) Then
Set objFile = objFSO.OpenTextFile(strINIPath, ForReading)
Else
Exit Function
End If
Do Until objFile.AtEndOfStream
strLine = objFile.ReadLine
strLCLine = LCase(strLine)
If Left(strLCLine, 9) = "username=" Then
ReadINI = strLine
End If
Loop

objFile.close
End Function

'//////Replace original INI files with new from Program Files\Citrix\ICA Client\\\\\\'
Function ReplaceINI(strDestPath,strSourcePath,byref strError)
set objSourceFile = objFSO.GetFile(strSourcePath)
strError = objFSO.CopyFile (objSourceFile.Path, strDestPath, OverwriteExisting)
End Function

'//////Re-add original username to new file, replacing new string\\\\\\'
Function ReplaceUsername(strDestPath,strNewUsernameLoc,strINIUsername)
Set objFile = objFSO.OpenTextFile(strDestPath, ForReading)
strText = objFile.ReadAll
objFile.Close

intUserString = Len(strINIUsername)
strINIUsernameUC = UCase(Left(strINIUsername, 1))
strINIUsernameLC = LCase(Right(strINIUsername, intUserString - 1))
strINIUsername = strINIUsernameUC & strINIUsernameLC

set objReg = New RegExp
objReg.Global = True
objReg.IgnoreCase = True
objReg.Pattern = strNewUsernameLoc

If strNewUsernameLoc <> "" Then
strNewText = objReg.Replace(strText, strINIUsername)
Else
wscript.quit
End If

Set objFile = objFSO.OpenTextFile(strDestPath, ForWriting)
objFile.WriteLine strNewText
objFile.Close
End Function

'//////Replace paths to LogFile and Cache files with user-writable directories\\\\\\'
Function ReplacePaths(strDestPath)
colPath = Split(strDestPath, "\")
i = 0
For Each objItem in colPath
i = i + 1
If objItem = "Documents and Settings" Then
strUsername = colPath(i)
End If
Next

Set objFile = objFSO.OpenTextFile(strDestPath, ForReading)

Do Until objFile.AtEndOfStream
strNextLine = objFile.Readline
strNextLineLC = lcase(strNextLine)

intLineFinder = Instr(strNextLineLC, "logfile=")
If intLineFinder <> 0 Then
strNextLine = ("LogFile=" & strDrive & "\Documents and Settings\Application Data\" & strUsername & "\ICAClient\wfclient.log")
End If

intLineFinder = Instr(strNextLineLC, "logfilewin32=")
If intLineFinder <> 0 Then
strNextLine = ("LogFileWin32=" & strDrive & "\Documents and Settings\Application Data\" & strUsername & "\ICAClient\wfcwin32.log")
End If

intLineFinder = Instr(strNextLineLC, "persistentcachepath=")
If intLineFinder <> 0 Then
strNextLine = ("PersistentCachePath=" & strDrive & "\Documents and Settings\Application Data\" & strUsername & "\ICAClient\Cache\")
End If

strNewFile = strNewFile & strNextLine & vbCrLf
Loop

objFile.Close

Set objFile = objFSO.OpenTextFile(strDestPath, ForWriting)

objFile.WriteLine strNewFile
objFile.Close
End Function


This script is provided without guarantees, use it at your own risk etc. etc.
  • | Post Points: 20
Top 500 Contributor
Points 510
Just a quick heads up that you'll want to change the paths in the "ReplacePaths" function to \Documents and Settings\" & strUsername & "\Application Data\ICAClient\" instead of the backwards way I have written above
  • | Post Points: 5
Top 75 Contributor
Points 2,145

To revive this thread, this still occurs with the 11.x client:

This problem can occur for sevaeral reasons:

1. It appears that the APPSRV.INI file under \Documents and Settings\<<UserID>>\Application Data\ICAClient records the location of wfcwin32.log, which is also under the same directory, has an in correct path statement. This usually occurs if you have roaming profiles and are experencing stuck profiles and users are getting UserID.000, UserID.001, etc

2. The location of the wfcwin32.log file is write protected.

To correct for this, ensure that users are able to write to the path specified in the APPSRV.INI file.

Additional methods of correcting for this:

1. Delete the APPSRV.INI at login as part of a login script.

2. Preconfigure APPSRV.INI under Default User\Application Data\ICAClient\ (create folder and file) to point to a commonly accessible logation, like \Temp\logs\wfcwin32.log.  However this will not fix the problem for existing users who have profiles already.  Option 1 is best.

  • | Post Points: 5
Page 1 of 1 (3 items) | RSS