.net知识和学习方法系列(二十五) .net中的windows service与服务操作

简介:


昨天一个朋友想用做个短信网关,与移动TCP/IP通迅来完成短信的发送。并且想是用一个Windows服务来完成这个工作,但是又想让管理员能在客户端(浏览器端)对服务进行装载,卸载,启动,停止。我初步听了以后,觉得这个需求是可以完成的,服务这个项目的建立没有问题,控制服务这个项目也是没有问题的。于是就研究了一下,并去网上搜集了一些资料,整理了一个从技术角度相对完整的文档,拿出来给大家分享一下。

为了简化业务,这里就把与短信网关通信的需求改成每间隔一秒钟向一个txt 文档写一个当前时间的需求。
我们先来看服务部分:
打开VS2008 ,“文件 →新建→项目 ”,选择“Windows ”项中的“Windows 服务”,根据自己的情况修跑径和名称,这里的名称修为“WriteTextService ”,确定后,出现一个“若要在类中添加组件,请从 工具箱 中拖出它们,然后例用属性窗口来设置它们的属性。若要为类创建方法和事件,请 单击此处切换到代码视图 。”的一个界面,我们如果处理业务逻辑,单击“单击此处切换到代码视图”,来转换到代码页。
代码
WriteTextService.cs
 
1using System; 
2using System.ServiceProcess; 
3using System.IO; 
4using System.Threading; 

6namespace WriteTextServiceNS 
7{ 
8         public partial class WriteTextService : ServiceBase 
9        { 
10                 public WriteTextService() 
11                { 
12                        InitializeComponent(); 
13                } 
14                protected override void OnStart(string[] args) 
15                { 
16                        Thread t = new Thread(new ThreadStart(DY)); 
17                        t.Start();                                            
18                } 
19                private void DY() 
20                { 
21                         while (true) 
22                        { 
23                                 File.WriteAllText(@"F:/gsw.txt", DateTime.Now.ToString()); 
24                                Thread.Sleep(2000); 
25                        } 
26                } 
27                protected override void OnStop() 
28                { 
29                } 
30        } 
31} 
32
现在,我们还需要在服务中创建一个服务安装类,来完成服务初始化安装工作。
我们创建一个类ServiceInstall
ServiceInstall.cs
 
1using System.Collections; 
2using System.Configuration.Install; 
3using System.ServiceProcess; 
4using System.ComponentModel; 
5using Microsoft.Win32; 

7namespace WriteTextServiceNS 
8{    
9        [RunInstaller(true)] 
10         public class ServiceInstall : Installer 
11        { 
12                private ServiceInstaller WTSerInst;    //它由安装实用工具用来将与服务关联的注册表值写入 HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services 注册表项内的子项。 
13                private ServiceProcessInstaller    WTProInst;    //安装实用工具使用它来写与要安装服务关联的注册表值。 
14                 public ServiceInstall() 
15                { 
16                        WTProInst = new ServiceProcessInstaller(); 
17                        WTProInst.Account = ServiceAccount.LocalSystem;    //安装服务时使用的账户 
18                     
19                        WTSerInst = new ServiceInstaller();                         
20                        WTSerInst.StartType = ServiceStartMode.Automatic ; //启动服务的后模式(Automatic 自动,Manual 手动,Disabled 禁用)    
21                        WTSerInst.ServiceName = "WriteTextService";     //要安装服务的名称 与服务类名相同 
22                        
23                        Installers. Add(WTSerInst);    //把服务安装类放入安装集合中 
24                        Installers. Add(WTProInst); 
25                } 
26                /**//// <summary> 
27                /// 重写父类的安装,并在安装服务后写入服务的描述 
28                /// </summary> 
29                /// <param  name="stateSaver"></param> 
30                 public override void Install(IDictionary stateSaver) 
31                { 
32                        RegistryKey system,service,config; 
33                        try 
34                        { 
35                                base.Install(stateSaver); 
36                                system = Registry.LocalMachine.OpenSubKey("System").OpenSubKey("CurrentControlSet").OpenSubKey("Services"); 
37                                service = system.OpenSubKey(this.WTSerInst.ServiceName, true); 
38                                service.SetValue("Description", "……这是一个每秒写入 Text一次时间的服务……");                            
39                                config = service.CreateSubKey("AdditionalInformation"); 
40                        } 
41                        catch 
42                        { } 
43                } 
44                /**//// <summary> 
45                /// 重写父类的卸载,并在卸载服务后删除描述 
46                /// </summary> 
47                /// <param  name="stateServer"></param> 
48                 public override void Uninstall(IDictionary stateServer) 
49                { 
50                        RegistryKey system,currentControlSet,services,service; 
51                        try 
52                        { 
53                                system = Microsoft.Win32.Registry.LocalMachine.OpenSubKey("System"); 
54                                currentControlSet = system.OpenSubKey("CurrentControlSet"); 
55                                services = currentControlSet.OpenSubKey("Services"); 
56                                service = services.OpenSubKey(this.WTSerInst.ServiceName, true); 
57                                service.DeleteSubKeyTree("AdditionalInformation"); 
58                        } 
59                        catch    
60                        {} 
61                        finally 
62                        { 
63                                base.Uninstall(stateServer); 
64                        } 
65                } 
66        } 
67} 
68
这样就完成了一个服务,关且有服务的描述,最要是通过重写父类 Install 和Uninstall 来完成对服务描述的添加。因为服务都是在HKEY_LOCAL_MACHINE/SYSTEM/CurrentControlSet/Services/WriteTextService 下有个项Description ,给这个项添加数据就对应该服务的描述,所以 Install 和Uninstall 两个方法本质上就是注册表英的添加与删除。
 
