我正在尝试制作通知系统。为了证明这一点,用户1向用户2发送了好友请求。我正在使用express.js,angularjs和socket.io。单击按钮后,User1发送请求。在User2的末尾,有一个套接字on(),正在侦听好友请求事件。但是当我广播时,其他用户无法接收任何消息。

app.js(节点服务器文件)

var express = require('express'),
    app = express();

var port = process.env.PORT || 3000;

var io = require('socket.io').listen(app.listen(port));

require('./config')(app,io);
require('./routes')(app,io);


config.js

// This file handles the configuration of the app.
// It is required by app.js

var express = require('express');

module.exports = function(app, io){

    // Set .html as the default template extension
    app.set('view engine', 'html');

    // Initialize the ejs template engine
    app.engine('html', require('ejs').renderFile);

    // Tell express where it can find the templates
    app.set('views', __dirname + '/views');

    // Make the files in the public folder available to the world
    app.use(express.static(__dirname + '/public'));

};


routes.js(从此文件发送好友请求)

var gravatar = require('gravatar');
var mysql = require('mysql');
// This is needed if the app is run on heroku:
var connection = mysql.createConnection({
    host : "localhost",
    user : "root",
    password : "",
    database : "two_way_demo"
});

connection.connect(function(error){
    if(error)
    {
        console.log("Problem with MySQL"+error);
    }
    else {
        console.log("Connected with Database");
    }
});

module.exports = function(app,io){
    app.get('/',function(req,res){
        res.render('index');
    });

    app.get('/create', function(req,res){

        // Generate unique id for the room
        var id = Math.round((Math.random() * 1000000));

        // Redirect to the random room
        res.redirect('/chat/'+id);
    });

    app.get('/home/:id', function(req,res){

        // Render the chant.html view
        res.render('home');
    });

    // Initialize a new socket.io application, named 'chat'
    var chat = io.on('connection', function (socket) {
        socket.on('get-user-id',function(data){

            connection.query("SELECT * from user_info WHERE email='"+data.userEmail+"'",function(err,rows){
                if(err)
                {
                    console.log("Problem with MySQL"+err);
                }
                else
                {
                    //console.log(rows);
                    JSON.stringify(rows);
                    socket.emit('user-id',rows);
                }
            });
        });
        socket.on('send-request',function(data){
            console.log(data);
*********************************************************************
             // Tried the emit here but its not working
                //io.emit('friend request', {
                //    receiverid: data.receiverid
                //});
*********************************************************************
        });

    });
}


angular-code.js(角度代码文件)

$(function () {
    var app = angular.module("notificationApp", []);

    app.controller("chatCTRL", ["$scope", "$http", "$interval", function ($scope, $http, $interval) {
        // connect to the socket

        //var socket = io();
        //socket.on('connect', function () {
        //    io.on('friend request', function (data) {
        //        alert("here")
        //    });
        //});

        $scope.senderId = Number(window.location.pathname.match(/(\d+)$/)[1]);

        $scope.sendrequest = function (senderid, receiverid) {

            var socket = io();
            socket.on('connect', function () {
                socket.emit('send-request', {
                    senderid: senderid,
                    receiverid : receiverid
                });
            });
        }
    }]);

    app.controller("loginCTRL", ["$scope", "$http", "$interval", "$window", function ($scope, $http, $interval, $window) {
        $scope.sendLogin = function () {
            var socket = io();
            socket.on('connect', function () {
                socket.emit('get-user-id', {
                    userEmail: $scope.hisEmail
                });
            });
            socket.on('connect', function () {
                socket.on('user-id', function (data) {
                    $scope.UserId = data[0].user_id;
                    $window.location = "http://localhost:3000/home/" + $scope.UserId;
                });
            });
        }
    }]);
}());


home.html

<!DOCTYPE html>
<html ng-app="notificationApp">
<head lang="en">
    <meta charset="UTF-8">
    <title></title>
</head>
<body ng-controller="chatCTRL">
<h1>welcome</h1>
    <div id="createbutton">
        <div id="little"><button ng-click="sendrequest(senderId,6)">Send Friend Request to User#6</button></div>
    </div>

<script src="http://cdnjs.cloudflare.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script>
<script src="/socket.io/socket.io.js"></script>
<script src="../angular/angular.js"></script>
<script src="../angular/common_angular.js"></script>

</body>
</html>

最佳答案

一些客户端架构的事情:


在大多数情况下,在有角度的客户端上,最好将套接字连接移到服务中。并在服务初始化时建立连接(服务为单例,因此启动时将只有一个连接),然后将此服务注入控制器中。
使用以下方法创建一些父抽象控制器可能会很方便
所有套接字侦听器,因此,无论角度控制器是否处于活动状态,所有侦听器都在监视。当父控制器从套接字获取数据时,它可以将其广播到子控制器


在您的注释代码中,您具有:

    //var socket = io();
    //socket.on('connect', function () {
    //    io.on('friend request', function (data) {
    //        alert("here")
    //    });
    //});


更改为此(如果您在使用中建立连接,则应省略连接部分):

    var socket = io();
    socket.on('connect', function () {
      socket.on('friend request', function (data) {
        alert("here")
      });
    });


后端:

在您的注释代码中,您具有:

//io.emit('friend request', {
//    receiverid: data.receiverid
//});


您应该使用socket中的var chat = io.on('connection', function (socket) {...而不是io.emit进行发射

创建数组变量,在其中将在连接部分之前存储所有具有用户ID的套接字:

var socketList = [];
var chat = io.on('connection', function (socket) {
  socketList.push({id:someId,socket:socket})
  ...
}


现在,在send-request中,用户应该发送其朋友的ID(我们必须知道应该通知哪个用户,我们当然可以通知所有人):

socket.on('send-request',function(data){
  socketList.forEach(function(soc){
    if(soc.id === someId){
      soc.socket.emit('friend request', {
        receiverid: data.receiverid
      })
    }
});


我也不喜欢这部分receiverid: data.receiverid,因为这意味着标记用户从接收者客户端获取接收者的ID。这可能是不安全的(用户可以更改其ID并发送其他ID)。我更喜欢在服务器端创建ID,并且当用户A向用户B发送通知时,我会从服务器变量获取用户A ID。

一段时间以来,我创建了聊天应用程序的简单原型(角度和快速),在此我提到了一些东西。如果您的应用程序仍然有问题,请去那里检查我的代码:
https://github.com/uhlryk/chat-prototype

10-02 16:43
查看更多