1.ActiveMQ简介
先分析这么一个场景:当我们在网站上购物时,必须经过,下订单、发票创建、付款处理、订单履行、航运等。但是,当用户下单后,立即跳转到“感谢那您的订单” 页面。不仅如此,若果没有延迟,用户还会受到一封电子邮件。如果我们使用传统方式去实现,一般是对数据库操作一通,然后调用各种接口、各种服务等待各种响应,这样一来下个订单需要很久时间才能看到结果,如果某个环节出了问题,那这个订单结果一时半会是看不到了,对于现代电子商务来说,这是不能容忍的。 那么ActiveMQ久可以很好的解决这个问题:当用户下单后,有一个对ActiveMQ的调用,用来提交订单,然后系统就可以返回结果页面,而整个订单流程不会同步调用,后台JOB可以边聊天边跑。前台订单量很大的情况下每个订单也只需要调用一次,后台一下子处理不了? 慢慢来,没人逼你,订单都在ActiveMQ中排队等待呢,他们可不会烦躁。 这个场景非常适合一种缓存队列,这种队列叫消息队列,很多产品都能实现这个功能,顺便回答下一个潜在的问题:他可比数据库操作快多了。
2.下载ActiveMQ
官方网站下载地址:http://activemq.apache.org/
3.运行ActiveMQ
解压缩apache-activemq-*-bin.zip,然后运行bin目录里的InstallService.bat安装ActiveMQ服务到window服务
启动ActiveMQ以后,可以使用浏览器登陆:http://localhost:8161, 默认用户名是:admin 密码是:admin
先分析这么一个场景:当我们在网站上购物时,必须经过,下订单、发票创建、付款处理、订单履行、航运等。但是,当用户下单后,立即跳转到“感谢那您的订单” 页面。不仅如此,若果没有延迟,用户还会受到一封电子邮件。如果我们使用传统方式去实现,一般是对数据库操作一通,然后调用各种接口、各种服务等待各种响应,这样一来下个订单需要很久时间才能看到结果,如果某个环节出了问题,那这个订单结果一时半会是看不到了,对于现代电子商务来说,这是不能容忍的。 那么ActiveMQ久可以很好的解决这个问题:当用户下单后,有一个对ActiveMQ的调用,用来提交订单,然后系统就可以返回结果页面,而整个订单流程不会同步调用,后台JOB可以边聊天边跑。前台订单量很大的情况下每个订单也只需要调用一次,后台一下子处理不了? 慢慢来,没人逼你,订单都在ActiveMQ中排队等待呢,他们可不会烦躁。 这个场景非常适合一种缓存队列,这种队列叫消息队列,很多产品都能实现这个功能,顺便回答下一个潜在的问题:他可比数据库操作快多了。
2.下载ActiveMQ
官方网站下载地址:http://activemq.apache.org/
3.运行ActiveMQ
解压缩apache-activemq-*-bin.zip,然后运行bin目录里的InstallService.bat安装ActiveMQ服务到window服务
启动ActiveMQ以后,可以使用浏览器登陆:http://localhost:8161, 默认用户名是:admin 密码是:admin
如果服务无法安装或无法启动,可以查看data目录里的log文件 ,一般是java环境没装好,或者有什么端口被其他程序占用了
4..net调用
nuget搜索activemq安装
发送和接受消息示例:
public static ConnectionFactory GetFactory()
{
//web 管理 http://localhost:8161
string uri = "tcp://localhost:61616";
ConnectionFactory factory = new ConnectionFactory(uri);
return factory;
}
public static void Send(string queue, string filter, string content)
{
ConnectionFactory factory = GetFactory();
try
{
//通过工厂建立连接
using (IConnection connection = factory.CreateConnection())
{
//通过连接创建Session会话
using (ISession session = connection.CreateSession())
{
//通过会话创建生产者,方法里面new出来的是MQ中的Queue
IMessageProducer prod = session.CreateProducer(new Apache.NMS.ActiveMQ.Commands.ActiveMQQueue(queue));
//创建一个发送的消息对象
ITextMessage message = prod.CreateTextMessage();
//给这个对象赋实际的消息
message.Text = content;
//设置消息对象的属性,这个很重要哦,是Queue的过滤条件,也是P2P消息的唯一指定属性
message.Properties.SetString("filter", filter);
//生产者把消息发送出去,几个枚举参数MsgDeliveryMode是否长链,MsgPriority消息优先级别,发送最小单位,当然还有其他重载
prod.Send(message, MsgDeliveryMode.Persistent, MsgPriority.Normal, TimeSpan.MinValue);
}
}
}
catch (Exception ex)
{
Logger.Error(ex);
}
}
public static string Receive(string queue, string filter)
{
ConnectionFactory factory = GetFactory();
string text = "";
IConnection connection = null;
ISession session = null;
try
{
//通过工厂构建连接
connection = factory.CreateConnection();
//这个是连接的客户端名称标识
connection.ClientId = Guid.NewGuid().ToString("N");
//启动连接,监听的话要主动启动连接
connection.Start();
//通过连接创建一个会话
session = connection.CreateSession(AcknowledgementMode.ClientAcknowledge);
//通过会话创建一个消费者,这里就是Queue这种会话类型的监听参数设置
IMessageConsumer consumer = session.CreateConsumer(new Apache.NMS.ActiveMQ.Commands.ActiveMQQueue(queue), "filter='" + filter + "'");
//注册监听事件
//consumer.Listener += consumer_Listener;
//consumer.Listener += new MessageListener(consumer_Listener);
//如果队列没有消息了,会一直阻塞等待
ITextMessage msg = (ITextMessage)consumer.Receive();
if (msg != null)
{
text = msg.Text;
}
//必须受到消费者确认才算成功消费
msg.Acknowledge();
}
catch (Exception ex)
{
Logger.Error(ex);
}
finally
{
if (connection != null)
{
try
{
connection.Stop();
connection.Close();
}
catch (Exception ex)
{
Logger.Error(ex);
}
}
if (session != null)
{
try
{
session.Close();
}
catch (Exception ex)
{
Logger.Error(ex);
}
}
}
return text;
}
static void consumer_Listener(IMessage message)
{
try
{
ITextMessage msg = (ITextMessage)message;
Console.WriteLine("Receive: " + msg.Text);
}
catch (System.Exception e)
{
Console.WriteLine(e.Message);
}
}