1. 程式人生 > >SignalR+MongoDB實現用戶留言即時推送

SignalR+MongoDB實現用戶留言即時推送

ava UNC ssi jquer tle 滾動 $.ajax 控制器 接收

前言:

最近寫了一個項目,要實現即時通訊功能,在網上查了一下有兩種常見的實現方式:SignalR和WebSocket,SignalR是封裝好的一個類庫,有三種傳輸模式:LongLooping(長輪詢)、WebSocket、Forever Frame(隱藏框架的長請求連接),它會根據瀏覽器的環境自動選擇合適的傳輸方式(比如說低版本的IE瀏覽器不支持WebSocket,SiganlR就會采用長輪詢的方式傳輸)。SiganlR的介紹可以在百度搜一下有很多,這篇博客簡單的介紹一下如何用SiganlR實現一個實時的消息推送功能。

一開始用戶留言是存到SqlServer中的,考慮到用戶留言價值相對較低,數據量大的特點,用MongoDB在性能上比較有優勢(不用寫Sql了,幹活好快)

實現步驟:


1.安裝SignalR

Install-Package Microsoft.AspNet.SignalR

安裝成功後會系統會新增對應的js文件

技術分享圖片

2.創建Connections文件夾,存放永久連接類和Startup.cs

創建永久連接類:

技術分享圖片

代碼:

技術分享圖片
    public class ChatConnections : PersistentConnection
    {
        protected override Task OnConnected(IRequest request, string connectionId)
        {
            
return null; } protected override Task OnReceived(IRequest request, string connectionId, string data) { return Connection.Broadcast(data); } }
View Code

創建startup類,如果項目中已經有了就不用創建了

技術分享圖片

代碼:

技術分享圖片
    public class Startup1
    {
        public void Configuration(IAppBuilder app)
        {
            app.MapSignalR
<ChatConnections>("/Connections/ChatConnections"); } }
View Code

3.用戶發送留言

SignalR推送消息給後臺->留言寫入MongoDB

1.頁面引入jquery.signalR-2.4.0.js和jquery

js:

技術分享圖片
<script src="~/layer/layer.js"></script>
<script src="~/scripts/jquery-1.10.2.min.js"></script>
<script src="~/scripts/jquery.signalR-2.4.0.js"></script>
<script type="text/javascript">
    $(function () {
        //獲取連接
        var connection = $.connection("/Connections/ChatConnections");
        //監聽消息,用戶端不用做處理
         connection.received(function (data) {
        });
     // Wire up Send button to call NewContosoChatMessage on the server.
        connection.start().done(function () {
            $("#btn1").click(function () {
                layer.msg(‘確定發起留言?‘, {
                    time: 0 //不自動關閉
                    , btn: [‘確定‘, ‘取消‘]
                    , btn1: function (index) {
                        //加載層
                        var index = layer.load(1, {
                            shade: [0.1, ‘#fff‘]
                        });
                        $.ajax({
                            type: "post",
                            url: "/User/Message/SendMessage",
                            data: $(‘#form1‘).serialize(),
                        }).success(function (message) {
                           //消息推送
                            connection.send(message);
                            layer.msg(message, { icon: 1 });
                            var index = parent.layer.getFrameIndex(window.name);//獲取當前彈出層的層級
                            window.parent.location.reload();//刷新父頁面
                            parent.layer.close(index);//關閉彈出層
                        }).fail(function (err) {
                            layer.msg(‘系統錯誤,請稍後重試‘, { icon: 2 });
                        })
                        layer.close(index)//關閉加載層
                    }, btn2: function (index) {
                        layer.close();
                    }
                });
            });
        });

    });
</script>     
View Code

控制器:

技術分享圖片
        public async Task<JsonResult> SendMessage(MessageReq req)
        {
            SessionModel session = SessionInfo.GetSession();
            var info = _mysqlRepository.GetUserInfo(session.UserCode);
            req.SendName = info.UserName;
            req.SendCode = info.UserCode;
            req.SendPhone = info.Phone;
            //寫入MongoDB
            if (! await _mongoRepository.InsertMessage(req))
            {
                return Json("留言失敗");
            }
            return Json("留言成功");
        }
        #endregion
View Code

4.管理員接收留言:

SignalR監聽用戶發送留言,刷新頁面時查詢MongoDB裏是否有未讀留言

js:

技術分享圖片
<script src="~/scripts/jquery.signalR-2.4.0.min.js"></script>
<script>
    $(function () {
        //監聽用戶發送留言
        var connection = $.connection("/Connections/ChatConnections");
        connection.received(function (data) {
            layer.closeAll();
            layer.open({
                type: 2,
                shade: [0],
                title: ‘您有新的留言‘,
                shadeClose: true,
                shade: false,
                area: [‘280px‘, ‘215px‘],
                content: [‘/Manager/Home/Ifarme‘, ‘no‘], //iframe的url,no代表不顯示滾動條
                offset: ‘rb‘ //右下角彈出
            });
        });

        connection.start().done(function () {
        });
        //刷新頁面查詢是否有未讀留言
        $.ajax({
            type: "post",
            url: "/Manager/Home/QueryExist"
        }).success(function (message) {
            if (message == "Yes") {
                layer.open({
                    type: 2,
                    shade: [0],
                    title: ‘您有新的留言‘,
                    shadeClose: true,
                    shade: false,
                    area: [‘280px‘, ‘215px‘],
                    content: [‘/Manager/Home/Ifarme‘, ‘no‘], //iframe的url,no代表不顯示滾動條
                    offset: ‘rb‘ //右下角彈出
                });
            }
        }).fail(function (err) {
            layer.msg(‘未能讀取未讀留言‘, { icon: 2 });
        })
    });
</script>
View Code

控制器:

技術分享圖片
        /// <summary>
        /// 查詢是否有未讀留言
        /// </summary>
        /// <returns></returns>
        public async Task<JsonResult> QueryExist()
        {
            var result = await _msg.QueryExist();
            if (!result)
            {
                return Json("No");
            }
            return Json("Yes");
        }
View Code

點擊留言標為已讀:

技術分享圖片
        /// <summary>
        /// 標為已讀
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public async Task<JsonResult> AlRead(string id)
        {
            if (! await _mongoRepository.AlRead(id))
            {
                return Json("操作失敗", JsonRequestBehavior.AllowGet);
            }
            return Json("成功", JsonRequestBehavior.AllowGet);
        }
View Code

到這裏用戶->管理員的實時消息推送就實現了

效果圖:

技術分享圖片

寫在最後:博主本人也是最近剛學SignalR,說的有不對的地方,請各位大佬指點,相互學習,在此我也會深入的學習SignalR,後續會繼續分享SignalR的學習記錄

SignalR+MongoDB實現用戶留言即時推送