I'm repackaging a legacy installation app that was installed a while ago in my environment with a wise installer. The wise uninstall for this was nasty, left a bunch of elements behind.

In my repackaged MSI, I have made a custom action vb script that checks for and removes the legacy installation if it is present. It is run under the Execute Immediate sequence right after InstallInitialize. The script is shown below, although it is not the focus of this problem because the script works when I run it manually, I put it here for reference only. Here's my problem:

When I invoke the script via custom action, (Call VBScript from Embedded Code, Synchronous, Always Execute), the CA runs, but does not actually remove the software, (line sho.run "UNWISE.EXE /S Clientview.LOG",,True), it appears to immediately step through. Again, when I simply run the script it works like a champ, Any ideas on what might be causing this? I really don't want to use a wrapper. Wscript is the default scripting host on all our machines.

Thanks all.


On Error Resume Next
Set sho = Wscript.CreateObject("Wscript.Shell")
Set fso = CreateObject("Scripting.FileSystemObject")
Set objEnv = WshShell.Environment("Process")
strComputer = "."
'******* Abort Removal if legacy install not present
If Not keyExists("ClientView", "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall", &H80000002) Then
msgbox "reg key not found, aborting legacy removal"
wscript.quit(0)
End If
msgbox "initiating legacy removal"
'******* Check for Clientview Processes, kill if running
ProcKill("ClientView.exe")
ProcKill("Client~1.exe")
ProcKill("qCapSvc.exe")
'******* Delete Clientview screen capture service
deleteservice "Qfiniti Screen Capture","TRUE"
'******* Check for Clientview, remove if installed
If keyExists("ClientView", "SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall", &H80000002) Then
sho.CurrentDirectory = "C:\Program Files\AutoQuality"
sho.run "UNWISE.EXE /S Clientview.LOG",,True
msgbox "NOW check for removal..."
End If
If fso.FolderExists("C:\Program Files\AutoQuality") Then
fso.DeleteFolder "C:\Program Files\AutoQuality",force
msgbox "Found and removed C:\Program Files\AutoQuality..."
END IF
If fso.FolderExists("C:\Documents and Settings\All Users\Start Menu\Programs\Etalk ClientView") Then
fso.DeleteFolder "C:\Documents and Settings\All Users\Start Menu\Programs\Etalk ClientView",force
msgbox "Found and removed C:\Documents and Settings\All Users\Start Menu\Programs\Etalk ClientView..."
END IF
'******** Functions Below Here
Function deleteservice(strSvcName,boolStopService)
strComputer = "."
set objWMI = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")
set objService = objWMI.Get("Win32_Service.Name='" & strSvcName & "'")
if boolStopService = TRUE then
intRC = objService.StopService
WScript.Sleep 5000 ' Give the service 5 seconds to stop
end if
intRC = objService.Delete
End Function
Function ProcKill(strProcNam)
Set objWMIService = GetObject("winmgmts:" _
& "{impersonationLevel=impersonate,(Debug)}!\\" _
& strComputer & "\root\cimv2")
Set colProcessList = objWMIService.ExecQuery _
("Select * from Win32_Process Where Name ='"+strProcNam+"'")
For Each objProcess in colProcessList
objProcess.Terminate()
Next
End Function
Function keyExists(strKeyName, strKeyPath, regCategory)
retVal = false
strComputer = "."
Set oReg=GetObject("winmgmts:{impersonationLevel=impersonate}!\\" &_
strComputer & "\root\default:StdRegProv")

oReg.EnumKey regCategory, strKeyPath, arrSubKeys

For Each subkey In arrSubKeys
If strKeyName = subkey Then
retVal = true
Exit For
End If
Next
keyExists = retVal
End Function
0 Comments   [ + ] Show Comments

Comments

Please log in to comment

Rating comments in this legacy AppDeploy message board thread won't reorder them,
so that the conversation will remain readable.

Answers

0
(line sho.run "UNWISE.EXE /S Clientview.LOG",,True),

seems you will need to change your processing options to "asynch no wait"
Answered 08/19/2009 by: cygan
Fifth Degree Brown Belt

Please log in to comment
2
Change:

Set sho = Wscript.CreateObject("Wscript.Shell")

To:

Set sho = CreateObject("Wscript.Shell")

Cheers,
Rob.
Answered 08/19/2009 by: MSIPackager
Third Degree Black Belt

Please log in to comment
0
Set sho = Wscript.CreateObject("Wscript.Shell")
well spotted wscript.createobject is not suppported in windows installer

well this is another good interview question

but please no one should re ignite that thread
cheers
Answered 08/19/2009 by: cygan
Fifth Degree Brown Belt

Please log in to comment
0
Well spotted indeed. Thanks very much for the assist guys, always a pleasure.
Answered 08/19/2009 by: elgwhoppo
Senior Purple Belt

Please log in to comment
0
Also remember that everything after InstallFinalize in the EI sequence runs in user context so you need to be running the MSI as a local administrator or equivalent.
Answered 08/19/2009 by: VBScab
Red Belt

Please log in to comment
0
well spotted wscript.createobject is not suppported in windows installer

Jeeez. We'll make this issue a sticky one day.....[;)]

http://itninja.com/question/faulttree-101268&mpage=1&key=wscript%2E즉
http://www.appdeploy.com/messageboards/tm.asp?m=8333&mpage=1&key=wscript%2E쥔
http://itninja.com/question/faulttree-100754&mpage=1&key=wscript%2Cengine왏
http://itninja.com/question/faulttree-100362&mpage=1&key=wscript쓄
Answered 08/19/2009 by: captain_planet
Third Degree Brown Belt

Please log in to comment
0
Ya.. must be the oldest trick in the book.

No point making it a sticky.. noone reads them.... [;)]
Answered 08/19/2009 by: MSIPackager
Third Degree Black Belt

Please log in to comment
0
[:(] Ouch guys, go easy on a typo! I'm aware that the method isn't supported, just didn't catch it because I copied my declaration from another script.
Answered 08/19/2009 by: elgwhoppo
Senior Purple Belt

Please log in to comment
0
ORIGINAL: elgwhoppo

.
.
.
wscript.quit(0)
.
.
.
WScript.Sleep 5000 ' Give the service 5 seconds to stop



And for the sake of completeness, the above lines won't work for the reasons already given in earlier replies.

Regards,

Spartacus
Answered 08/19/2009 by: spartacus
Black Belt

Please log in to comment
2
All my scripts have a test for the Session object and set a Boolean according to its presence or absence. That Booelan is then tested at the appropriate time. It makes for a little more code but it means that, once my script is tested externally, it can be used more or less immediately in a package.

None use WScript.Quit - proper error-handling and the use of functions obviates its use - or WScript.Echo - I use the Event Log and/or Windows Installer log. Sleep is a little tricker, but some imagination helps:Call Sleep(5)

Sub Sleep(ByVal intDelayInSecs)
Dim datStart
Dim blnCompleted

datStart = Now()
blnCompleted = False

While Not blnCompleted
If DateDiff("s", datStart, Now()) >= CInt(intDelayInSecs) Then
blnCompleted = True
End If
Wend
End Sub
Answered 08/19/2009 by: VBScab
Red Belt

Please log in to comment
0
Perfect, great subroutine. Thanks Ian.
Answered 08/20/2009 by: elgwhoppo
Senior Purple Belt

Please log in to comment
Answer this question or Comment on this question for clarity