使用 socket.io 的 Express Session 和值在每次页面加载时重置
Express Session with socket.io and vue gets reset on every pageload
我正在尝试创建一个带有登录名的简单应用程序,只是为了玩弄 socketio、vue 和 nodejs (express),我在客户端和服务器上都可以进行发送和接收。
但是当我尝试集成一个会话以便让用户保持登录时我遇到了问题。
我尝试了很多不同的模块,但没有一个对我有用。我确定我现在还没有得到一些东西,因为我对 nodejs 和所有这些还很陌生。
无论如何这是我的代码:
前端:
<template>
<div>
<p>
<input type="text" name="username" id="username" v-model="user.username" placeholder="Username" /><br />
<input type="password" name="password" id="password" v-model="user.password" placeholder="Password" /><br />
<button v-on:click="register()">Register</button>
</p>
</div>
</template>
<script>
import io from 'socket.io-client';
export default {
name: 'BlockGame',
data() {
return {
user: {
username: '',
password: '',
},
socket: {},
context: {},
};
},
created() {
this.socket = io('localhost:3000', {
withCredentials: true,
});
},
mounted() {
this.socket.on('', (data) => {});
},
methods: {
register() {
this.socket.emit('register-user', this.user);
},
},
};
</script>
<style scoped></style>
后端:
const app = require('express')();
const redis = require('redis');
const server = require('http').createServer(app);
const session = require('express-session');
const socketio = require('socket.io')(server, {
cors: {
origin: 'http://localhost:8080',
methods: ['GET', 'POST'],
preflightContinue: false,
optionsSuccessStatus: 204,
credentials: true,
},
});
let RedisStore = require('connect-redis')(session);
let redisClient = redis.createClient();
var sessionMiddleware = session({
name: 'session_cookie',
secret: 'edfafewfdsfezhrjew',
store: new RedisStore({ client: redisClient }),
resave: false,
saveUninitialized: true,
cookie: { maxAge: 1000 * 60 * 5, secure: false },
});
app.use(sessionMiddleware);
socketio.use((socket, next) => {
sessionMiddleware(socket.request, {}, next);
});
socketio.on('connect', (socket) => {
const session = socket.request.session;
console.log(session.id);
if (session.user) {
console.log('----- SESSION -----');
console.log('Session ID: ' + session.id + ' / Session User: ' + session.user);
}
socket.on('register-user', (data) => {
const session = socket.request.session;
session.user = data['username'];
session.save();
console.log(session);
});
});
server.listen(3000, () => {
console.log('Listening at :3000...');
});
基本上应该发生的是,当用户“登录”时,他的用户名被保存到会话中。当用户刷新页面时,它应该仍然存在。但目前,每次用户刷新页面时,他都会获得一个新会话,所以一切都消失了。
希望有人能帮助我。
我尝试了您的服务器代码,客户端通过 express.static 提供服务,它按预期工作。即使在刷新后或在新选项卡上也提供相同的 sessionId。
app.use(express.static("public"))
客户端代码,保存在public/index.html
<!doctype html>
<html>
<head>
<script src='/socket.io/socket.io.js'></script>
<script>
var socket = io("/",{withCredentials: true,});
socket.on('connect', ()=>{
socket.emit('register-user', {username:"User Name"});
document.write("Connected")
})
</script>
</head>
</html>
在您的情况下,您正在为来自不同来源的客户端文件提供服务。
快速会话将不会像您预期的那样工作。即使对于简单的获取请求,也会创建新会话。尝试将以下代码添加到您的服务器,并尝试从您的客户端获取请求,您就会明白我的意思
app.use((req,_,next)=>{
console.log(req.session.id)
next()
})
我正在尝试创建一个带有登录名的简单应用程序,只是为了玩弄 socketio、vue 和 nodejs (express),我在客户端和服务器上都可以进行发送和接收。 但是当我尝试集成一个会话以便让用户保持登录时我遇到了问题。
我尝试了很多不同的模块,但没有一个对我有用。我确定我现在还没有得到一些东西,因为我对 nodejs 和所有这些还很陌生。
无论如何这是我的代码:
前端:
<template>
<div>
<p>
<input type="text" name="username" id="username" v-model="user.username" placeholder="Username" /><br />
<input type="password" name="password" id="password" v-model="user.password" placeholder="Password" /><br />
<button v-on:click="register()">Register</button>
</p>
</div>
</template>
<script>
import io from 'socket.io-client';
export default {
name: 'BlockGame',
data() {
return {
user: {
username: '',
password: '',
},
socket: {},
context: {},
};
},
created() {
this.socket = io('localhost:3000', {
withCredentials: true,
});
},
mounted() {
this.socket.on('', (data) => {});
},
methods: {
register() {
this.socket.emit('register-user', this.user);
},
},
};
</script>
<style scoped></style>
后端:
const app = require('express')();
const redis = require('redis');
const server = require('http').createServer(app);
const session = require('express-session');
const socketio = require('socket.io')(server, {
cors: {
origin: 'http://localhost:8080',
methods: ['GET', 'POST'],
preflightContinue: false,
optionsSuccessStatus: 204,
credentials: true,
},
});
let RedisStore = require('connect-redis')(session);
let redisClient = redis.createClient();
var sessionMiddleware = session({
name: 'session_cookie',
secret: 'edfafewfdsfezhrjew',
store: new RedisStore({ client: redisClient }),
resave: false,
saveUninitialized: true,
cookie: { maxAge: 1000 * 60 * 5, secure: false },
});
app.use(sessionMiddleware);
socketio.use((socket, next) => {
sessionMiddleware(socket.request, {}, next);
});
socketio.on('connect', (socket) => {
const session = socket.request.session;
console.log(session.id);
if (session.user) {
console.log('----- SESSION -----');
console.log('Session ID: ' + session.id + ' / Session User: ' + session.user);
}
socket.on('register-user', (data) => {
const session = socket.request.session;
session.user = data['username'];
session.save();
console.log(session);
});
});
server.listen(3000, () => {
console.log('Listening at :3000...');
});
基本上应该发生的是,当用户“登录”时,他的用户名被保存到会话中。当用户刷新页面时,它应该仍然存在。但目前,每次用户刷新页面时,他都会获得一个新会话,所以一切都消失了。
希望有人能帮助我。
我尝试了您的服务器代码,客户端通过 express.static 提供服务,它按预期工作。即使在刷新后或在新选项卡上也提供相同的 sessionId。
app.use(express.static("public"))
客户端代码,保存在public/index.html
<!doctype html>
<html>
<head>
<script src='/socket.io/socket.io.js'></script>
<script>
var socket = io("/",{withCredentials: true,});
socket.on('connect', ()=>{
socket.emit('register-user', {username:"User Name"});
document.write("Connected")
})
</script>
</head>
</html>
在您的情况下,您正在为来自不同来源的客户端文件提供服务。 快速会话将不会像您预期的那样工作。即使对于简单的获取请求,也会创建新会话。尝试将以下代码添加到您的服务器,并尝试从您的客户端获取请求,您就会明白我的意思
app.use((req,_,next)=>{
console.log(req.session.id)
next()
})