接下来我们看一下服务的操作,即装载,卸载,启动,停止。
我们新建一个web 网站,只有一个Default.aspx 页面,代码如下:
Default.aspx
 
1<%@ Page Language="C#" AutoEventWireup="true"    CodeFile=" Default.aspx.cs" Inherits="_Default" %> 

3<!DOCTYPE html  PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 

5<html xmlns="http://www.w3.org/1999/xhtml"> 
6<head runat="server"> 
7        <title>无标题页</title> 
8</head> 
9<body> 
10        <form id="form1" runat="server"> 
11        <div> 
12         
13                <asp:Button ID="Button1" runat="server"  Text="装载服务" /> 
14                <asp:Button ID="Button2" runat="server"  Text="卸载服务" /> 
15                <asp:Button ID="Button3" runat="server"  Text="启动服务" /> 
16                <asp:Button ID="Button4" runat="server"  Text="停止服务" /> 
17         
18        </div> 
19        </form> 
20</body> 
21</html> 
22
 
Default.aspx.cs
 
1using System; 
2using System.Configuration; 
3using System.Web; 
4using System.Web.Security; 
5using System.Web.UI; 
6using System.Web.UI.HtmlControls; 
7using System.Web.UI.WebControls; 
8using System.Web.UI.WebControls.WebParts; 
9using System.Xml.Linq; 
10using System.Configuration.Install; 
11using System.Collections; 
12using System.ServiceProcess; 
13 
14 
15public partial class _Default : System.Web.UI.Page    
16{ 
17        protected void Page_Load(object sender, EventArgs e) 
18        { 
19 
20        } 
21        protected void Button1_Click(object sender, EventArgs e) 
22        { 
23                AssemblyInstaller myassemblyinstaller = new AssemblyInstaller();//加载一个程序集,并运行其中的所有安装程序。 
24                myassemblyinstaller.UseNewContext = true; 
25                myassemblyinstaller.Path = @"f:/gsw.exe";//服务所在的路径 
26                Hashtable mysavedstate = new Hashtable(); 
27                myassemblyinstaller.Install(mysavedstate); 
28                myassemblyinstaller. Commit(mysavedstate); 
29                myassemblyinstaller.Dispose(); 
30                Response.Write("安装服务成功"); 
31         
32        } 
33        protected void Button2_Click(object sender, EventArgs e) 
34        { 
35                AssemblyInstaller myassemblyinstaller = new AssemblyInstaller(); 
36                myassemblyinstaller.UseNewContext = true; 
37                myassemblyinstaller.Path = @"f:/gsw.exe";//服务所在的路径 
38                myassemblyinstaller.CommandLine = new string[1] { "/u" };// 利用/u命令来完成卸载 
39                myassemblyinstaller.Uninstall( null); 
40                myassemblyinstaller.Dispose(); 
41                Response.Write("卸载服务成功"); 
42        } 
43        protected void Button3_Click(object sender, EventArgs e) 
44        { 
45                ServiceController sc = new ServiceController();//表示 Windows 服务并允许连接到正在运行或者已停止的服务、对其进行操作或获取有关它的信息。 
46                sc.DisplayName = "桂素伟"; 
47                sc.ServiceName = "WriteTextService"; 
48                sc.Start();//启动这个名称的服务 
49                System.Threading.Thread.Sleep(1000); 
50                sc.Refresh();//刷新服务的状态 
51                 if (sc.Status == ServiceControllerStatus.Running)//判断服务是已经运行 
52                { 
53                    Response .Write ("服务成功启动!"); 
54                } 
55        } 
56        protected void Button4_Click(object sender, EventArgs e) 
57        { 
58                ServiceController sc = new ServiceController(); 
59                sc.ServiceName = "WriteTextService"; 
60                sc.Stop(); 
61                
62                System.Threading.Thread.Sleep(1000); 
63                sc.Refresh();//刷新服务的状态 
64                 if (sc.Status == ServiceControllerStatus.Stopped)//判断服务是已经运行 
65                { 
66                     Response .Write ("服务成功停止!"); 
67                } 
68        } 
69} 
70
 
