安装可以由非管理员用户启动的 Windows 服务
Posted
技术标签:
【中文标题】安装可以由非管理员用户启动的 Windows 服务【英文标题】:Installing a windows service that can be started by a non-admin user 【发布时间】:2013-06-17 09:11:03 【问题描述】:我使用 Visual Studio 2012 开发了一个包含 Windows 服务的解决方案。VS 2012 删除了创建安装程序的功能,因此我使用了一个用于安装程序生成的第三方工具 (WiX),它可以很好地集成到 Visual工作室。
我的问题是,虽然 WiX 能够安装具有自动启动/停止类型的服务,但它无法安装在启动时启动的服务。
我已经阅读了许多关于为非管理员用户启动和停止服务的文章,但是对于使用带有“net start myservice”的批处理脚本是否真的适用于非管理员用户似乎有些困惑。我不愿意尝试提升指定用户对指定服务的权限,因为它需要为安装应用程序套件的任何用户工作。同样,我也不愿意搞乱组策略,因为:
a) 项目需要由简单的安装程序安装,用户无需摆弄类似的东西 b) 目标机器上的任何用户都需要能够启动服务
所以我的问题是:
-
是否有一种不错的、简单的、保证为非管理员用户工作的方式来启动服务?
是否有其他方法可以为 Windows 服务创建安装程序,该安装程序能够在启动时启动该服务?
是否有可以作为安装程序的一部分运行的批处理脚本或其他构建后操作,以使服务在启动时启动?
对于如何解决此问题的任何其他建议,我们将不胜感激。
【问题讨论】:
我想你在这里很困惑。如果服务配置为自动启动,这意味着服务会在 Windows 启动后立即启动。 “启动时启动”选项仅适用于内核服务,也就是众所周知的设备驱动程序。但是,如果您真的想从您的应用程序中手动启动服务,这个问题已经被问及并得到了回答(见下文)。 Start Windows Service From Application without Admin right(c++) 的可能重复项 【参考方案1】:事实证明,用户错误是有问题的:我的服务依赖于另一个服务(MSMQ aka Microsoft Message Queuing),它在 MSMQ 之前尝试启动但未能启动。这里的问题是双重的:
-
访问消息队列的尝试导致未处理的异常,该异常记录在应用程序日志中,但未记录在我的服务特定日志中(因为它未处理)
我在安装服务时没有包含对 MSMQ 的引用。
我解决了问题
-
确保对消息队列的引用被 try catch 包围,该 try catch 将错误记录到我的应用程序日志中
我没有像启动任何其他程序那样启动我的服务,而是将我的大部分初始化代码移到另一个函数中,如果成功则返回一个布尔值。如果不成功,我会等待 x 秒,然后重试最多 y 次重试,其中 x 和 y 是可配置的
在我的 wix 安装程序文件中添加服务引用。
WiX 参考如下所示:
<ServiceInstall Id="ServiceNameId" Type="ownProcess"
Name="ServiceName" DisplayName="Service Display Name"
Description="Service Description" Start="auto"
Account="LOCALSYSTEM" ErrorControl="normal">
<ServiceDependency Id="MSMQ" />
</ServiceInstall>
【讨论】:
以上是关于安装可以由非管理员用户启动的 Windows 服务的主要内容,如果未能解决你的问题,请参考以下文章
windows安装RabbitMQ因为用户名为中文文件夹导致RabbitMQ服务启动失败解决办法
是否可以在没有管理员权限的情况下安装、启动和停止 Windows 服务?
windows服务中添加n g i n x 服务开机为啥没自动启动