Closed Azzerty23 closed 1 year ago
As a workaround, destructuring the input object allows all relations to be present, but as optional.
Hi @Azzerty23 ,
Thanks for bringing this up. Unfortunately, this is a current limitation of tRPC. Due to the way how tRPC infers types, the router's typing is determined statically and cannot automatically adapt to the input's shape as Prisma could. Here's a github issue about this topic: https://github.com/trpc/trpc/issues/3311.
As suggested in the github discussion, it's possible to wrap another layer of hooks around the trpc router to achieve such kind of typing (pretty much what ZenStack is doing with the @zenstackhq/react
plugin for generating react hooks), but that'll introduce more complexity and also strange to use because it doesn't look like using tRPC anymore ...
The workaround you suggested can also be useful, although not ideal. At least you can get autocompletion to work for the relation fields. Maybe we can make that change to the trpc plugin?
I was not aware of this limitation in tRPC. I understand that you do not want to tweak tRPC. I hope that this issue will be solved through an enhancement of TypeScript and tRPC implementation. In the meantime, having an option to opt-in for the workaround would be great for sure!
Cool. Let me think about how to express that "opt-in" 😄.
Hi, @Azzerty23 I'm thinking about this issue again, and I feel maybe we can do something to "fix" trpc's typing, by casting its client hooks appropriately. Are you using trpc over Next.js with createTRPCNext
now?
Hi @ymc9, yes, I do. Do you mean you want to improve the typing of AppRouter
that is passed to createTRPCNext<AppRouter>
?
I spent some time poking around trpc's typing and couldn't find a way to hack it on the server-side router definition, but I think we can probably fix it on the trpc client side, since we're doing code generation anyway.
The change may look like this:
import { enhance } from '../routers/generated/next-utils.ts';
const trpc = enhance(createTRPCNext<AppRouter>({
...
}));
...
const query = trpc.post.findMany({include: { author: true}});
// query.data has type `Post & { author: User }` then
The enhance
function is generated and only does type-casting, turning hooks like findMany
etc. into Prisma-style generic typing so that the output's type adapts to the input.
What's unfortunate is the casting is client-specific, so I guess separate code needs to be generated for different client frameworks. Haven't looked deeply into this yet.
Does this make sense to you in general?
I see, indeed it seems to be the best approach!
Thanks! I'll continue exploring this route then.
Hi @Azzerty23 , this has been added in the latest "beta.3" release.
https://zenstack.dev/docs/reference/plugins/trpc#client-helpers
Description and expected behavior Generated Trpc routes do not allow for retrieving the types of relationships (
include
).Screenshots ✅ With original Prisma client:
❌ With generated trpc routes:
Environment (please complete the following information):
Additional context When I overwrite the generated procedure...
...typing works well
But I don't have the solution to dynamically attach types to the procedure input.