简体   繁体   English

如何使用 express 和 typescript 正确共享上下文

[英]How do I properly share context using express and typescript

I'd like to expose a value to all request handlers using express & typescript. I'd like to be able to "inject" this value from a middleware (or some other way), the point is that it should be easy to mock it in case I need to.我想使用 express & typescript 向所有请求处理程序公开一个值。我希望能够从中间件(或其他方式)“注入”这个值,关键是它应该很容易模拟以防万一。

I came up with this solution:我想出了这个解决方案:

// The context type, I'd like to be able to inject this using the middleware below. 
// In a real scenario think of this like a database connection, etc.
type RequestContext = {
  foo: string
}

// The type enriching the Request type with the context field
type HasContext = {
  context: RequestContext
}

// Middleware attaching the context to the request
const contextMiddleware =
  (context: RequestContext) => 
  (req: Request & Partial<HasContext>, _res: Response, next: NextFunction) => {
    req.context = context
    next()
  }


// Now an actual route using the extra type
const mainRoute = express.Router().get('/test', (req: Request & HasContext, res) => {
  res.json({ context: req.context })
})

// Adding the middlewares and listen
app.use(contextMiddleware({ foo: 'bar' }))
app.use(mainRoute)

app.listen(8000)

My questions:我的问题:

  • Is this the intended way of doing this using express?这是使用 express 执行此操作的预期方式吗? I scouted the API but couldn't find a better solution我搜索了 API 但找不到更好的解决方案
  • The extra data is attached to the request.额外的数据附加到请求中。 Is there any other way that does this without mutating the request or response itself?有没有其他方法可以在不改变请求或响应本身的情况下做到这一点?
  • The type Request & HasContext has to be defined in each request that uses this context.必须在使用此上下文的每个请求中定义类型Request & HasContext Is there a better way?有没有更好的办法?

You can overwrite the express Request interface to include your context property.您可以覆盖快速Request接口以包含您的context属性。 This way you don't have to specify the type anywhere.这样您就不必在任何地方指定类型。 It will also keep all the other properties that Request normally has.它还将保留Request通常具有的所有其他属性。

declare global {
  namespace Express {
    interface Request {
      context: RequestContext 
    }
  }
}

I would recommend not using the Request object to store information.我建议不要使用Request object 来存储信息。 Express recommends the use of the res.locals property. Express 建议使用res.locals属性。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM