【问题标题】:"message":"invalid csrf token","code":"EBADCSRFTOKEN"“消息”:“无效的 csrf 令牌”,“代码”:“EBADCSRFTOKEN”
【发布时间】:2021-08-19 06:18:03
【问题描述】:

我在 stackoverflow 中阅读了所有类似的问题,我在csurf github 页面中检查了问题,但我无法找出问题所在。这是 express 中间件文件:

const app = express();
const csrfProtection = csrf();
const MongoDBSessionStore = MongoDBStore(session);
const store = new MongoDBSessionStore({
  uri: process.env.MONGODB_URI!,
  collection: "sessions",
});
app.set("view engine", "ejs");
app.set("views", path.join(__dirname, "views"));
app.use(favicon(path.join(__dirname, "public", "favicon.ico")));
app.use(cors());
app.use(express.json());
app.use(multer({ storage: fileStorage, fileFilter }).single("image")); //arrray for multiple
app.use(express.static(path.join(__dirname, "public")));
app.use("/images", express.static(path.join(__dirname, "images")));
app.use(helmet());
app.use(compression()); 
app.use(
  session({
    name: "ts-authentication-app",
    secret: process.env.SESSION_SECRET!,
    resave: false,
    saveUninitialized: false,
    store: store,
  })
);
app.use(csrfProtection);
app.use(flash());
app.use(isAuthroized);
app.use((req, res, next) => {
  res.locals.isAuthenticated = req?.session?.isLoggedIn;
  res.locals.csrfToken = req.csrfToken();
  console.log("token", req.csrfToken());
  next();
});

app.use("/admin", adminRoutes);
app.use(shopRoutes);
app.use(authRoutes);
app.get("/500", errorController.get500);
app.use(errorController.get404);
app.use(morgan("combined", { stream: morganLogStream }));
app.use(errorHandler);

我正在使用 ejs 模板引擎。这是登录模板。

<form class="login-form" action="/login" method="POST" >
            <div class="form-control">
                <label for="email">E-Mail</label>
                <input 
                    class="<%= validationErrors.find(e => e.param === 'email') ? 'invalid' : '' %>"
                    type="email" 
                    name="email" 
                    id="email" 
                    value="<%= oldInput.email %>">
            </div>
            <div class="form-control">
                <label for="password">Password</label>
                <input 
                    class="<%= validationErrors.find(e => e.param === 'password') ? 'invalid' : '' %>"
                    type="password" 
                    name="password" 
                    id="password" 
                    value="<%= oldInput.password %>">
            </div>
            <input type="hidden" name="_csrf" value="<%= csrfToken %>">
            <button class="btn" type="submit">Login</button>
        </form>
  • csrfToken 显示在模板中。当我将“隐藏”类型更改为“文本”类型时,我会在页面上看到令牌。

  • 我注释掉了每个中间件以查看是否有任何中间件导致了问题,但我仍然收到错误消息。

  • 我记录了请求对象,csrfToken: [Function: csrfToken], 附加到请求对象。

我仍然无法解决问题。

【问题讨论】:

    标签: node.js typescript express ejs csrf


    【解决方案1】:

    您似乎没有为您用于表单的编码类型设置正确的正文解析器 - 即默认的x-www-form-urlencoded。

    Express 提供了这样一个正文解析器,只需将其添加到您的中间件堆栈中,如下所示:

    app.use(express.urlencoded({ extended: false }))
    

    【讨论】:

    • 我知道我犯了一个愚蠢的错误。我花了数周时间自己弄清楚:(。谢谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-01-02
    • 2017-07-15
    • 1970-01-01
    • 1970-01-01
    • 2018-05-12
    • 2019-09-05
    • 2022-08-16
    相关资源
    最近更新 更多