Uninstall exe program in through cmd - c#

I am writing an app to remove an old version of Qmuzik ERP software from a network and install the new version. I have used the Process methods in C# to execute the msi through a cmd command to install the new version. The command I use is:
msiexec /qn /i "MSI Path"
This works beautifully.
The reason I am doing this is because of the fact that there are more than one msi which has to be run in sequence. Using the process method I can watch the process and detect when it is done and execute the next msi in the sequence. All of this happens quietly on the users pc.
The problem is, before I can install the new version I have to uninstall the previous version. The old version was installed on to the machines using an exe setup file. I have tried converting the exe file to msi and using msiexec to uninstall through command line but it has no effect on the instances that has been installed with the exe and not the converted msi (which is the entire network)
Is there any Command that I can use in cmd to uninstall these instances that has been installed using the exe?

When you install a program in Windows a registry key for its uninstallation is created holding several values, among them is the UninstallString value which is the command line the Add or remove programs uses when you click Remove.
The parent key is:
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall
And these UninstallStrings usually have the following format:
MsiExec.exe /I{0826F9E4-787E-481D-83E0-BC6A57B056D5}
In order to acomplish what you are trying to do you will have to create a RegistryKey object, read the UninstallString value for the application you want to remove and run the command line.
More info here.

You can use revo uninstaller, not for its uninstallation features, but for its main view, that shows the registered uninstall string of your application.
But it's only a starting point. Every setup engine can have its own uninstall string. You have to find the correct one, if you are lucky enough for it to exists (try /quiet, /passive, etc. until you find the correct one).

Go to the FIle Path, looks for a .exe which you need to uninstall. In command prompt open the path of .exe located and execute "xxxx.exe --uninstall".

Related

Microsoft Visual Studio Installer Projects - how to provide restart prompt to MSI executed with Process.Start(), but without Repair option

