Set Custom Response Headers in OpenAPI
trpc-openapi does not allow us to set response headers as part of responses of a path.
To set custom response headers as part of swagger, we need to set headers within responses like given below.
paths:
/ping:
get:
summary: Checks if the server is alive.
responses:
'200':
description: OK
headers:
X-RateLimit-Limit:
schema:
type: integer
description: Request limit per hour.
The current implementation only sets the description and content within the status code of each response.
Have created a PR for the same
I would like to be able to set headers and status code dynamically in a request handler.
Doing this
res.statusCode = 302
res.setHeader('location', redirectPath)
doesn't work because trpc-openapi takes over both status code and headers.
How do I best achieve this?
trpc openApi doesn't recognise the status code and header set on the response and needs to be explicitly set again as part of meta.
export const appRouter = t.router({
sayHello: t.procedure
.meta({ /* 👉 */ openapi: { method: 'GET', path: '/say-hello', responseHeaders: 'location' } })
.input(z.object({ name: z.string() }))
.output(z.object({ greeting: z.string() }))
.query(({ input }) => {
return { greeting: `Hello ${input.name}!` };
});
});
For now status code is still by default 200. We need to create a new PR to accommodate this change
I would like to be able to set both headers and status code dynamically based on the request. So setting it in the .meta() function is not enough.
+1 here. Need to be able to set headers for the response. Feeling the pain on this one as we need to specify that we're calling set-cookie on the /signin route.
+1
+1
For what it's worth, there is a hacky workaround to get the headers set. It's just not defined via trpc-openapi
const router = t.router({
asset: t.procedure
.meta({ openapi: { method: 'GET', path: '/api/docs/{path}' } })
.input(z.object({
path: z.string()
}))
.output(z.any())
.query(({ ctx, input }) => {
Object.assign(ctx, {
path: input.path
});
return readFileSync(absolutePath() + `/${input.path}`, 'utf-8');
})
});
...
const server = http.createServer(createOpenApiHttpHandler({
router: router,
createContext: context,
responseMeta: (opts) => {
const path = opts?.ctx?.path;
const mime = path ? mimeTypes.lookup(path) : false;
if (mime) {
return {
headers: {
'Content-Type': mime
}
};
}
return {};
}
}));