Skip to content

Commit e7fc88b

Browse files
authored
fix(gatsby): Throw Typegen errors & add IGatsbyImageData to output (#35683)
1 parent d85fd9e commit e7fc88b

File tree

18 files changed

+77
-26
lines changed

18 files changed

+77
-26
lines changed

packages/gatsby-cli/src/structured-errors/error-map.ts

+15-5
Original file line numberDiff line numberDiff line change
@@ -262,21 +262,21 @@ const errors = {
262262
${context.sourceMessage}
263263
264264
This can happen if you e.g. accidentally added { } to the field "${context.fieldName}". If you didn't expect "${context.fieldName}" to be of type "${context.fieldType}" make sure that your input source and/or plugin is correct.
265-
However, if you expect "value" to exist, the field might be accessible in another subfield. Please try your query in GraphiQL and use the GraphiQL explorer to see which fields you can query and what shape they have.
265+
However, if you expect "value" to exist, the field might be accessible in another subfield. Please try your query in GraphiQL.
266266
267-
It is recommended to explicitly type your GraphQL schema if you want to use optional fields. This way you don't have to add the mentioned
268-
"dummy content". Visit our docs to learn how you can define the schema for "${context.type}":
269-
https://www.gatsbyjs.com/docs/reference/graphql-data-layer/schema-customization#creating-type-definitions`,
267+
It is recommended to explicitly type your GraphQL schema if you want to use optional fields.`,
270268
type: Type.GRAPHQL,
271269
level: Level.ERROR,
272270
category: ErrorCategory.USER,
271+
docsUrl: `https://gatsby.dev/creating-type-definitions`,
273272
},
274273
"85923": {
275274
text: (context): string =>
276-
`There was an error in your GraphQL query:\n\n${context.sourceMessage}\n\nIf you don't expect "${context.field}" to exist on the type "${context.type}" it is most likely a typo.\nHowever, if you expect "${context.field}" to exist there are a couple of solutions to common problems:\n\n- If you added a new data source and/or changed something inside gatsby-node.js/gatsby-config.js, please try a restart of your development server\n- The field might be accessible in another subfield, please try your query in GraphiQL and use the GraphiQL explorer to see which fields you can query and what shape they have\n- You want to optionally use your field "${context.field}" and right now it is not used anywhere. Therefore Gatsby can't infer the type and add it to the GraphQL schema. A quick fix is to add at least one entry with that field ("dummy content")\n\nIt is recommended to explicitly type your GraphQL schema if you want to use optional fields. This way you don't have to add the mentioned "dummy content". Visit our docs to learn how you can define the schema for "${context.type}":\nhttps://www.gatsbyjs.com/docs/reference/graphql-data-layer/schema-customization#creating-type-definitions`,
275+
`There was an error in your GraphQL query:\n\n${context.sourceMessage}\n\nIf you don't expect "${context.field}" to exist on the type "${context.type}" it is most likely a typo. However, if you expect "${context.field}" to exist there are a couple of solutions to common problems:\n\n- If you added a new data source and/or changed something inside gatsby-node/gatsby-config, please try a restart of your development server.\n- You want to optionally use your field "${context.field}" and right now it is not used anywhere.\n\nIt is recommended to explicitly type your GraphQL schema if you want to use optional fields.`,
277276
type: Type.GRAPHQL,
278277
level: Level.ERROR,
279278
category: ErrorCategory.USER,
279+
docsUrl: `https://gatsby.dev/creating-type-definitions`,
280280
},
281281
"85924": {
282282
text: (context): string =>
@@ -713,6 +713,16 @@ const errors = {
713713
type: Type.COMPILATION,
714714
category: ErrorCategory.USER,
715715
},
716+
"12100": {
717+
text: (
718+
context
719+
): string => `There was an error while trying to generate TS types from your GraphQL queries:
720+
721+
${context.sourceMessage}`,
722+
level: Level.ERROR,
723+
type: Type.GRAPHQL,
724+
category: ErrorCategory.USER,
725+
},
716726
}
717727

718728
export type ErrorId = string | keyof typeof errors

packages/gatsby-plugin-image/package.json

+1
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,7 @@
8383
"common-tags": "^1.8.2",
8484
"fs-extra": "^10.1.0",
8585
"gatsby-core-utils": "^3.15.0-next.1",
86+
"gatsby-plugin-utils": "^3.9.0-next.2",
8687
"objectFitPolyfill": "^2.3.5",
8788
"prop-types": "^15.8.1"
8889
},

