nexus
Version:
Scalable, strongly typed GraphQL schema development
319 lines (303 loc) • 9.74 kB
text/typescript
import type { GraphQLScalarTypeConfig } from 'graphql'
import type { AllInputTypes, GetGen2 } from '../typegenTypeHelpers'
import type { AllNexusArgsDefs, AllNexusInputTypeDefs } from './wrapping'
import { Maybe, NexusTypes, withNexusSymbol } from './_types'
export type ArgsRecord = Record<string, AllNexusArgsDefs>
export type CommonArgConfig = {
/**
* [GraphQL 2018 Spec](https://spec.graphql.org/June2018/#sec-Descriptions)
*
* The description for this argument.
*
* Various GraphQL tools will make use of this information but it has zero runtime impact. The value given
* here will also be included as heredocs in the generated GraphQL SDL file.
*
* Default :: By default there will be no description
*
* @example
* export const Query = queryType({
* definition(t) {
* t.list.int('connectionCount', {
* args: {
* lastSeconds: intArg({
* description: 'Limit count to this number of past seconds from now.',
* }),
* },
* })
* },
* })
*
* // GraphQL SDL
* // -----------
* //
* // type Query {
* // connectionCount(
* // """Limit count to this number of past seconds from now."""
* // lastSeconds: Int
* // ): [Int]
* // }
*/
description?: Maybe<string>
/**
* Data that will be added to the arg-level [extensions field on the graphql-js type def
* instances](https://github.com/graphql/graphql-js/issues/1527) resulting from makeSchema. Useful for some
* graphql-js based tools which rely on looking for special data here.
*/
extensions?: GraphQLScalarTypeConfig<any, any>['extensions']
} & NexusGenPluginArgConfig
export interface ScalarArgConfig<T> extends CommonArgConfig {
/**
* The default value for this argument when ***none*** is given by the client.
*
* Note that *null* is still considered something meaning if the client gives an explicit null that will
* prevent the default from activating. This is why the type of an arg with a default value in the resolver
* includes "undefined | null".
*
* @example
* intArg({ default: 42 })
*/
default?: T
}
export type NexusArgConfigType<T extends string> = T | AllNexusInputTypeDefs<T>
export interface NexusAsArgConfig<T extends string> extends CommonArgConfig {
/**
* Sets the default value for this argument, should match the type of the argument
*
* @example
* intArg({ default: 42 })
*/
default?: GetGen2<'inputTypeShapes', T>
}
export interface NexusArgConfig<T extends string> extends NexusAsArgConfig<T> {
/**
* [GraphQL 2018 Spec](https://spec.graphql.org/June2018/#sec-Types)
*
* The type that this argument should be.
*
* Argument types may be scalars or other input types (input objects, enums) in your schema and modified
* with non-null and list types.
*
* Types may be expressed in one of three ways:
*
* 1. As string literals matching the name of a builtin scalar. 2. As string literals matching the name of
* another type. Thanks to [Nexus' reflection
* system](https://nxs.li/guides/reflection) this is typesafe and autocompletable. 3. As references to other
* enums or input object type definitions.
*
* Type modifier helpers like list() may also be used and in turn accept one of the three methods listed above.
*
* @example
* arg({ type: 'UserCreateInput' })
*
* @example
* arg({ type: nonNull(list(nonNull('UserCreateInput'))) })
*
* @example
* arg({ type: UserCreateInput })
*
* @example
* arg({ type: nonNull(list(nonNull(UserCreateInput))) })
*
* @example
* arg({ type: 'String' })
*/
type: NexusArgConfigType<T>
}
export interface NexusFinalArgConfig extends NexusArgConfig<any> {
configFor: 'arg'
argName: string
fieldName: string
parentType: string
}
export class NexusArgDef<TypeName extends AllInputTypes> {
constructor(readonly name: TypeName, protected config: NexusArgConfig<any>) {}
get value() {
return this.config
}
}
withNexusSymbol(NexusArgDef, NexusTypes.Arg)
/**
* [API Docs](https://nexusjs.org/docs/api/args) | [GraphQL.org
* Docs](https://graphql.github.io/learn/schema/#arguments) | [GraphQL 2018
* Spec](https://spec.graphql.org/June2018/#sec-Language.Arguments)
*
* Define an argument. Arguments can be used with the args config of any field.
*
* @example
* export const Mutation = mutationType({
* definition(t) {
* t.field('createDraft', {
* type: 'Post',
* args: {
* title: arg({
* type: 'String',
* default: 'Untitled',
* description: 'The title of this draft post.',
* }),
* body: nonNull(
* arg({
* type: 'String',
* description: 'The content of this draft post.',
* })
* ),
* },
* // ...
* })
* },
* })
*
* @param config Configuration for the argument like its type and description. See jsdoc on each config field
* for details.
*/
export function arg<T extends string>(config: NexusArgConfig<T>) {
if (!config.type) {
throw new Error('You must provide a "type" for the arg()')
}
return new NexusArgDef(typeof config.type === 'string' ? config.type : (config.type as any).name, config)
}
/**
* [API Docs](https://nexusjs.org/docs/api/args) | [GraphQL.org
* Docs](https://graphql.github.io/learn/schema/#arguments) | [GraphQL 2018
* Spec](https://spec.graphql.org/June2018/#sec-Language.Arguments)
*
* Define a string argument. Arguments can be used with the args config of any field.
*
* This is a shorthand equivalent to:
*
* `arg({ type: 'String', ... })`
*
* @example
* export const Mutation = mutationType({
* definition(t) {
* t.field('createDraft', {
* type: 'Post',
* args: {
* title: stringArg(),
* body: stringArg(),
* },
* // ...
* })
* },
* })
*
* @param config Configuration for the argument like its description. See jsdoc on each config field for details.
*/
export function stringArg(config?: ScalarArgConfig<string>) {
return arg({ type: 'String', ...config })
}
/**
* [API Docs](https://nexusjs.org/docs/api/args) | [GraphQL.org
* Docs](https://graphql.github.io/learn/schema/#arguments) | [GraphQL 2018
* Spec](https://spec.graphql.org/June2018/#sec-Language.Arguments)
*
* Define a string argument. Arguments can be used with the args config of any field.
*
* This is a shorthand equivalent to:
*
* `arg({ type: 'Int', ... })`
*
* @example
* export const Query = queryType({
* definition(t) {
* t.field('search', {
* type: 'SearchResult',
* args: {
* maxResults: intArg(),
* },
* // ...
* })
* },
* })
*
* @param config Configuration for the argument like its description. See jsdoc on each config field for details.
*/
export function intArg(config?: ScalarArgConfig<number>) {
return arg({ type: 'Int', ...config })
}
/**
* [API Docs](https://nexusjs.org/docs/api/args) | [GraphQL.org
* Docs](https://graphql.github.io/learn/schema/#arguments) | [GraphQL 2018
* Spec](https://spec.graphql.org/June2018/#sec-Language.Arguments)
*
* Define a string argument. Arguments can be used with the args config of any field.
*
* This is a shorthand equivalent to:
*
* `arg({ type: 'Float', ... })`
*
* @example
* export const Query = queryType({
* definition(t) {
* t.field('search', {
* type: 'SearchResult',
* args: {
* ratingAbove: floatArg(),
* },
* // ...
* })
* },
* })
*
* @param config Configuration for the argument like its description. See jsdoc on each config field for details.
*/
export function floatArg(config?: ScalarArgConfig<number>) {
return arg({ type: 'Float', ...config })
}
/**
* [API Docs](https://nexusjs.org/docs/api/args) | [GraphQL.org
* Docs](https://graphql.github.io/learn/schema/#arguments) | [GraphQL 2018
* Spec](https://spec.graphql.org/June2018/#sec-Language.Arguments)
*
* Define a string argument. Arguments can be used with the args config of any field.
*
* This is a shorthand equivalent to:
*
* `arg({ type: 'ID', ... })`
*
* @example
* export const Query = queryType({
* definition(t) {
* t.field('user', {
* type: 'User',
* args: {
* id: idArg(),
* },
* // ...
* })
* },
* })
*
* @param config Configuration for the argument like its description. See jsdoc on each config field for details.
*/
export function idArg(config?: ScalarArgConfig<string>) {
return arg({ type: 'ID', ...config })
}
/**
* [API Docs](https://nexusjs.org/docs/api/args) | [GraphQL.org
* Docs](https://graphql.github.io/learn/schema/#arguments) | [GraphQL 2018
* Spec](https://spec.graphql.org/June2018/#sec-Language.Arguments)
*
* Define a string argument. Arguments can be used with the args config of any field.
*
* This is a shorthand equivalent to:
*
* `arg({ type: 'Boolean', ... })`
*
* @example
* export const Query = queryType({
* definition(t) {
* t.list.field('users', {
* type: 'User',
* args: {
* active: booleanArg(),
* },
* // ...
* })
* },
* })
*
* @param config Configuration for the argument like its description. See jsdoc on each config field for details.
*/
export function booleanArg(config?: ScalarArgConfig<boolean>) {
return arg({ type: 'Boolean', ...config })
}