visual studio setup project windows service install error

100 Views Asked by At

In my visual studio setup project, ive added a windows service (inside applicationFolder\Service directory) which want to install during installation process. to do this, i've created an installService.bat batch file which contains the following commands :

@echo off
sc create "Houshmand Configuration Manager Service" binpath= "%~dp0Service\Houshmand.ConfigManager.Service.exe" start= delayed-auto
net start "Houshmand Configuration Manager Service"

to run this commands, i've add cmd.exe from windows directory into my setup project aplicationFolder directory and in custom action add it in commit node, then set the following command in arguments :

/k "installService.bat"

but when i build and run my setup project, facing this message during installation service and when i close the cmd windows, my setup process being rolled back!!!

DNS server not authoritative for zone. Not enough memory resources are available to process this command.

But when i execute the given batch file (installService.bat) as administrator manually, it works correctly!!!

where is the problem and how to solve it? Thanks in advance

1

There are 1 best solutions below

0
hdv212 On BEST ANSWER

After a lot of searchs, working and tests, finally, found the problem. The problem is related to path which send to batchFile. So, ,i've created an small console app to install windows service, base on the relative path which accept as arguments. here is my code : Maid method body :

string strAction = args[0];
string serviceExePath = args[1];
string serviceName = "Houshmand Configuration Manager Service";
string fullPath = Path.Combine(System.Windows.Forms.Application.StartupPath, serviceExePath);

if (strAction.ToLower() == "/i")
{
    bool bInstalledServiceSucceed = InstallService(serviceName, fullPath);
}
else if (strAction.ToLower() == "/u")
{
    bool bUninstalledServiceSucceed = UninstallService(serviceName, fullPath);
}

And static methods :

internal static bool InstallService(string serviceName, string serviceFullPath)
{
    bool bResult = false;

    try
    {
        ManagedInstallerClass.InstallHelper(new string[] { "/i", serviceFullPath });

        ProcessStartInfo psi = new ProcessStartInfo();
        psi.FileName = "sc.exe";
        psi.UseShellExecute = false;
        psi.RedirectStandardOutput = true;
        psi.RedirectStandardError = true;
        psi.Arguments = $"config \"{serviceName}\" start= delayed-auto";
        Process p = Process.Start(psi);
        p.WaitForExit();

        ServiceController sc = new ServiceController(serviceName);
        if (sc.Status != ServiceControllerStatus.Running)
        {
            sc.Start();
            sc.WaitForStatus(ServiceControllerStatus.Running);
        }

        bResult = true;
    }
    catch (Exception ex)
    {
        // logging ...
    }

    return bResult;
}

internal static bool UninstallService(string serviceName, string serviceFullPath)
{
    bool bResult = false;

    try
    {
        ServiceController sc = new ServiceController(serviceName);
        if (sc.Status == ServiceControllerStatus.Running)
        {
            sc.Stop();
            sc.WaitForStatus(ServiceControllerStatus.Stopped);
        }

        ManagedInstallerClass.InstallHelper(new string[] { "/u", serviceFullPath });
        bResult = true;
    }
    catch (Exception ex)
    {
        // logging...
    }

    return bResult;
}

Then add it to my setup project (as project outPut). Then call it via custom action > commit section and send relative path of my service as arguments. Don't remember, make sure the property InstallerClass for given custom action to False!

Best regards...