我们是通过 AssemblyInstaller 类来完成对服务的装载和卸载,通过 ServiceController 类来完成对服务的启动和停止。
这样,我们就把服务和控制服务的代友做完整了。
(我的代码是在vista和vs2008下实现的。)





















本文转自桂素伟51CTO博客,原文链接: http://blog.51cto.com/axzxs/149945 ,如需转载请自行联系原作者



相关文章
|
1月前
|
监控 搜索推荐 开发工具
2025年1月9日更新Windows操作系统个人使用-禁用掉一下一些不必要的服务-关闭占用资源的进程-禁用服务提升系统运行速度-让电脑不再卡顿-优雅草央千澈-长期更新
2025年1月9日更新Windows操作系统个人使用-禁用掉一下一些不必要的服务-关闭占用资源的进程-禁用服务提升系统运行速度-让电脑不再卡顿-优雅草央千澈-长期更新
137 2
2025年1月9日更新Windows操作系统个人使用-禁用掉一下一些不必要的服务-关闭占用资源的进程-禁用服务提升系统运行速度-让电脑不再卡顿-优雅草央千澈-长期更新
|
2月前
|
区块链 C# Windows
PasteEx:一款.NET开源的Windows快捷粘贴神器
PasteEx:一款.NET开源的Windows快捷粘贴神器
57 17
|
2月前
|
Web App开发 C# Windows
一款.NET开源的Windows资源管理器标签页工具
一款.NET开源的Windows资源管理器标签页工具
|
2月前
|
弹性计算 开发框架 安全
基于云效 Windows 构建环境和 Nuget 制品仓库进行 .Net 应用开发
本文将基于云效 Flow 流水线 Windows 构建环境和云效 Packages Nuget 制品仓库手把手教你如何开发并部署一个 .NET 应用,从环境搭建到实战应用发布的详细教程,帮助你掌握 .NET 开发的核心技能。
|
3月前
|
数据库连接 数据库 C#
Windows下C# 通过ADO.NET方式连接南大通用GBase 8s数据库(上)
Windows下C# 通过ADO.NET方式连接南大通用GBase 8s数据库(上)
|
3月前
|
数据库连接 数据库 C#
Windows下C# 通过ADO.NET方式连接南大通用GBase 8s数据库(下)
本文接续前文,深入讲解了在Windows环境下使用C#和ADO.NET操作南大通用GBase 8s数据库的方法。通过Visual Studio 2022创建项目,添加GBase 8s的DLL引用,并提供了详细的C#代码示例,涵盖数据库连接、表的创建与修改、数据的增删查改等操作,旨在帮助开发者提高数据库管理效率。
|
3月前
|
网络安全 Windows
Windows server 2012R2系统安装远程桌面服务后无法多用户同时登录是什么原因?
【11月更文挑战第15天】本文介绍了在Windows Server 2012 R2中遇到的多用户无法同时登录远程桌面的问题及其解决方法,包括许可模式限制、组策略配置问题、远程桌面服务配置错误以及网络和防火墙问题四个方面的原因分析及对应的解决方案。
226 4
|
3月前
|
开发框架 监控 .NET
【Azure App Service】部署在App Service上的.NET应用内存消耗不能超过2GB的情况分析
x64 dotnet runtime is not installed on the app service by default. Since we had the app service running in x64, it was proxying the request to a 32 bit dotnet process which was throwing an OutOfMemoryException with requests >100MB. It worked on the IaaS servers because we had the x64 runtime install
|
4月前
|
安全 Java 网络安全
Android远程连接和登录FTPS服务代码(commons.net库)
Android远程连接和登录FTPS服务代码(commons.net库)
61 1
|
4月前
|
Windows
.NET 隐藏/自定义windows系统光标
【10月更文挑战第20天】在.NET中,可以使用`Cursor`类来控制光标。要隐藏光标,可将光标设置为`Cursors.None`。此外,还可以通过从文件或资源加载自定义光标来更改光标的样式。例如,在表单加载时设置`this.Cursor = Cursors.None`隐藏光标,或使用`Cursor.FromFile`方法加载自定义光标文件,也可以将光标文件添加到项目资源中并通过资源管理器加载。这些方法适用于整个表单或特定控件。

热门文章

最新文章