在Windows窗体应用程序中安装服务

3

我有一个按钮,允许用户浏览文件,然后将路径+文件名存储在变量中:

openFileDialog1.ShowDialog();
string filePath = openFileDialog1.FileName;

在浏览 .exe 文件后,我想安装服务。

目前我们使用 installutil 作为管理员运行 bat 文件来进行安装。也可以通过管理员命令提示符使用 sc create 进行安装。

从 Windows 窗体安装服务的最简单方法是什么?

我能否创建像这样的字符串:

sc create "servicename" binpath="filepath"

并从程序中运行它?

我考虑的另一个选项是让程序创建一个批处理文件,并以管理员身份运行它?


2
请查看Process.Start() - itsme86
2个回答

3
您可以使用以下代码来安装一个服务:

注意:您需要添加对 System.ServiceProcess 的引用。

public static void InstallService(string serviceName, Assembly assembly)
{
    if (IsServiceInstalled(serviceName))
    {
        return;
    }

    using (AssemblyInstaller installer = GetInstaller(assembly))
    {
        IDictionary state = new Hashtable();
        try
        {
            installer.Install(state);
            installer.Commit(state);
        }
        catch
        {
            try
            {
                installer.Rollback(state);
            }
            catch { }
            throw;
        }
    }
}

public static bool IsServiceInstalled(string serviceName)
{
    using (ServiceController controller = new ServiceController(serviceName))
    {
        try
        {
            ServiceControllerStatus status = controller.Status;
        }
        catch
        {
            return false;
        }

        return true;
    }
}

private static AssemblyInstaller GetInstaller(Assembly assembly)
{
    AssemblyInstaller installer = new AssemblyInstaller(assembly, null);
    installer.UseNewContext = true;

    return installer;
}

您只需要这样调用它:

Assembly assembly = Assembly.LoadFrom(filePath);
InstallService("name", assembly);

我已经让它工作了。出现了以下错误。“在 Configs.exe 中发生了未处理的类型为 'System.InvalidOperationException' 的异常”。 - TiraULTI
@TiraULTI 应用程序是否以管理员身份运行? - TheLethalCoder
通过以管理员身份运行,您是指以管理员身份打开它吗?如果是的话,那是的。 - TiraULTI
我假设你正在尝试安装的应用程序中实现了ServiceBaseInstaller?也就是说,它是一个服务。 - TheLethalCoder
我正在尝试安装的应用程序是一个Windows服务。它不是由我编写的,而是由我们团队的另一部分制作的。 - TiraULTI
@TiraULTI,你试过另一个答案了吗?虽然我已经用它来安装当前的应用程序,但上面的代码并没有完全测试。也就是说,它只能安装自身,而不能安装其他应用程序。 - TheLethalCoder

0

你可以使用Process.Start

System.Diagnostics.Process process = new System.Diagnostics.Process();
System.Diagnostics.ProcessStartInfo startInfo = new System.Diagnostics.ProcessStartInfo();
startInfo.FileName = "cmd.exe";
startInfo.Arguments = String.Format(@"sc create \"servicename\" \"{0}\"", filepath);
startInfo.Verb = "runas";
process.StartInfo = startInfo;
process.Start();

startInfo.Verb = "runas"; 这行代码可以让进程以管理员权限启动。


你确定这部分代码没问题吗?String.Format(@"sc create "servicename" "{0}"", filepath);我不明白在哪里放置名称。 - TiraULTI
@TiraULTI 好的,那就是你传递给安装服务的命令,所以你可以使用任何你想要的,例如在问题中你说 sc create "servicename" binpath="filepath" 所以你可以将其作为 startInfo.Arguments 传递,当然要正确设置 servicename 和 filepath。 - TheLethalCoder
startInfo.Arguments = String.Format(@"sc create 'name12' binpath='"+filePath+"'");现在正在编译,当我搜索exe并选择它时,唯一的事情就是打开cmd。 - TiraULTI

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接