The problem is following: I have my custom uninstaller called before MSI uninstall. After shutting down my application properly it calls msiexec to use Windows Installer to uninstall MSI.
It's done by executing something like "msiexec /x{PRODUCT_CODE} /promptrestart".
And here is important thing - if the system is not restarted after uninstallation, and then the user installs the app again, some of its files will be deleted after next restart, so it's not acceptable. The restart is required, however, I need prompt, automatic and unconditional restart is evil and should never ever be used.
So, the invocation above displays STUPID "uninstall / repair" dialog. I do not want it. When I use "msiexec /x{PRODUCT_CODE} /qr /promptrestart" - then it uninstalls nicely, however it refuses propt for restart afterwards.
I have read about setting ARPNOREPAIR property.
But the idiots who gave that answer wouldn't care to say WHERE and HOW that property could be set. Even... Where the property belongs, it's the property of what? MSI file?
Then, maybe is it another way to achieve this, like invoke the prompt for restart from my code, but... how? The uninstaller should remove all my files until that moment. Maybe it's possible to execute a kind of script after the uninstallation process is complete?
(One more problem, the Windows Installer doesn't delete ALL files and directories created by my app. It would be nice if I could execute some code to clean up better.)
UPDATE
I see 2 paths ahead: make a script to be run once the uninstallation ends (like using Registry or Task Scheduler or IDK), use Win32 API to modify MSI file, because AFAIK it's possible to change its properties that way.
Questions: Some questions first.
Restart Manager: Are you familiar with the Restart Manager feature of MSI? Intended to help shut down and restart
applications without the need for reboots. I would give it a quick
skim? I think this is your real solution?
Alternative MSI Tools: There are many tools available for creating MSI setups. This link also contains further links to a summary of the shortcomings of Visual Studio Installer Projects.
Using the free, open-source WiX toolset - for example - you can change MSI dialogs. Github sample. SO question 1. SO question 2. And here is the official WiX toolset site.
Adding my own answer from SO: Changing text color to Wix dialogs (please do skim)
I am not familiar with how to change dialogs in Visual Studio Installer Projects. Commercial products Advanced Installer and Installshield can certainly change dialogs.
Services: What is the nature of the product you are installing? Does it has a lot of services for example? Services can be shut down and restarted via MSI tables if you use a proper tool to build the MSI.
REINSTALLMODE: Do you use a custom REINSTALLMODE for your setup? (some settings can cause more reboot prompts).
Custom Uninstaller: How do you invoke that custom uninstaller of yours? Manually or do you register an uninstall command line with Add / Remove Programs? (this latter approach is not recommended).
ARP Applet vs MSI Dialogs: The ARPNOREPAIR property is set in the MSI itself - in the property table. It affects only what is seen in Windows' Add / Remove Programs applet (ARP = Add / Remove Programs), and not what you see when your MSI is invoked via command line. Then you see the dialogs defined in that MSI itself (which can be changed - not entirely trivial to do).
ARP / Add Remove Programs Applet: A quick review of this applet below:
Hold Windows Key and Tap R. Type: appwiz.cpl and press Enter. This opens the Add /Remove Programs Applet.
Select the different package entries in the list to see different settings for ARPNOREPAIR, ARPNOMODIFY, etc...
If ARPNOREPAIR is set in the MSI's property table then the Repair entry is missing.
If ARPNOMODIFY is set in the MSI's property table then the Change entry is missing.
If ARPNOREMOVE is set in the MSI's property table then the Remove entry is missing.
If the special ARPSYSTEMCOMPONENT property is set, then the MSI will be missing from ARP altogether.
Links:
In-use files not updated by MSI-installer (Visual Studio Installer project)
So, there is an "ugly hack" which solves the exact problem:
First - we need an executable, that isn't affected by the installer. This one is easy, we just copy that one installed exe to a TEMP directory and run it from there.
The next step is to that file must wait unit the uninstall phase is done. There are a couple of ways of doing so. You can observe the installer process, you can observe the file system if main program file is deleted. Considering the pace of common installer operations, polling once a second is a good enough option.
The next step is optional - you remove remaining files created by application, empty directories and such.
The next step is reboot itself, MessageBox.Show() from PresentationFramework is fine to ask user, when user answer OK or YES, then reboot itself can be performed in many ways, I use ExitWindowsEx() from user32.dll since it's probably what msiexec calls internally.
Here's example code:
if (MessageBox.Show(RestartPromptMsg, "", MessageBoxButton.OKCancel, MessageBoxImage.Exclamation) == MessageBoxResult.OK) {
NativeMethods.ExitWindowsEx(
NativeMethods.Flags.Reboot,
NativeMethods.Reason.MajorApplication | NativeMethods.Reason.MinorInstallation | NativeMethods.Reason.FlagPlanned
);
}
Of course some parameters could be passed to our special clean up executable, so it could do some extra things, like skip the restart prompt if it's not really required.
The last step is to delete our executable itself. It's easy, but it's tricky. Again I hope my example code would help:
var cleanUpTempPath = Path.Combine(Path.GetTempPath(), CleanUpExe);
File.Copy(CleanUpPath, cleanUpTempPath, overwrite: true);
Process.Start(new ProcessStartInfo {
FileName = "cmd",
Arguments = $"/c (\"{cleanUpTempPath}\" -purge \"{InstallerDir}\") & (del \"{cleanUpTempPath}\")",
UseShellExecute = false,
CreateNoWindow = true
});
We use cmd.exe special feature, the power of & and (). Commands separated with & gets executed when previous command exits. So when our clen up exe completes, it's gets deleted by the same cmd instance which called it. Remember to quote all paths, they can contain spaces. Remember to enclose a command with arguments in parentheses, because otherwise the & operator would be seen as a parameter to the previous command, not the cmd.exe.
I tested it in my big production application and it works as charm. The code examples don't work when just pasted, if you're looking for complete code, just google for it, there are plenty of working examples on pinvoke.net and StackOverflow.

Run a C# class library with IIS from the command line

I have a C# solution that I am developing in Visual Studio. It has a multiple startup projects.
To run it during development, I click the Start button in Visual Studio:
Now I am working on automated testing. I want to start the current code base in an ad hoc environment, the same way I do when I'm developing. I'm assuming there is some way to do this from the command line - some way to do the same thing the Start button does, from the command line. How can I do that?
Update
Thanks to those who have responded so far. My project is a Class Library, so it is outputting DLLs in bin/Debug. It normally launches with IIS, so I'm attempting to duplicate that behavior.
What Start does is
Builds the project.
Runs it.
Attaches a debugger
I imagine you care only about 1. and 2.
To build the project, open a Command Prompt in the solution's folder and execute:
msbuild SolutionName.sln /t:ProjectName /p:Configuration=Debug
To run the project, in the same command prompt, you can execute:
cd ProjectName/bin/Debug
ProjectName.exe
Obviously, replace SolutionName and ProjectName with your project's parameters and you can replace the Debug configuration with Release.
I edited the .csproj file edited to have the following (see this SO):
<UseGlobalApplicationHostFile>True</UseGlobalApplicationHostFile>
and then I rebuilt and ran this from the command line:
"C:\Program Files (x86)\IIS Express\iisexpress.exe" /site:WebSite1
(where WebSite1 is the name of the project), and it seems to work.
See Running IIS Express from the Command Line.
Open a command line (Win+R cmd)
Change folder (cd XXXX) to your solution folder.
Change folder to Debug or Release.
In those folders should be your exe file, based on your project name.
Type in the name of the application

Installutil command cannot find windows service executable

I have created a windows service and would like to test it however when I attempt to try and install the service using the developer command prompt I get this error:
Exception occurred while initializing the installation:
System.IO.FileNotFoundException: Could not load file or assembly
'file:///C:\Program Files (x86)\Microsoft Visual Studio 14.0\BackUpService.exe'
or one of its dependencies. The system cannot find the file specified..
the command i used was: installutil BackUpService.exe
I am not quite sure why I am getting this?
It's look like you just forgot install(-i) word.
C:\Windows\Microsoft.NET\Framework64\v4.0.30319>InstallUtil.exe -i C:\BackupProject\bin\Debug\BackupService.exe
Use -u for uninstall.
There is complete process of install & uninstall Windows Service on this link:
https://stackoverflow.com/a/51788260/9888476
One way of figuring out what's missing here is by using Process Monitor. You would want to use the icons on the top right to limit the captured events to "Show File System Activity" only otherwise you'll get heaps of irrelevant information.
According to my understanding you are using InstallUtil.exe to install the windows service. In that case you have to specify full path of the windows service exe file in the command.
Like this
>InstallUtil.exe "C:\dev\DBBackupService\BackUpService.exe"
Hopefully this will work.

Automate deployment of Excel AddIn

I have created an Excel Add-in using AddIn Express .Net component. Business users install the add-in using the MSI provided by the build team. Everytime we make any changes to the product and provide it to business users, they need to manually uninstall existing Add-in and then install new one with the updated MSI.
I wanted to know if there is any way this process can be automated using some windows batch file, scriptcs or a small C# console program. Ideally, it should uninstall existing Add-in, wait for uninstallion process to complete and then install new AddIn.
I tried multiple options using Msiexec, scriptcs etc, but without any success so far. My main problem is once the existing add-in uninstallion process starts, it immediately starts installing new Addin, which then pops up standard windows message that 'Installation is already in progress...'
Any help would be appreciated.
Thanks
I answered already a similiar question where it seemed to help:
Windows batch file does not wait for commands to complete
Normally, when you have a batch file with two lines:
call msiexec /x {...} /qb
call msiexec /i "c:\myPath\myProduct.msi" /qb
it should work in the sense that the uninstall waits before install starts.
The "call" is important !
For uninstalls of previous versions you have to use /x {ProductCode to fill in} instead of /x "filename" . In each case using the product code is safer.
To be sure what happens, you can add a pause line between the two and at the end.
If it still seems not to work you have to loop until the product is really uninstalled, wait two seconds and proceed then with an install.
There are several possibilities to find out, if a program is still installed.
Most people would recommend a VB script as the easiest solution, at least these are most known.
Here is a VBS snippet from saschabeaumont for an uninstall call from another question:
MSI Install Fails because "Another version of this product is already installed"
It mainly finds out the ProductCode of a given productname (part), and starts uninstall, if it fits (be careful about partial matches). You can use it for the same thing and additionally copy the algorithm a second time to ask asynchronously, if the uninstall has already been finished (= product is no longer in list of installed products).
Of course it is possible in other script languages, namely JScript, Powershell and traditional programming languages.
It is difficult to do in pure batch scripts- for example you could test the ProductCode registry entry under HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall, if a product is installed. But only one disadvantage to mention: You have to consider the difference, if batch is started from 32/64 bit subsystem and/or MSI is 32/64 bit. Therefore I would advise instead using VBS instead of a batch (you can call it from the batch with cscript xxx.vbs).
A few things here:
First question is if you are aware of the xlstart folder in Excel which allows you to easily load certain addin files on Excel startup just by putting them into this folder. As far as I know you can't disable addins this way via the Excel GUI, you have to remove them from the xlstart folder to not load them into Excel.
Second issue is that you should update your MSI file to use a major upgrade so that it automatically removes the existing MSI whilst installing the new one. This would probably remove the whole problem that you describe.
Finally you should be able to use start wait msiexec.exe /i /qn File.msi to have your batch file wait for msiexec to return from the first msiexec call. Check Waiting for msiexec.exe to finish. Or you can try MSI Software Deployment Using Batch File.

Merge msi and exe

My deployment project creates and .msi-file and an .exe-file. Is it possible to merge these into one .exe?
Yes, you can create a self-extracting installer containing both MSI and the setup.exe bootstrapper file.
I think it is possible to do that with WinZip, or you can use IExpress coming with Windows. Here is a guide how to create a self-extracting executable with IExpress. You can either use the IExpress wizard or manually write a config file which you then can execute in the post-built step of your setup project, e.g. by calling
IExpress /N /Q MySetup.sed
A sample configuration file would look like this:
[Version]
Class=IEXPRESS
SEDVersion=3
[Options]
PackagePurpose=InstallApp
ShowInstallProgramWindow=1
HideExtractAnimation=1
UseLongFileName=1
InsideCompressed=0
CAB_FixedSize=0
CAB_ResvCodeSigning=0
RebootMode=N
InstallPrompt=%InstallPrompt%
DisplayLicense=%DisplayLicense%
FinishMessage=%FinishMessage%
TargetName=%TargetName%
FriendlyName=%FriendlyName%
AppLaunched=%AppLaunched%
PostInstallCmd=%PostInstallCmd%
AdminQuietInstCmd=%AdminQuietInstCmd%
UserQuietInstCmd=%UserQuietInstCmd%
SourceFiles=SourceFiles
[Strings]
InstallPrompt=
DisplayLicense=
FinishMessage=
TargetName=MySetup.exe
FriendlyName=My cool application
AppLaunched=CMD /C setup.exe
PostInstallCmd=
AdminQuietInstCmd=
UserQuietInstCmd=
FILE0="setup.exe"
FILE1="MySetup.msi"
[SourceFiles]
SourceFiles0=
[SourceFiles0]
%FILE0%=
%FILE1%=
There is a little caveat however with the self-extracting installer scenarios. Due to another fix these scenarios are broken with the bootstrapper (setup.exe) created by VS2008 SP1. For a workaround see the following thread: http://social.msdn.microsoft.com/Forums/en-US/winformssetup/thread/3731985c-d9cc-4403-ab7d-992a0971f686/?ffpr=0.
I like it, you can see how to use IExpress on this link!
The only problem I see was that I've generated a installer on Windows Vista 64bits, I was trying to install the generated .exe in a server with Windows Server 2008 32bits, but it throws an error about processor type.
Another option could be 7zip with sfx plugin: http://www.7-zip.org/download.html or WinZip self extractor: http://www.winzip.com/prodpagese.htm

Categories

Resources