Angularjs $ http似乎不理解响应中的“Set-Cookie”

时间:2013-10-15 14:05:30

标签: node.js angularjs express

我有一个nodejs用Passport模块表达REST api进行身份验证。 登录方法(GET)在标头中返回一个cookie。当我从Chrome中调用它时,它可以正常工作,我的cookie已在我的浏览器中设置。

但是如果我通过Angularjs的$ http调用它,则不会设置cookie。

Set-Cookie:connect.sid=s%3Ad7cZf3DSnz-IbLA_eNjQr-YR.R%2FytSJyd9cEhX%2BTBkmAQ6WFcEHAuPJjdXk3oq3YyFfI; Path=/; HttpOnly

如上所示,Set-Cookie出现在http服务响应的标题中。

也许HttpOnly可能是这个问题的根源?如果是,我该如何更改?这是我的快速配置:

app.configure(function () {
    app.use(allowCrossDomain);
    app.use(express.bodyParser());
    app.use(express.cookieParser())
    app.use(express.session({ secret: 'this is a secret' }));
    app.use(flash());
    //passport init
    app.use(passport.initialize());
    app.use(passport.session());
    app.set('port', process.env.PORT || 8080);
});

感谢您的帮助

5 个答案:

答案 0 :(得分:19)

确保配置$ http请求以使用凭据。 来自XHR文档:

https://developer.mozilla.org/en-US/docs/HTTP/Access_control_CORS

  

XMLHttpRequest和XML公开的最有趣的功能   访问控制是能够进行“凭证”请求的能力   认识到HTTP Cookie和HTTP身份验证信息。通过   默认情况下,在跨站点XMLHttpRequest调用中,浏览器不会   发送凭据。必须在XMLHttpRequest上设置特定标志   调用它时的对象。

您可以使用options对象设置凭据的使用,请参阅

http://docs.angularjs.org/api/ng.$http

示例:

$http({withCredentials: true, ...}).get(...)

答案 1 :(得分:5)

你是如何检查cookie的存在的?

$http只是浏览器XHR的包装器,就像jQuery的$.ajax和朋友一样。这意味着您的浏览器将正常处理cookie。

我的猜测是 正在设置,但您正试图通过document.cookie阅读它。 HttpOnly阻止脚本访问cookie。 这是一件好事。

HttpOnly有助于缓解XSS攻击。它使恶意脚本无法窃取用户的会话令牌(以及他们的登录)。 请勿关闭HttpOnly

无论如何你不应该需要cookie。由于$http只是XHR的包装器,因此浏览器会在您下次发出请求时自动发送cookie。您可以通过在开发人员工具的“网络”面板中查看请求来验证这一点。

答案 2 :(得分:5)

我通过在角度{withCredential : true}请求中设置$http并设置:

来解决了这个问题
res.header("Access-Control-Allow-Credentials", true);

在我的快速服务器配置中。通过这样做,我的cookie很好地出现在我的浏览器cookie列表中。

答案 3 :(得分:1)

以下解决方案对我有用

Angular 中,我使用了以下代码段, withCredentials: true应我的要求。

this._http.post(this._apiUrl + 'api/' + url, data, { withCredentials: true })
            .subscribe(data => { resolve(data) }, error => { this.showServerError(error)})

在Node中,在获得解决方案之前,我只是使用

初始化 CORS
app.use(cors());

但是,现在我实现了以下代码段

app.use(cors({origin: [
   "http://localhost:5000"
 ], credentials: true}))
  

其中http://localhost:5000是我的Angular应用程序端点。您   可以从config或.env文件动态设置此URL。

希望上述解决方案能解决您的问题。

答案 4 :(得分:0)

您可以通过配置express.session

来更改它
app.use(express.session({
  secret : 'this is a secret',
  cookie : {
    httpOnly : false,
    maxAge   : XXX // see text
  }
});

但我认为Angular不太关心cookie,这些是由浏览器处理的(我同意@josh3736你应该httpOnly保持true)。

这可能与您的Cookie(浏览器)会话Cookie有关。您可以通过为cookie明确设置maxAge来尝试查看它是否更好。(以毫秒为单位)。