packages/gatsby-plugin-image/src/resolver-utils.ts

+3-2
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import type {
55
ObjectTypeComposerFieldConfigAsObjectDefinition,
66
ObjectTypeComposerArgumentConfigMapDefinition,
77
} from "graphql-compose"
8+
import { hasFeature } from "gatsby-plugin-utils"
89
import type { ISharpGatsbyImageArgs, IImageSizeArgs } from "./image-utils"
910

1011
export const ImageFormatType: EnumTypeComposerAsObjectDefinition = {
@@ -74,7 +75,7 @@ export function getGatsbyImageResolver<TSource, TContext, TArgs>(
7475
IGatsbyImageResolverArgs & TArgs
7576
> {
7677
return {
77-
type: `JSON!`,
78+
type: hasFeature(`graphql-typegen`) ? `GatsbyImageData!` : `JSON!`,
7879
args: {
7980
layout: {
8081
type: ImageLayoutType.name,
@@ -166,7 +167,7 @@ export function getGatsbyImageFieldConfig<TSource, TContext, TArgs>(
166167
IGatsbyImageFieldArgs & TArgs
167168
> {
168169
return {
169-
type: `JSON!`,
170+
type: hasFeature(`graphql-typegen`) ? `GatsbyImageData!` : `JSON!`,
170171
args: {
171172
layout: {
172173
type: ImageLayoutType.name,

packages/gatsby-plugin-utils/src/polyfill-remote-file/graphql/gatsby-image-resolver.ts

+2-1
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { hasFeature } from "../../has-feature"
12
import { generateImageUrl } from "../utils/url-generator"
23
import { getImageFormatFromMimeType } from "../utils/mime-type-helpers"
34
import { stripIndent } from "../utils/strip-indent"
@@ -260,7 +261,7 @@ export function generateGatsbyImageFieldConfig(
260261
IGatsbyImageDataArgs
261262
> {
262263
return {
263-
type: `JSON`,
264+
type: hasFeature(`graphql-typegen`) ? `GatsbyImageData!` : `JSON`,
264265
description: `Data used in the <GatsbyImage /> component. See https://gatsby.dev/img for more info.`,
265266
args: {
266267
layout: {

packages/gatsby-plugin-utils/src/types.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
* These types are duplicated from packages/gatsby/src/bootstrap/load-plugins/types.ts
44
* If you edit this file, make sure to edit that file too!!!
55
* They are duplicate to avoid a circular dependency between gatsby-plugin-utils <=> gatsby <=> gatsby-plugin-utils
6-
* See gatsbyjs/gatsby#27578 and ping @laurieontech or @mxstbr if you have any questions
6+
* See gatsbyjs/gatsby#27578
77
*/
88

99
export interface IRawSiteConfig {

packages/gatsby-transformer-sharp/package.json

+1
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
"bluebird": "^3.7.2",
1313
"common-tags": "^1.8.2",
1414
"fs-extra": "^10.1.0",
15+
"gatsby-plugin-utils": "^3.9.0-next.2",
1516
"probe-image-size": "^7.2.3",
1617
"semver": "^7.3.7",
1718
"sharp": "^0.30.3"

packages/gatsby-transformer-sharp/src/customize-schema.js

+4-1
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ const {
1717
traceSVG,
1818
generateImageData,
1919
} = require(`gatsby-plugin-sharp`)
20+
const { hasFeature } = require(`gatsby-plugin-utils`)
2021

2122
const sharp = require(`./safe-sharp`)
2223
const fs = require(`fs-extra`)
@@ -407,7 +408,9 @@ const imageNodeType = ({
407408
cache,
408409
}) => {
409410
return {
410-
type: new GraphQLNonNull(GraphQLJSON),
411+
type: hasFeature(`graphql-typegen`)
412+
? `GatsbyImageData!`
413+
: new GraphQLNonNull(GraphQLJSON),
411414
args: {
412415
layout: {
413416
type: ImageLayoutType,

packages/gatsby/index.d.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ import { GraphQLOutputType } from "graphql"
1717
import { PluginOptionsSchemaJoi, ObjectSchema } from "gatsby-plugin-utils"
1818
import { IncomingMessage, ServerResponse } from "http"
1919

20-
export type AvailableFeatures = "image-cdn"
20+
export type AvailableFeatures = "image-cdn" | "graphql-typegen"
2121

2222
export {
2323
default as Link,

packages/gatsby/scripts/__tests__/api.js

+1
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ it("generates the expected api output", done => {
3232
},
3333
"features": Array [
3434
"image-cdn",
35+
"graphql-typegen",
3536
],
3637
"node": Object {
3738
"createPages": Object {},

packages/gatsby/scripts/output-api-file.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ async function outputFile() {
4141
}, {})
4242

4343
/** @type {Array<import("../index").AvailableFeatures>} */
44-
output.features = ["image-cdn"];
44+
output.features = ["image-cdn", "graphql-typegen"];
4545

4646
return fs.writeFile(
4747
path.resolve(OUTPUT_FILE_NAME),

packages/gatsby/src/schema/__tests__/__snapshots__/print.js.snap

+3-3
Original file line numberDiff line numberDiff line change
@@ -193,7 +193,7 @@ interface RemoteFile {
193193
fit: RemoteFileFit = COVER
194194
cropFocus: [RemoteFileCropFocus]
195195
quality: Int = 75
196-
): JSON
196+
): GatsbyImageData!
197197
}
198198
199199
type File implements Node @dontInfer {
@@ -582,7 +582,7 @@ interface RemoteFile {
582582
fit: RemoteFileFit = COVER
583583
cropFocus: [RemoteFileCropFocus]
584584
quality: Int = 75
585-
): JSON
585+
): GatsbyImageData!
586586
}
587587
588588
type File implements Node @dontInfer {
@@ -981,7 +981,7 @@ interface RemoteFile {
981981
fit: RemoteFileFit = COVER
982982
cropFocus: [RemoteFileCropFocus]
983983
quality: Int = 75
984-
): JSON
984+
): GatsbyImageData!
985985
}
986986
987987
type File implements Node @dontInfer {

packages/gatsby/src/schema/schema-composer.ts

+2
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { SchemaComposer, GraphQLJSON } from "graphql-compose"
22
import { addDirectives, GraphQLFieldExtensionDefinition } from "./extensions"
33
import { GraphQLDate } from "./types/date"
44
import { IGatsbyResolverContext } from "./type-definitions"
5+
import { GatsbyImageDataScalar } from "./types/media"
56
import { getNodeInterface } from "./types/node-interface"
67
import { getOrCreateRemoteFileInterface } from "./types/remote-file-interface"
78

@@ -19,6 +20,7 @@ export const createSchemaComposer = <TSource, TArgs>({
1920

2021
schemaComposer.add(GraphQLDate)
2122
schemaComposer.add(GraphQLJSON)
23+
schemaComposer.add(GatsbyImageDataScalar)
2224
addDirectives({ schemaComposer, fieldExtensions })
2325
return schemaComposer
2426
}

packages/gatsby/src/schema/types/built-in-types.ts

+1
Original file line numberDiff line numberDiff line change
@@ -156,6 +156,7 @@ export const builtInScalarTypeNames = [
156156
`Int`,
157157
`JSON`,
158158
`String`,
159+
`GatsbyImageData`,
159160
]
160161

161162
export const internalTypeNames = [
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
import { GraphQLScalarType } from "graphql"
2+
3+
export const GatsbyImageDataScalar = new GraphQLScalarType({
4+
name: `GatsbyImageData`,
5+
})

packages/gatsby/src/services/graphql-typegen.ts

+12-3
Original file line numberDiff line numberDiff line change
@@ -30,9 +30,18 @@ export async function graphQLTypegen({
3030

3131
const { schema, definitions } = store.getState()
3232

33-
await writeGraphQLSchema(directory, schema)
34-
await writeGraphQLFragments(directory, definitions)
35-
await writeTypeScriptTypes(directory, schema, definitions)
33+
try {
34+
await writeGraphQLSchema(directory, schema)
35+
await writeGraphQLFragments(directory, definitions)
36+
await writeTypeScriptTypes(directory, schema, definitions)
37+
} catch (err) {
38+
activity.panicOnBuild({
39+
id: `12100`,
40+
context: {
41+
sourceMessage: err,
42+
},
43+
})
44+
}
3645

3746
activity.end()
3847
}

packages/gatsby/src/state-machines/develop/actions.ts

+21-3
Original file line numberDiff line numberDiff line change
@@ -207,7 +207,16 @@ export const schemaTypegen: ActionFunction<
207207

208208
context.reporter!.verbose(`Re-Generating schema.graphql`)
209209

210-
await writeGraphQLSchema(directory, schema)
210+
try {
211+
await writeGraphQLSchema(directory, schema)
212+
} catch (err) {
213+
context.reporter!.panicOnBuild({
214+
id: `12100`,
215+
context: {
216+
sourceMessage: err,
217+
},
218+
})
219+
}
211220
}
212221

213222
export const definitionsTypegen: ActionFunction<
@@ -220,8 +229,17 @@ export const definitionsTypegen: ActionFunction<
220229

221230
context.reporter!.verbose(`Re-Generating fragments.graphql & TS Types`)
222231

223-
await writeGraphQLFragments(directory, definitions)
224-
await writeTypeScriptTypes(directory, schema, definitions)
232+
try {
233+
await writeGraphQLFragments(directory, definitions)
234+
await writeTypeScriptTypes(directory, schema, definitions)
235+
} catch (err) {
236+
context.reporter!.panicOnBuild({
237+
id: `12100`,
238+
context: {
239+
sourceMessage: err,
240+
},
241+
})
242+
}
225243
}
226244

227245
export const buildActions: ActionFunctionMap<IBuildContext, AnyEventObject> = {

packages/gatsby/src/utils/flags.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -240,8 +240,8 @@ const activeFlags: Array<IFlag> = [
240240
env: `GATSBY_GRAPHQL_TYPEGEN`,
241241
command: `develop`,
242242
telemetryId: `GraphQLTypegen`,
243-
description: `A built-in way for automatic TypeScript type generation and better GraphQL IntelliSense. See https://github.com/gatsbyjs/gatsby/discussions/35420 for more details.`,
244-
experimental: true,
243+
description: `More easily incorporate content into your pages through automatic TypeScript type generation and better GraphQL IntelliSense. See https://github.com/gatsbyjs/gatsby/discussions/35420 for more details.`,
244+
experimental: false,
245245
noCI: true,
246246
testFitness: (): fitnessEnum => true,
247247
},

packages/gatsby/src/utils/graphql-typegen/ts-codegen.ts

+1-3
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ const DEFAULT_TYPESCRIPT_CONFIG: Readonly<TypeScriptPluginConfig> = {
2929
scalars: {
3030
Date: `string`,
3131
JSON: `Record<string, unknown>`,
32+
GatsbyImageData: `import('gatsby-plugin-image').IGatsbyImageData`,
3233
},
3334
// import type {} syntax is nicer
3435
useTypeImports: true,
@@ -121,8 +122,6 @@ export async function writeTypeScriptTypes(
121122
}
122123
})
123124

124-
const isVerbose = process.env.gatsby_log_level === `verbose`
125-
126125
const codegenOptions: Omit<Types.GenerateOptions, "plugins" | "pluginMap"> = {
127126
// @ts-ignore - Incorrect types
128127
schema: undefined,
@@ -139,7 +138,6 @@ export async function writeTypeScriptTypes(
139138
skipTypename: true,
140139
flattenGeneratedTypes: true,
141140
},
142-
skipDocumentsValidation: !isVerbose,
143141
}
144142

145143
const result = await codegen({

0 commit comments

Comments
 (0)