UNPKG

graphql-gene

Version:

Generates automatically an executable schema out of your ORM models

1 lines 18.3 kB
{"version":3,"file":"index.cjs","sources":["../../src/utils/extend.ts","../../src/utils/index.ts"],"sourcesContent":["import type {\n StrictExtendedTypes,\n NarrowExtendedTypes,\n StrictArgsDefinition,\n GeneDirectiveConfig,\n GeneConfig,\n} from '../defineConfig'\nimport type { GraphqlReturnTypes, TypeOrFunction, ValidGraphqlType } from '../types'\nimport { isObject } from '.'\n\ndeclare global {\n var __graphqlGeneExtendedTypes:\n | { config: StrictExtendedTypes; geneConfig: { [type: string]: GeneConfig | undefined } }\n | undefined\n}\n\nexport function getGloballyExtendedTypes(): NonNullable<\n typeof globalThis.__graphqlGeneExtendedTypes\n> {\n globalThis.__graphqlGeneExtendedTypes = globalThis.__graphqlGeneExtendedTypes ?? {\n config: {},\n geneConfig: {},\n }\n\n return globalThis.__graphqlGeneExtendedTypes\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport function setGeneConfigByType<TGeneConfig extends GeneConfig<any>>(\n type: string,\n geneConfig: TGeneConfig | undefined\n) {\n if (!geneConfig) return\n\n const globalTypes = getGloballyExtendedTypes()\n globalTypes.geneConfig[type] = geneConfig\n}\n\nexport function extendTypes<\n T extends {\n [TypeName in keyof T]: {\n [Field in keyof T[TypeName]]: {\n [K in keyof T[TypeName][Field]]: K extends 'returnType'\n ? GraphqlReturnTypes<ValidGraphqlType>\n : K extends 'args'\n ? StrictArgsDefinition\n : K extends 'directives'\n ? TypeOrFunction<GeneDirectiveConfig[]>\n : T[TypeName][Field][K]\n }\n }\n },\n>(types: NarrowExtendedTypes<T>) {\n const globalTypes = getGloballyExtendedTypes()\n\n Object.entries(types).forEach(([graphqlType, fieldConfigs]) => {\n if (!isObject(fieldConfigs)) {\n throw new Error(`Provided field config for type \"${graphqlType}\" must be an object.`)\n }\n const type = graphqlType as 'Query'\n globalTypes.config[type] = globalTypes.config[type] || {}\n globalTypes.config[type] = { ...globalTypes.config[type], ...fieldConfigs }\n })\n}\n","import {\n buildASTSchema,\n buildSchema,\n extendSchema,\n GraphQLDirective,\n GraphQLInterfaceType,\n GraphQLList,\n GraphQLNonNull,\n GraphQLObjectType,\n GraphQLSchema,\n isScalarType,\n isSpecifiedDirective,\n isSpecifiedScalarType,\n parse,\n parseType,\n print,\n type DocumentNode,\n type GraphQLField,\n type GraphQLNamedType,\n type GraphQLOutputType,\n} from 'graphql'\nimport type { GeneContext } from 'graphql-gene/context'\nimport type { AnyObject, FieldLines, GraphQLVarType, TypeDefLines, TypeOrFunction } from '../types'\nimport type { GeneConfig, GeneTypeConfig } from '../defineConfig'\n\nexport * from './extend'\n\ntype GraphQLOutputObjectType = GraphQLObjectType | GraphQLInterfaceType\n\nexport function parseSchemaOption(\n schema: GraphQLSchema | DocumentNode | string | undefined,\n scalars?: string[]\n): GraphQLSchema | undefined {\n if (!schema && (!scalars || !scalars.length)) return undefined\n\n let parsedSchema: GraphQLSchema | undefined = undefined\n\n if (schema) {\n parsedSchema =\n typeof schema === 'string'\n ? buildSchema(schema)\n : schema instanceof GraphQLSchema\n ? schema\n : buildASTSchema(schema)\n }\n if (scalars?.length) {\n const undefinedScalars = scalars.filter(scalar => !parsedSchema?.getType(scalar))\n const scalarsDef = undefinedScalars.map(scalar => `scalar ${scalar}`).join('\\n')\n\n parsedSchema = parsedSchema\n ? extendSchema(parsedSchema, parse(scalarsDef))\n : buildSchema(scalarsDef)\n }\n return parsedSchema\n}\n\nexport function lookDeepInSchema<TState>(options: {\n each: (details: {\n field: string\n fieldDef: GraphQLField<\n Record<string, unknown> | undefined,\n GeneContext,\n Record<string, unknown> | undefined\n >\n isList: boolean\n isNonNullable: boolean\n parentType: string\n parentTypeDef: GraphQLOutputObjectType\n state: TState\n type: string\n typeDef: GraphQLNamedType\n }) => TState | undefined\n schema: GraphQLSchema\n state?: TState\n}) {\n const queryType = options.schema.getQueryType()\n const mutationType = options.schema.getMutationType()\n if (!queryType && !mutationType) return\n\n const typesChecked = new Set<string>([])\n\n const lookDeeper = (parentTypeDef: GraphQLOutputObjectType, state: TState) => {\n if (typesChecked.has(parentTypeDef.name)) return\n\n typesChecked.add(parentTypeDef.name)\n const childFields = parentTypeDef.getFields()\n\n Object.entries(childFields).forEach(([field, fieldDefinition]) => {\n const fieldDef = fieldDefinition\n const typeDefWrap = fieldDefinition.type\n if (!fieldDef || !typeDefWrap) return\n\n const typeDef = findAccurateTypeDef(typeDefWrap)\n if (!typeDef) return\n\n const newState = options.each({\n field,\n fieldDef,\n\n get isList(): boolean {\n return (\n fieldDef instanceof GraphQLList ||\n ('ofType' in typeDefWrap && typeDefWrap.ofType instanceof GraphQLList)\n )\n },\n get isNonNullable(): boolean {\n return fieldDef instanceof GraphQLNonNull\n },\n parentType: parentTypeDef.name,\n parentTypeDef,\n state,\n type: typeDef.name,\n\n get typeDef() {\n const type = options.schema.getType(typeDef.name)\n return type as NonNullable<typeof type>\n },\n })\n\n // Look deeper if the type has child fields\n if ('getFields' in typeDef) lookDeeper(typeDef, newState || state)\n })\n }\n if (queryType) lookDeeper(queryType, options.state || ({} as TState))\n if (mutationType) lookDeeper(mutationType, options.state || ({} as TState))\n}\n\nexport function findAccurateTypeDef(type: GraphQLOutputType) {\n const typeDefinition = ('ofType' in type ? findAccurateTypeDef(type.ofType) : type) as\n | GraphQLOutputType\n | undefined\n\n if (typeDefinition && 'name' in typeDefinition) return typeDefinition\n}\n\nexport function getGraphqlType(\n variable: string | number | boolean | string[] | number[] | boolean[]\n) {\n const isArray = Array.isArray(variable)\n const varType = isArray ? typeof variable[0] : typeof variable\n\n const typeMap: Record<string, 'String' | 'Int' | 'Boolean'> = {\n string: 'String',\n number: 'Int',\n boolean: 'Boolean',\n }\n return isArray ? `[${typeMap[varType]}!]` : typeMap[varType]\n}\n\n/**\n * Inspired by\n * @see https://github.com/graphql/graphql-js/issues/869#issuecomment-374351118\n */\nexport function printSchemaWithDirectives(schema: GraphQLSchema) {\n let schemaString = ''\n\n const printAst = (type: GraphQLDirective | GraphQLNamedType) => {\n if (isScalarType(type)) schemaString += `scalar ${type.name}\\n\\n`\n if (type && 'astNode' in type && type.astNode) schemaString += `${print(type.astNode)}\\n\\n`\n }\n\n schema.getDirectives().forEach(type => {\n if (!isSpecifiedDirective(type)) printAst(type)\n })\n\n const typeEntries = Object.entries(schema.getTypeMap())\n\n // Print Query and Mutation types before the other types that are alphabetically sorted\n typeEntries.sort(([aTypeName], [bTypeName]) => {\n if (aTypeName === 'Query') return -1\n if (aTypeName === 'Mutation') return bTypeName === 'Query' ? 1 : -1\n\n if (bTypeName === 'Query') return 1\n if (bTypeName === 'Mutation') return aTypeName === 'Query' ? -1 : 1\n\n return aTypeName.localeCompare(bTypeName)\n })\n\n typeEntries\n // Filter out internal type definition like __Directive, __Field, __InputValue\n .filter(([typeName]) => !/^__/.test(typeName))\n .forEach(([, type]) => {\n if (!isSpecifiedScalarType(type)) printAst(type)\n })\n\n return schemaString.replace(/\\n$/, '')\n}\n\n/** is using default Gene resolver if `resolver` or `args` option is set to \"default\" */\nexport function isUsingDefaultResolver(fieldConfig: AnyObject): boolean {\n return (['resolver', 'args'] as const).some(\n prop => prop in fieldConfig && fieldConfig[prop] === 'default'\n )\n}\n\nexport function getDefaultTypeDefLinesObject(): TypeDefLines[0] {\n return { varType: 'type', directives: new Set<string>([]), lines: {} }\n}\n\nexport function getDefaultFieldLinesObject(): FieldLines[0] {\n return { directives: new Set<string>([]), typeDef: '', argsDef: {} }\n}\n\nexport function isObject<T>(variable: T) {\n return variable !== null && typeof variable === 'object'\n}\n\nexport function isEmptyObject<T extends object>(obj: T) {\n for (const _prop in obj) return false\n\n return true\n}\n\nexport function isArrayFieldConfig<T>(\n fieldConfigs: T\n): fieldConfigs is Extract<T, readonly string[]> {\n return Array.isArray(fieldConfigs)\n}\n\nexport function isObjectFieldConfig<T>(\n fieldConfigs: T\n): fieldConfigs is Exclude<T, readonly string[]> {\n return isObject(fieldConfigs)\n}\n\n// eslint-disable-next-line @typescript-eslint/no-explicit-any\nexport function normalizeFieldConfig<TConfig extends string | GeneTypeConfig<any, any, any, any>>(\n fieldConfig: TConfig\n): GeneTypeConfig {\n return typeof fieldConfig === 'string'\n ? ({ returnType: fieldConfig } as GeneTypeConfig)\n : fieldConfig\n}\n\nexport function isListType(type: ReturnType<typeof parseType>) {\n const typeToCheck = type.kind === 'NonNullType' ? type.type : type\n return typeToCheck.kind === 'ListType'\n}\n\nexport function findTypeNameFromTypeNode(type: ReturnType<typeof parseType>): string {\n return 'type' in type ? findTypeNameFromTypeNode(type.type) : type.name.value\n}\n\nexport function getFieldDefinition(options: {\n schema: GraphQLSchema\n parent: string\n field: string\n}) {\n const typeDefinition = options.schema.getType(options.parent)\n\n // // This should only happen if the provided parent type is invalid\n if (!typeDefinition) return\n\n const fields = 'getFields' in typeDefinition ? typeDefinition.getFields() : undefined\n const fieldDef = fields?.[options.field]\n\n return fieldDef && 'resolve' in fieldDef ? fieldDef : undefined\n}\n\n/**\n * Receives the full GraphQL return type and returns the type name as string.\n *\n * @example\n * const returnTypeName = getReturnTypeName('[Foo!]!') // => 'Foo'\n */\nexport function getReturnTypeName(returnType: string) {\n return findTypeNameFromTypeNode(parseType(returnType))\n}\n\nexport function getGeneConfigFromOptions<M>(options: {\n model: M\n geneConfig?: GeneConfig<M>\n}): GeneConfig<M> | undefined {\n return (\n options.geneConfig ||\n (options.model &&\n (typeof options.model === 'object' || typeof options.model === 'function') &&\n 'geneConfig' in options.model &&\n options.model.geneConfig) ||\n undefined\n )\n}\n\nexport function parseGetterConfig<T>(config: TypeOrFunction<T>): T {\n return config instanceof Function ? config() : config\n}\n\nexport function isFieldIncluded<M>(\n geneConfig: GeneConfig<M> | undefined,\n fieldKey: string\n): boolean {\n const config = geneConfig || {}\n\n const check = (filters: unknown[]) => {\n for (const keyOrRegex of filters) {\n if (typeof keyOrRegex === 'string' && keyOrRegex === fieldKey) return true\n if (keyOrRegex instanceof RegExp && keyOrRegex.test(fieldKey)) return true\n }\n }\n if (config.include && !check(config.include)) return false\n\n let extraExclude = new Set(['createdAt' as const, 'updatedAt' as const])\n\n if (Array.isArray(config.includeTimestamps)) {\n config.includeTimestamps.forEach(timestamp => extraExclude.delete(timestamp))\n } else if (config.includeTimestamps === true) {\n extraExclude = new Set([])\n }\n\n const exclude = [...(config.exclude || []), ...extraExclude]\n if (check(exclude)) return false\n\n return true\n}\n\nexport function createTypeDefLines(\n typeDefLines: TypeDefLines,\n varType: GraphQLVarType,\n varName: string\n) {\n typeDefLines[varName] = { ...getDefaultTypeDefLinesObject(), ...typeDefLines[varName] }\n typeDefLines[varName].varType = varType\n}\n"],"names":["getGloballyExtendedTypes","setGeneConfigByType","type","geneConfig","globalTypes","extendTypes","types","graphqlType","fieldConfigs","isObject","parseSchemaOption","schema","scalars","parsedSchema","buildSchema","GraphQLSchema","buildASTSchema","scalarsDef","scalar","extendSchema","parse","lookDeepInSchema","options","queryType","mutationType","typesChecked","lookDeeper","parentTypeDef","state","childFields","field","fieldDefinition","fieldDef","typeDefWrap","typeDef","findAccurateTypeDef","newState","GraphQLList","GraphQLNonNull","typeDefinition","getGraphqlType","variable","isArray","varType","typeMap","printSchemaWithDirectives","schemaString","printAst","isScalarType","print","isSpecifiedDirective","typeEntries","aTypeName","bTypeName","typeName","isSpecifiedScalarType","isUsingDefaultResolver","fieldConfig","prop","getDefaultTypeDefLinesObject","getDefaultFieldLinesObject","isEmptyObject","obj","_prop","isArrayFieldConfig","isObjectFieldConfig","normalizeFieldConfig","isListType","findTypeNameFromTypeNode","getFieldDefinition","getReturnTypeName","returnType","parseType","getGeneConfigFromOptions","parseGetterConfig","config","isFieldIncluded","fieldKey","check","filters","keyOrRegex","extraExclude","timestamp","exclude","createTypeDefLines","typeDefLines","varName"],"mappings":"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"}