当我的PHP脚本启动时,用户尝试建立与WebSocket的连接。一旦与Websocket建立了第一个连接,我就会创建以下会话变量session.authorized。然后我更新一个名为clients
的对象。 clients
对象和每个键代表一个会话,每个值都是来自相同会话ID的每个连接的对象,#34;
object clients (
session_id1 = object ('conn1','conn2','conn2'),
session_id2 = object ('conn1','conn2')
)
用户刷新我的PHP应用程序后,脚本将尝试再次连接到Websocket。此时,我想使用已为该用户存储的会话数据,因为用户已经过验证。
对于我的Websocket实现,我在node.js上使用socket.io。我正在使用express
框架和express-session
。
问题
当我尝试在我的Websocket服务器中读取会话变量时,它似乎没有保存,因为我无法在第二个请求中检索会话数据。
我的代码存在的问题是,在disconnect事件中,值session_id
始终未定义。此外,当用户再次连接时,会话变量不存在"我无法在页面刷新时重新使用它#34;
我认为我没有创建会话或正确使用它。
问题
如何在用户通过身份验证后保存会话? 我怎么知道用户已被授权?
这是我的代码
const env = require('./config');
const sess = require('./sessions');
const app = require('express')();
const https = require('https');
const fs = require('fs');
const server = https.createServer(
{
key: fs.readFileSync('certs/key.pem'),
cert: fs.readFileSync('certs/cert.pem')
}, function (req, res){
res.setHeader('Access-Control-Allow-Origin', '*');
res.setHeader('Access-Control-Allow-Headers', 'X-Requested-With, Content-Type');
}
).listen(env.socket.port, env.socket.host, function () {
console.log('\033[2J');
console.log('Websocket is running at http://%s:%s', server.address().address, server.address().port);
});
const io = require('socket.io')(server);
const session = require('express-session');
const RedisStore = require("connect-redis")(session);
const cookie = require('cookie');
const sessionMiddleware = session({
store: new RedisStore({
host: env.redis.host,
port: env.redis.port
}),
secret: env.session.secret,
cookieName: env.session.name,
rolling: true,
resave: true,
saveUninitialized: false,
cookie: {
maxAge: env.session.duration
}
});
io.use(function(socket, next) {
sessionMiddleware(socket.request, socket.request.res, next);
});
app.use(sessionMiddleware);
var clients = {};
app.get('/', function (req, res) {
res.send('Welcome!');
});
io.on('connection', function (socket) {
var origin = socket.request.headers.origin || '';
var myIP = socket.request.socket.remoteAddress || '';
var socketId = socket.id;
var session_id = '';
var authorized = false;
console.log(socket.request.session);
if (!originIsAllowed(origin)) {
// Make sure we only accept requests from an allowed origin
request.reject();
console.log((new Date()) + ' Connection from origin ' + origin + ' rejected.');
return false;
}
if(socket.request.sessionID){
session_id = socket.request.sessionID;
}
if(socket.request.session.authorized){
authorized = socket.request.session.authorized;
}
socket.on('connectMe', function(msg){
if(!msg || !msg.tokenId || msg.tokenId == 'undefined'){
console.log('SessionId was not found!');
return false;
}
if(!myIP){
console.log('Could not find client\'s IP Address');
return false;
}
var userCons = clients[session_id] || [];
if(userCons.indexOf(socketId) == -1){
userCons.push(socketId);
}
clients[session_id] = userCons;
console.log(clients);
var uncoded_token = new Buffer(msg.tokenId, 'base64');
//autherize the user only once - until the session is terminated
if( !authorized && sess.handleSession(uncoded_token, myIP, env.session.duration) ){
authorized = true;
session.authorized = authorized;
}
});
socket.on('chat', function(msg){
//only autherized users can chat
if( session.authorized ){
console.log('Chat Message: ' + msg);
socket.emit('chat', { message: msg });
}
});
socket.on('disconnect', function(msg){
console.log('Closing sessionID: ' + session_id);
var userCons = clients[session_id] || [];
var index = userCons.indexOf(socketId);
if(index > -1){
userCons.splice(index, 1);
console.log('Removed Disconnect Message: ' + msg);
} else {
console.log('Disconnect Message: ' + msg);
}
});
socket.on('error', function(msg){
console.log('Error Message: ' + msg);
});
});
function originIsAllowed(origin) {
// put logic here to detect whether the specified origin is allowed.
var allowed = env.session.allowedOrigins || []
if(allowed.indexOf(origin) >= 0){
return true;
}
return false;
}