簡體   English   中英

表示csurf(csrf中間件)在angularjs中不使用XSRF

[英]express csurf (csrf middleware) not working with XSRF in angularjs

Express和Angular都有自己的csrf中間件。 我根本無法讓他們工作,互聯網上似乎沒有任何關於此問題的連貫指南。 我的理解是express 4.0使用csurf作為其csrf中間件,我必須在angularjs上設置X-XSRF-TOKEN

有關如何執行此操作的分散部分,有時會發生沖突的信息:

如何在node.js / express中測試受csrf保護的端點

angular,django和csrf

CSURF角度實施

但是我嘗試了它們並且它們不起作用。 我的_csrf在Angular客戶端上始終undefined ,盡管客戶端沒有提供csrf令牌,但csurf總是success

此外,我使用express-jwt來保持用戶會話,所以我不確定這是否會干擾cookie-session (curf所需)。

這是我用csrf處理注冊的簡單角度/快速應用程序(不工作):

angular app.js

var app = angular.module('app', ['ngCookies', 'ui.router']);

app.config(function($stateProvider) {
    $stateProvider.state('register', {
        url: '/register',
        controller: 'RegisterCtrl',
        templateUrl: 'views/register.html'
    });
});

// register csrf
app.run(['$http', '$cookies', function($http, $cookies) {
    $http.defaults.headers.post['X-XSRF-TOKEN'] = $cookies.csrftoken;
}]);

// controller
app.controller('RegisterCtrl', ['$scope', '$cookies', '$http', 
    function($scope, $cookies, $http) {
        $scope.data = { email: "", password: "", _csrf: $cookies._csrf};

        $scope.submitForm = function() {
            // This will alert 'undefined'
            alert("This is csrf token: " + $scope.data._csrf);

            $http.post('/register', data).success(function(done) {
               console.log('success');
               var jwt_token = done["jwt_token"];
               // save token to local storage.
            }).error(function(err) {
               console.log('error');
            });
        }
    }
]);

表達app.js

var express = require('express');
var app = express();
var http = require('http').Server(app);
var expressJwt = require("express-jwt");
var bodyParser = require('body-parser');
app.use(bodyParser.urlencoded({extended: true});
app.use(bodyParser.json());

// csrf setup
var session = require('cookie-session');
var csrf = require('csurf');
app.use(session({
    secret: 'keyboard cat'
}));
app.use(csrf());
// This part taken from csurf guide:
// https://github.com/expressjs/csurf
app.use(function(err, req, res, next) {
    if (err.code !== 'EBADCSRFTOKEN') return next(err)
    res.status(403);
    res.send('session has expired or form tampered with');
});

app.post("/login", function(req, res) {
    var email = req.body.email;
    var password = req.body.password;

    // save user to db ...
    var jwt_token = // create and sign jwt token to be given back to registered user

    res.json({"jwt_token": jwt_token});
});

http.listen(3000, function() {
   console.log("Express started");
});

現在,如果我提交注冊表單, alert()會說_csrf undefined 在expressjs方面, app.post('/login')一直運行而沒有失敗,即使csrf令牌應該是壞的( undefined因為角度側的csrf不起作用)。 這表明csurf在快遞方面根本不起作用。

有人可以提供一個深入的解釋,整合csurf在角快遞4.0,XSRF,並讓他們一起工作?

我在整合兩者時遇到了問題,並達到了以下結構(只是相關部分):

表達app.js

var cookieParser = require('cookie-parser');
var session = require('cookie-session');
var csrf = require('csurf');
app.use(session({
    secret: 'keyboard cat'
}));
app.use(cookieParser('secret'));
app.use(csrf());
app.use(function (req, res, next) {
    res.cookie("XSRF-TOKEN",req.csrfToken());
    return next();
});

在AngularJS方面,不需要改變。 它會自動識別XSRF-TOKEN。

現在,為了解釋上面的代碼,我需要引用csurf lib。 它是一個處理所有csrf身份驗證的中間件,但它實現了另一個名為csrf的 csrf庫。 這個csrf返回一個帶有四個函數的“類”(secret,secretSync,create,verify)。

csurf所做的是,當你調用它的中間件時,通過secretSync方法生成一個秘密並存儲在你的會話中。 您可以通過變量req.session.csrfSecret訪問它。 但是,它不執行req.csrfToken方法,該方法使用此秘密返回csrf令牌。 要正確返回csrf令牌,您需要在另一個中間件中調用它。

另一個重要的事情是,返回cookie的名稱必須是“XSRF-TOKEN”,而不是“_csrf”。 因此,Angular會自動識別它並將HTTP請求附加到“X-XSRF-TOKEN”,這是由csurf中間件識別的。

希望能幫助到你。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM