首先,建立一个windows服务项目
然后进行设计视图
在工作区空白处右属,添加一个安装项目
然后就可以写我们的代码了,我们的服务需要实时监视MSMQ的队列中有没有记录,如果有,就向数据库中插入
核心代码如下
/// <summary>
/// 接收来自MSMQ的消息,并保存到数据库
/// </summary>
public class MessageQueueService
{
public static bool blnStopThread;
public static string exTemp = string.Empty;
public MessageQueueService()
{
//
// TODO: 在此处添加构造函数逻辑
//
}
public static void Start()
{
string queuePath = ".\\Private$\\zzl";
IsQueueExists(queuePath);
MessageQueue myQueue = new MessageQueue(queuePath);
myQueue.Formatter = new XmlMessageFormatter(new Type[] { typeof(Log) });
do
{
try
{
// Receive and format the message.
Message myMessage = myQueue.Receive(); //当消息队列空时,线程会挂起
Log log = (Log)myMessage.Body;
if (log == null) return;
Save(log);//保存到数据库,此处略详细代码
}
catch (System.Exception ex)
{
//异常处理
//……
}
} while (blnStopThread == false);
}
private static void IsQueueExists(string path)
{
if (!MessageQueue.Exists(path))
{
MessageQueue.Create(path);
}
}
private static void Save(Log entity)
{
using (SqlConnection sqlconn = new SqlConnection(System.Configuration.ConfigurationManager.ConnectionStrings["conn"].ToString()))
{
using (SqlCommand sqlcomm = new SqlCommand(
"INSERT INTO [Web_Logs]([LogID],[FromURL],[ExeSQL],[FromSystem],[HttpMethod],[OccurTime],[info]) VALUES (@LogID,@FromURL,@ExeSQL,@FromSystem,@HttpMethod,@OccurTime,@Info);"
, sqlconn))
{
SqlParameter parameter = new SqlParameter("@ExceptionID", SqlDbType.VarChar, 36);
parameter.Value = Guid.NewGuid().ToString();
sqlcomm.Parameters.Add(parameter);
parameter = new SqlParameter("@LogID", SqlDbType.VarChar, 36);
parameter.Value = entity.ID;
sqlcomm.Parameters.Add(parameter);
parameter = new SqlParameter("@FromURL", SqlDbType.VarChar, 200);
parameter.Value = string.Empty;
sqlcomm.Parameters.Add(parameter);
parameter = new SqlParameter("@ExeSQL", SqlDbType.VarChar, 1000);
parameter.Value = string.Empty;
sqlcomm.Parameters.Add(parameter);
parameter = new SqlParameter("@FromSystem", SqlDbType.Int);
parameter.Value = 1;
sqlcomm.Parameters.Add(parameter);
parameter = new SqlParameter("@HttpMethod", SqlDbType.VarChar, 50);
parameter.Value = string.Empty;
sqlcomm.Parameters.Add(parameter);
parameter = new SqlParameter("@Info", SqlDbType.VarChar, 50);
parameter.Value = entity.Info;
sqlcomm.Parameters.Add(parameter);
parameter = new SqlParameter("@OccurTime", SqlDbType.DateTime);
parameter.Value = entity.OccerTime;
sqlcomm.Parameters.Add(parameter);
sqlconn.Open();
sqlcomm.ExecuteNonQuery();
sqlconn.Close();
}
}
}
public class Log
{
public string ID { get; set; }
public string Info { get; set; }
public DateTime OccerTime { get; set; }
public void PrintAll()
{
Console.WriteLine("{0} {1} {2}", ID, Info, OccerTime);
}
}
为了使服务实时对MSMQ进行监控,需要我们在服务中使用一个定时事件,代码如下:
当然在程序初始化时,需要为一个System.Timers.Timer类型进行相应的初始化工作
this.timer1 = new System.Timers.Timer();
this.timer1.Start();
this.timer1.Interval = 1000;
this.timer1.Elapsed += new System.Timers.ElapsedEventHandler(this.timer1_Elapsed);
这个WINDOWS服务我们已经添加完成,现在需要做的就是MSMQ部分了,事实上windows服务这块主要是从MSMQ中得到消息,而在MSMQ这块主要是向MSMQ去写入消息,微软的MSMQ完全支持复杂类型,也就是说你可以将一个类对象写到MSMQ中
/// <summary>
/// 日志实体
/// 可以被序列化
/// </summary>
[Serializable()]
public sealed class Log
{
public string ID { get; set; }
public string Info { get; set; }
public DateTime OccerTime { get; set; }
}
/// <summary>
/// MSMQ消息功能密封类
/// 向消息队列中写入日志信息
/// </summary>
public sealed class MSMQLog
{
private static object sync = new object();
private static object syncWrite = new object();
static volatile MessageQueue writer = null;
private static MessageQueue MSQWriter
{
get
{
if (writer == null)
{
lock (sync)
{
if (writer == null)
{
string queuePath = ".\\Private$\\zzl";
IsQueueExists(queuePath);
writer = new MessageQueue(queuePath);
}
}
}
return writer;
}
}
private static void IsQueueExists(string path)
{
if (!MessageQueue.Exists(path))
{
MessageQueue.Create(path);
}
}
public static void Write(Log log)
{
lock (syncWrite)
{
MSQWriter.Send(log);
}
}
}
当需要调用它时,可以这样:
安装与卸载windows服务的方法:
installutil工具在目录:系统盘:\WINDOWS\Microsoft.NET\Framework\v4.0.30319下,运行cmd,输入
C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\installutil xxxx.exe 回车,即可完成windows服务的安装。
卸载则为输入 C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\installutil /u xxxx.exe 回车。
本例经过自己实验,已经成功,当若干客户端同时进行某种操作时,可以同时写入数据库中,这就是我要说的,进行window服务和MSMQ技术实现高并发的解决方案