2012-11-23 37 views
2

我試圖將Express(3.x)與NowJS(主要是圍繞Socket.io的包裝)結合起來創建一個實時應用程序,首先要求您記錄我承認Node是新手,但是我對每個軟件包的工作方式都有很好的掌握。但是,從NowJS訪問快速會話信息會讓我覺得合適。通過XHR輪詢的Socket.io未通過Cookie

問題似乎是因爲我被迫使用XHR-Polling(使用Heroku作爲主機平臺),我無法輕鬆訪問Socket.io身份驗證方法中的cookie信息。在authFunction的以下代碼中,「data.headers.cookie」未定義。以迂迴的方式(在Now.js代碼中),這會在nowjs.on(「connect」,...)回調中留下「this.user.cookie」爲空(但不是未定義)。這反過來讓我無法獲取會話信息。

從閱讀來看,似乎只有使用websocket纔可以使用cookie。沒有cookie,我不知道哪個用戶正在調用服務器,除了爲它們生成的隨機標識符。

任何人都可以提出如何解決這個問題嗎?在建立與Now.js服務器的連接後,是否需要手動從客戶端發送cookie?

var app = express(); 

app.configure(function(){ 
    app.set('port', process.env.PORT || 3000); 
    app.set('views', __dirname + '/views'); 
    app.engine('html', consolidate.swig); 
    app.set('view engine', 'html'); 

    app.use(express.favicon()); 
    app.use(express.logger('dev')); 
    app.use(express.bodyParser()); 
    app.use(express.methodOverride()); 
    app.use(express.cookieParser()); 
    app.use(express.session({ secret: "secrethere" , store: sessionStore})); 

    app.use(express.static(path.join(__dirname, 'public'))); 
    app.use(app.router); 
}); 

app.configure('development', function(){ 
    app.use(express.errorHandler({dumpExceptions: true, showStack: true})); 
}); 

//Map the routes 
var routes = require('./routes/routes')(db); 
app.get[...] //routes defined here 

var server = http.createServer(app, {cookieKey: 'connect.sid'}); 
server.listen(app.get('port'), function(){ 
    console.log("Express server listening on port " + app.get('port')); 
}); 

var parseCookie = require('express/node_modules/connect').utils.parseCookie; 
var authFunction = function (data, accept) { 
// check if there's a cookie header 
if (data.headers.cookie) { 
    // if there is, parse the cookie 
    data.cookie = parseCookie(data.headers.cookie); 

    // note that you will need to use the same key to grad the 
    // session id, as you specified in the Express setup. 
    data.sessionID = data.cookie['connect.sid']; 
} else { 
    // if there isn't, turn down the connection with a message 
    // and leave the function. 
    return accept('No cookie transmitted.', false); 
} 

// accept the incoming connection 
accept(null, true); 
}; 

var everyone = nowjs.initialize(server, {socketio: {transports: ['xhr-polling', 'jsonp-polling'], authorization: authFunction}}); 

nowjs.on('connect', function (socket) { 
//TODO - This will need to be based on the URL that is being visited, or 
//similar to establish that users are viewing the same thing 
var sid = unescape(this.user.cookie["connect.sid"]); //# you DO have to unescape the session id! 

sessionStore.get(sid, function(err, sess){ 
    console.log("That group who joined? his userId is " + sess.userId) 
}); 

var newRoom = "group";//this.user.session;//.groupName; 
var newGroup = nowjs.getGroup(newRoom); 
this.now.serverRoom = newRoom; 
newGroup.addUser(this.user.clientId); 
}); 

編輯:當然,我寧願喜歡這裏最多的回答簡單的解決方案:Session support in Now.js,但是,這並不爲我工作了(可能)同樣的原因 - 我的「cookie」是空的,不包含「connect.sid」鍵。

回答

0

經過大量嘗試不同的事情之後,我意識到這實際上與我使用的環境(Cloud9 IDE)有關。

使用Cloud9進行調試時,它們會爲您提供一個很好的網址,以便在「http:// [projectname]。[username] .c9.io」中瀏覽您的網站。但是,NowJS將其請求發送到「http:// project- [unique ID] .rhcloud.com/socket.io/1/xhr-polling/...」。這是而不是提示cookie與請求一起發送,因爲它不是與cookie關聯的主機(好的,術語可能稍微偏離此處)。

要解決此問題,我使用「http:// project- [unique ID] .rhcloud.com/...」作爲我的調試基礎,並且它似乎正常工作100%。 Heroku似乎沒有這個問題,因爲所有請求(常規頁面請求 socketio)都通過相同的主機。