寻找API到SC.exe实用程序,以及有关自我更新Windows服务的建议

我们构建了一个在客户端计算机上运行的Windows服务,它偶尔会下载更新版本的自身,然后执行自我更新:安装新服务,启动它,停止旧服务,最后删除它。该服务无法直接停止并执行其他操作,因此它会旋转另一个可执行文件,从而完成一些工作。实现这一点很棘手,当使用较新的.Net Framework构建较新的服务时(例如最近从.Net 2.0切换到.net 4.0),这一点尤其糟糕。问题是.Net 2.0库无法在.Net 4.0服务上运行。 现在,一种方法是让旧版本的服务旋转一个辅助程序,该程序随新版本一起提供,但是...如果它的行为以破坏方式改变怎么办?我觉得不要混淆版本更安全,即使有些东西通常保持不变 - 有助于降低设计复杂性。 现在,似乎有一种.Net版本中立的Windows服务操作方式:
sc.exe
工具:http://support.microsoft.com/kb/251192 我想知道这是不是我正在寻找的银弹。现在,因为我将以编程方式调用此人并检查错误,所以我不妨使用API​​。理想情况下,我会有一个本机C ++项目,它编译为与SC.exe接口的本机exe。这可能吗?如果没有,那么我该如何在不同的计算机上找到sc.exe呢?它们可以是32位或64位,并运行从Win XP SP2 / 3开始的任何版本的Windows。 如果您对我的问题或一些巧妙的想法有疑问,或者对我在这里提出的确切问题的答案,请告诉我。 编辑:如果我尝试使用2.0代码安装4.0服务,我会得到与我一样的错误:
> C:WindowsMicrosoft.NETFrameworkv2.0.50727InstallUtil.exe MyService4.exe
  Microsoft(R).NET Framework   安装工具版本   2.0.50727.4927版权所有(c)Microsoft Corporation。版权所有。      初始化时发生异常   安装:   System.BadImageFormatException:可以   不加载文件或程序集   'file:/// [path] MyService4.exe'或者一个   它的依赖关系。这个组件是   由比运行时更新的运行时构建的   当前加载的运行时并不能   装..     
已邀请:
您的本机C ++应用程序可以调用此处记录的函数:http://msdn.microsoft.com/en-us/library/ms685942(v = VS.85).aspx(其他人提到的SCM API) 你会想做一些事情
OpenSCManager
OpenService (or CreateService)
ChangeServiceConfig
CloseServiceHandle
    
我不确定你的意思是:   问题是.Net 2.0库无法在.Net 4.0服务上运行。
ServiceController
类能够控制任何服务,甚至是本地服务。我没有尝试过,但我相信
ServiceInstaller
类也可以用来(un)安装任何服务。 如果
ServiceController
ServiceInstaller
不符合您的需求,我建议直接包装本机API而不是
sc.exe
。 MSDN文档应该让你开始;您将需要服务控制管理器功能。
sc.exe
程序只是SCM API的一个瘦命令行包装器。     
作为更新包的一部分,包括名称在版本之间不变的可执行文件,例如Setup.exe :-) 然后,此工具在更新逻辑作为新进程启动时执行所有设置操作。它应该使用与包的其余部分相同的Framework版本进行编译,以避免CLR版本控制问题。 我在现有的
ServiceInstaller
类中遇到的最大问题是缺乏对更新服务功能的支持,例如描述和故障/恢复操作。为了解决这个问题,我从CodeProject调整了Narendra(Neil)Baliga的代码并使用了
ServiceInstallerEx
类。他的代码包含了调用相同的Windows API所需的p调用定义。 有点相关:如果您的更新要求与我之前使用的相似,我建议安装到并排文件夹(其名称包括版本/版本号),并保留最后2或3以允许回滚。将当前版本的路径传递给设置工具,以便了解当前的播放状态。     
sc.exe实际上始终位于相同的路径:%windir% System32 sc.exe(x64使用System32 for 64位二进制文​​件:-)。不知道你当前的设置是什么样的,但是如果你有,或者可以切换到MSI - 它可以运行自定义安装操作,可以是你的新.exe,配置文件要么用于SCM API,要么只是启动sc.exe 2-3次做停止,配置,启动。从技术上讲,您甚至可以在MSI中使用.cmd作为自定义安装操作,但它可能看起来有点难看(用户看到cmd窗口即将出现)。 如果你想使用SCM API并且你知道你的C ++,那肯定是最好的方法 - 中间没有任何层来混淆。此外,一旦为安装任务提供单独的二进制文件,您就不受.NET嵌入式安装过程的约束 - 您可以从C#和C ++获得相同的NT API。关键是执行管理任务以停止,启动,配置等的二进制文件必须与服务本身的二进制文件不同 - 这就是.NET的问题 - 结果。 由于您正在进行主要切换,如果您之前的安装不在MSI下,那么新的MSI将无法自行处理所有内容,因此您可能希望直接删除.cmd文件以停止并清理使用sc.exe的旧服务,只是为了开始清理,然后启动新安装二进制文件 - 无论它是什么。 MSI将停止并取消暂停窗口服务,但前提是它以前是由MSI安装的。它有点粘:-)     

要回复问题请先登录注册