如何用Typescript正确创建自定义Express.js请求接口?



我试图为我的API创建一个自定义的Express请求接口。为此,我创建了一个名为AuthRequest的自定义接口,它从Express扩展了Request。无论如何,当我试图导入我的接口和定义req使用接口我在我的中间件功能,我从Typescript得到以下错误:

No overload matches this call.
The last overload gave the following error.
Argument of type '(req: AuthRequest, res: Response, next: NextFunction) => void' is not assignable to parameter of type 'PathParams'.
Type '(req: AuthRequest, res: Response<any, Record<string, any>>, next: NextFunction) => void' is missing the following properties from type '(string | RegExp)[]': pop, push, concat, join, and 28 more.ts(2769)
index.d.ts(165, 5): The last overload is declared here.

项目结构:

.
+-- src
|   +-- index.ts
|   +-- interface.ts
+-- package.json
+-- tsconfig.json

index.ts

import express, { Response, NextFunction } from "express";
import { AuthRequest } from "./interface";
const app = express();
const port = 8080;
app.use((req: AuthRequest, res: Response, next: NextFunction) => {
next();
});
app.listen(port, () => {
console.log(`App started on port ${port}`);
});

interface.ts

import { Request } from "express";
interface User {
id: number;
}
export interface AuthRequest extends Request {
user: User;
}

tsconfig.json

{
"compilerOptions": {
"target": "es6",
"module": "commonjs",
"outDir": "./dist",
"strict": true,
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true,
},
"include": [
"**/*.ts"
],
"exclude": [
"node_modules",
"dist/"
]
}

package.json

{
"name": "ts-express-server",
"version": "1.0.0",
"description": "Typescript Express Server",
"main": "src/index.ts",
"scripts": {
"start": "./node_modules/.bin/tsc --project ./tsconfig.json --watch & ts-node-dev src/index.ts"
},
"dependencies": {
"express": "4.17.1"
},
"devDependencies": {
"ts-node-dev": "1.1.8",
"typescript": "4.4.2",
"@types/express": "4.17.13"
},
"keywords": []
}

节点版本:v12.18.4NPM版本:6.14.13

我在这里错过了什么?请帮助!

不扩展Request接口,而是创建custom. d.s并扩展现有的Request接口。

import { User} from "./interface";
declare module "express-serve-static-core" {
export interface Request {
user?: User;
}
}

如果它将不工作检查答案在下一页包含相同的问题使用Typescript扩展Express Request对象

这行不通,因为Express不知道你的AuthRequest类,只知道Request。

你有两个选择。第一种方法是使用@types扩展Request对象:使用Typescript扩展Express Request对象

则可以将user添加为可选成员。然后您可以执行以下操作:

const RequireAuth = (middlewarefn: AuthMiddleware) => (req:Request, res:Response, next:NextFunction) => => {
if(req.user) {
return middlewarefn(req as AuthRequest, res, next)
}
// throw error?  404?
next();
}

你必须包装你的认证函数,但它会给你你需要的签名。你这样做违反了中间件API,所以你需要适应你的新方法签名。

如果您的目标是确保'user'存在,那么从实际的角度来看,还有一些其他的方法可以达到这个目的。

最新更新