Open macmillen opened 3 years ago
I'm afraid it's more complicated than it looks 😕
I wanted to do this by the custom attributes:
model User {
/// @TypeGraphQL.scalar(name: "EmailAddress")
email String @unique
}
But I realized I can only refer to built-in scalars as I don't know what import statement should it generate. For decorators it was solved by doing by TS file in runtime but TypeGraphQL has no way to alter already generated schema.
I need to find a better way to compose generation phase with TS values. Currently I'm thinking of exposing config object:
// typegraphql-config.ts
import { EmailAddressResolver } from 'graphql-scalars';
const config: TypeGraphQLGeneratorConfig = {
scalars: {
"EmailAddress": EmailAdressResolver,
},
};
export default config;
Which would be then registered in generator config:
generator typegraphql {
provider = "node ../src/cli/dev.ts"
output = "../prisma/generated/type-graphql"
config = "../typegraphql-config"
}
So the generator would be able to generate import for that file, so the scalar can be safely referenced:
import TypeGraphQLGeneratorConfig from "../some-relative-path/typegraphql-config";
@ObjectType()
export class Person {
@Field(() => TypeGraphQLGeneratorConfig.scalars["EmailAddress"])
email!: string;
}
The only drawback of this approach is that the config file would need to be as much static and independent (no custom code imports) as it's possible 🤔
Secondly, it's really complicated to apply such validation or scalars to input types, based on model type metadata. DMMF doesn't provide enough info about how the types are related to each other.
I try to apply some regex-like heuristic to detect that and rename types or fields. In case of scalars, it's one level more complicated because the types can be a complex StringFilter
which are harder to replace with custom scalar than simple field.
All in all, this feature might take a long time to implement, so for now I would recommend waiting a bit for applyInputTypesEnhanceMap
support and just use class-validator
on the fields you need 😉
Ok that makes sense, thanks for looking into it though. 👍 I'm already looking forward to the applyInputTypesEnhanceMap
.
@MichalLytek You can refer to unlight/prisma-nestjs-graphql, where he added options to generator field:
generator nestgraphql {
provider = "node node_modules/prisma-nestjs-graphql"
output = "../src/generated/prisma/nestgraphql"
# typescript declaration type
types_EmailAddress_fieldType = "string"
# graphql scalar type for @Field
types_EmailAddress_graphqlType = "EmailAddressResolver"
types_EmailAddress_graphqlModule = "graphql-scalars"
}
model Foo {
/// @TypeGraphQL.scalar(name: "EmailAddress")
email String @unique
}
Then it should generate:
import { EmailAddressResolver } from "graphql-scalars";
@ObjectType()
export class Foo {
@Field(() => EmailAddressResolver)
email!: string;
}
which should solve your problem
Also I think we can introduce default scalars in graphql-scalars
freely as we should be battery packed as much as possible. This mean we could let people to opt-out using it by import_default_types = false
If you could output just resolvers and a .graphql schema you could just import all types from graphql-codegen built from that .graphql. Could also output a codegen.yml with the model mappings mapped to the prisma models.
@fivethreeo typegraphql-prisma
emits resolver classes, not schema. TypeGraphQL can build typeDefs and resolvers but this breaks some of graphql-js
features like directives and extensions, so it's not a solution to force users to do that.
Any update? 😥
Just came across this. Would be great to use custom scalars in the generated code!
Would love to see this get merged! It would help us a lot @cerebruminc.
It would be useful if there would be a way to map certain primitive field scalars from certain types of the prisma schema to custom graphql scalars for example with graphql-scalars to have an even stricter type system which also reduces the need for class-validator since the validation takes place directly at the resolver level. It would be really nice to have this feature to have more control over the schema generation.
Example:
type definition of
Person
inprisma.schema
with the primitive typeString
:type definition of
Person
inschema.graphql
with a custom scalarEmailAddrress
:generated type definition of
Person
as a typegraphql object type with custom scalar resolver: