.net - studio - instalar servicio windows
¿Cómo hacer que un servicio Windows.NET comience justo después de la instalación? (8)
Además del servicio.StartType = ServiceStartMode.Automatic mi servicio no se inicia después de la instalación
Solución
Inserté este código en mi ProjectInstaller
protected override void OnAfterInstall(System.Collections.IDictionary savedState)
{
base.OnAfterInstall(savedState);
using (var serviceController = new ServiceController(this.serviceInstaller1.ServiceName, Environment.MachineName))
serviceController.Start();
}
Gracias a ScottTx y Francis B.
Debe agregar una acción personalizada al final de la secuencia ''ExecuteImmediate'' en el MSI, usando el nombre del componente del EXE o un lote (inicio sc) como fuente. No creo que esto se pueda hacer con Visual Studio, puede que tenga que usar una verdadera herramienta de autor MSI para eso.
He publicado un procedimiento paso a paso para crear un servicio de Windows en C # here . Parece que al menos has llegado a este punto, y ahora te preguntas cómo comenzar el servicio una vez que esté instalado. Establecer la propiedad StartType en Automático hará que el servicio se inicie automáticamente después de reiniciar su sistema, pero no comenzará (como ha descubierto) automáticamente su servicio después de la instalación.
No recuerdo dónde lo encontré originalmente (¿quizás Marc Gravell?), Pero sí encontré una solución en línea que le permite instalar e iniciar su servicio ejecutando su propio servicio. Aquí está el paso a paso:
Estructura la función
Main()
de tu servicio de esta manera:static void Main(string[] args) { if (args.Length == 0) { // Run your service normally. ServiceBase[] ServicesToRun = new ServiceBase[] {new YourService()}; ServiceBase.Run(ServicesToRun); } else if (args.Length == 1) { switch (args[0]) { case "-install": InstallService(); StartService(); break; case "-uninstall": StopService(); UninstallService(); break; default: throw new NotImplementedException(); } } }
Aquí está el código de soporte:
using System.Collections; using System.Configuration.Install; using System.ServiceProcess; private static bool IsInstalled() { using (ServiceController controller = new ServiceController("YourServiceName")) { try { ServiceControllerStatus status = controller.Status; } catch { return false; } return true; } } private static bool IsRunning() { using (ServiceController controller = new ServiceController("YourServiceName")) { if (!IsInstalled()) return false; return (controller.Status == ServiceControllerStatus.Running); } } private static AssemblyInstaller GetInstaller() { AssemblyInstaller installer = new AssemblyInstaller( typeof(YourServiceType).Assembly, null); installer.UseNewContext = true; return installer; }
Continuando con el código de apoyo ...
private static void InstallService() { if (IsInstalled()) return; try { using (AssemblyInstaller installer = GetInstaller()) { IDictionary state = new Hashtable(); try { installer.Install(state); installer.Commit(state); } catch { try { installer.Rollback(state); } catch { } throw; } } } catch { throw; } } private static void UninstallService() { if ( !IsInstalled() ) return; try { using ( AssemblyInstaller installer = GetInstaller() ) { IDictionary state = new Hashtable(); try { installer.Uninstall( state ); } catch { throw; } } } catch { throw; } } private static void StartService() { if ( !IsInstalled() ) return; using (ServiceController controller = new ServiceController("YourServiceName")) { try { if ( controller.Status != ServiceControllerStatus.Running ) { controller.Start(); controller.WaitForStatus( ServiceControllerStatus.Running, TimeSpan.FromSeconds( 10 ) ); } } catch { throw; } } } private static void StopService() { if ( !IsInstalled() ) return; using ( ServiceController controller = new ServiceController("YourServiceName")) { try { if ( controller.Status != ServiceControllerStatus.Stopped ) { controller.Stop(); controller.WaitForStatus( ServiceControllerStatus.Stopped, TimeSpan.FromSeconds( 10 ) ); } } catch { throw; } } }
En este punto, después de instalar su servicio en la máquina de destino, simplemente ejecute su servicio desde la línea de comando (como cualquier aplicación común) con el argumento de instalación de línea de comando para instalar e iniciar su servicio.
Creo que lo he cubierto todo, pero si ve que esto no funciona, hágamelo saber para poder actualizar la respuesta.
La solución más fácil se encuentra aquí install-windows-service-without-installutil-exe por @ Hoàng Long
@echo OFF
echo Stopping old service version...
net stop "[YOUR SERVICE NAME]"
echo Uninstalling old service version...
sc delete "[YOUR SERVICE NAME]"
echo Installing service...
rem DO NOT remove the space after "binpath="!
sc create "[YOUR SERVICE NAME]" binpath= "[PATH_TO_YOUR_SERVICE_EXE]" start= auto
echo Starting server complete
pause
Para agregar a la respuesta de ScottTx, aquí está el código real para comenzar el servicio si lo está haciendo de la manera de Microsoft (es decir, usando un proyecto de instalación, etc.)
(perdonen el código de VB.net, pero esto es a lo que me tengo que atener)
Private Sub ServiceInstaller1_AfterInstall(ByVal sender As System.Object, ByVal e As System.Configuration.Install.InstallEventArgs) Handles ServiceInstaller1.AfterInstall
Dim sc As New ServiceController()
sc.ServiceName = ServiceInstaller1.ServiceName
If sc.Status = ServiceControllerStatus.Stopped Then
Try
'' Start the service, and wait until its status is "Running".
sc.Start()
sc.WaitForStatus(ServiceControllerStatus.Running)
'' TODO: log status of service here: sc.Status
Catch ex As Exception
'' TODO: log an error here: "Could not start service: ex.Message"
Throw
End Try
End If
End Sub
Para crear el controlador de eventos anterior, vaya al diseñador ProjectInstaller donde están los 2 controles. Haga clic en el control ServiceInstaller1. Vaya a la ventana de propiedades debajo de eventos y allí encontrará el evento AfterInstall.
Nota: No coloque el código anterior debajo del evento AfterInstall para ServiceProcessInstaller1. No funcionará, viniendo de la experiencia. :)
Para iniciarlo justo después de la instalación, genero un archivo por lotes con installutil seguido por sc start
No es ideal, pero funciona ...
Puede hacer esto desde su ejecutable de servicio en respuesta a eventos disparados desde el proceso InstallUtil. Anule el evento OnAfterInstall para usar una clase ServiceController para iniciar el servicio.
http://msdn.microsoft.com/en-us/library/system.serviceprocess.serviceinstaller.aspx
Utilice la clase .NET ServiceController para iniciarlo o emita el comando de línea de comando para iniciarlo --- "net start servicename". De cualquier manera funciona.
Estudio visual
Si está creando un proyecto de instalación con VS, puede crear una acción personalizada que llame a un método .NET para iniciar el servicio. Sin embargo, no se recomienda utilizar acciones personalizadas administradas en una MSI. Vea esta page .
ServiceController controller = new ServiceController();
controller.MachineName = "";//The machine where the service is installed;
controller.ServiceName = "";//The name of your service installed in Windows Services;
controller.Start();
InstallShield o Wise
Si está utilizando InstallShield o Wise, estas aplicaciones ofrecen la opción de iniciar el servicio. Por ejemplo, con Wise, debe agregar una acción de control del servicio. En esta acción, especifica si desea iniciar o detener el servicio.
Wix
Usando Wix, necesitas agregar el siguiente código xml bajo el componente de tu servicio. Para obtener más información al respecto, puede consultar esta page .
<ServiceInstall
Id="ServiceInstaller"
Type="ownProcess"
Vital="yes"
Name=""
DisplayName=""
Description=""
Start="auto"
Account="LocalSystem"
ErrorControl="ignore"
Interactive="no">
<ServiceDependency Id="????"/> ///Add any dependancy to your service
</ServiceInstall>