-
-
Notifications
You must be signed in to change notification settings - Fork 2.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Enhanced TypeBox support for Fastify #3391
Comments
Will these changes to Fastify require adding typebox as a direct dependency? What other downside would have? cc @fastify/typescript |
@mcollina Hi. There's actually no changes required in Fastify to enable this. The library works over the top of Fastify (3.22.1) by remapping its type definitions using the TypeScript type system only. Users can opt into auto inference by installing import { FastifyTypeBoxInstance } from 'fastify-typebox'
const fastify = Fastify() as FastifyTypeBoxInstance // enable auto inference In terms of downsides, there are no functional changes (all this is happening entirely within the TypeScript type system). In terms of type differences, Fastify TypeBox rebuilds the export type FastifyTypeBoxSchema = {
body?: TSchema,
headers?: TSchema,
querystring?: TSchema,
response?: { [statusCode: number]: TSchema }
} At this stage, I'm treating the library as a proof of concept. I did want to share this approach as it does completely remove the need for Additionally, the technique used to augment Fastify types may prove useful to other JSON schema mappers, such as Lastly, I do actually get a few Fastify usage questions on the TypeBox project, so did want to provide something to help streamline usage scenarios specifically for Fastify. Given the nature of the library, I would actually be open to donating the Fastify TypeBox library to the Fastify organization for continued development if it ends up being helpful for users of either project. Cheers! |
I think we should document this in our docs, it looks amazing! |
@rickerp It should now. If you grab Example here. (note you may need to clear your browser cache to pull the latest dependency) import Fastify, { Type } from 'fastify-typebox'
import fastifySwagger from 'fastify-swagger'
const fastify = Fastify()
fastify.register(fastifySwagger, {
routePrefix: '/documentation',
swagger: { /* */ },
})
fastify.post('/hello/:world', {}, (request, reply) => {
reply.send(request.params.world)
}) I wonder if it might be a good idea to move additional issues over to the fastify-typebox repository. Would be good to gather all these edge cases to ensure things work as expected. Keep in mind this project is very much in the work in progress state, so expect a few issues here and there. Let me know how you go. |
@rickerp I'm still working on how best to expose these type mappings so things are a little in flux here. Currently there are two ways to opt in. import Fastify, { Type } from 'fastify-typebox'
const fastify = Fastify() // All setup with typebox import { Type, FastifyTypeBoxInstance } from 'fastify-typebox'
import Fastify from 'fastify'
const fastify = Fastify() as FastifyTypeBoxInstance // augment an existing instance While the first option is more ergonomic, the second is a bit more in-tune with how I'd prefer |
Definitely +1 on adding this to the documentation. The discussion itself is still highly active over a year later so i think it would be valuable to have more info on typescript/routes/typebox in the documentation site |
I like the |
I think it is the right time to re-visit the typing system for Maybe we can merge the argument of Lines 22 to 27 in 65de4e2
|
@climba03003 I agree with you that v4 is the perfect timing! Our types are very powerful but verbose too. Maybe providing better defaults or this concept of provider could make them even better! |
@climba03003 If it's helpful, I have actually been experimenting on a fastify fork exploring the Type Provider idea. I've actually managed to get Request schematics piping through and inferencing. Current implementation is quite rough, but the changes required to enable it can be viewed here https://github.com/sinclairzx81/fastify/commit/f2146ae46f01178faeeadc042a4775831a2f2245 Updates mostly included:
Current interface is roughly as follows. import { Fastify, FastifyTypeProvider } from 'fastify'
import { Static } from '@sinclair/typebox'
import { FromSchema } from 'json-schema-to-ts'
// typebox
interface TypeBoxTypeProvider extends FastifyTypeProvider {
output: Static<this["input"]>
}
// json-schema-to-ts
interface JsonSchemaTypeProvider extends FastifyTypeProvider {
output: FromSchema<this["input"]>
}
const fastify = Fastify().typeProvider<TypeBoxTypeProvider>() And a working screenshot. Hope this helps |
Prerequisites
Issue
Hi. I'm writing to submit a possible enhancement for Fastify + TypeBox users.
Given that the TypeBox library sees a fair amount of use in Fastify projects, I thought I'd see if there were ways to enhance the TypeBox user experience specifically for Fastify. The work primarily focused on removing the need to explicitly pass generic type parameters on Fastify routes, as well as removing the need for users to call TypeBox's
Static<T>
type. I felt the ideal solution was to try and automatically derive Fastify request and reply types directly from the TypeBox schemas, so the work primarily was centered on this aspect.I've setup an initial project which can be located here that provides such enhancements. The project is very much in a prototype proof of concept state and looking for community feedback. Also, I feel there may also be some potential here provide auto inference for direct JSON schema > TypeScript type mappers (without the use of TypeBox), so this project may serve as a possible integration path for that.
Submitting for community feedback.
Current Usage
Current usage requires keeping schema types external to the route so they can be passed to
Static<T>
. Additionally the Fastify route requires explicit generic arguments to ensure static checking inside the route.Enhanced Usage
Request and Reply types automatically inferred and statically checked in the route handler. You can test the type inference here.
The text was updated successfully, but these errors were encountered: