Gatsby struggles with generating Contentful pages using TypeScript

I have been working on creating dynamic pages with Contentful in Gatsby + Typescript. While I am able to fetch data successfully using GraphQL in a browser, I encounter issues when trying to fetch data in gatsby-node.ts. The pages seem to be generated partially and an error message pops up:

ERROR #12100 API.TYPESCRIPT.TYPEGEN

An error occurred while attempting to generate TypeScript types from the GraphQL queries:

Error: GraphQL Document Validation failed with 1 errors;   Error 0: This anonymous operation must be the only defined operation.
at /home/ugnius/GIT/New-webpage/gatsby-node.ts:1:1

For more information about this error, you can refer to our documentation page:

failed Generating GraphQL and TypeScript types - 0.109s

gatsby-node.ts

import type { GatsbyNode } from 'gatsby';
import * as path from 'path';

export const createPages: GatsbyNode['createPages'] = async ({ graphql, actions }) => {
  const { createPage } = actions;

  const request = await graphql<Queries.Query>(`
    {
      allContentfulInsight {
        edges {
          node {
            title
            slug
          }
        }
      }
    }
  `);

  const insightTemplate = path.resolve('./src/templates/Insight.tsx');
  const insights = request?.data?.allContentfulInsight.edges;

  insights?.forEach((insight, index) => {
    createPage({
      path: `insights/${insight.node.slug}`,
      component: insightTemplate,
      context: {
        slug: insight.node.slug,
      },
    });
  });
};

src/templates/Insight.tsx

import * as React from 'react';
import { graphql } from 'gatsby';

const InsightTemplate: React.FC<Queries.InsightBySlugQuery> = (data) => {
  const title = data?.contentfulInsight?.title; // => undefined
  console.log(data); // prints correct data from Contentful but it is undefined in code

  return (
    <>
      <h1>{title}</h1>
    </>
  );
};

export default InsightTemplate;

export const query = graphql`
  query InsightBySlug($slug: String!) {
    site {
      siteMetadata {
        title
      }
    }
    contentfulInsight(slug: { eq: $slug }) {
      title
      content {
        raw
      }
    }
  }
`;

gatsby-types.dts

declare namespace Queries {
  // ...
  type Query = {
    readonly allContentfulInsight: ContentfulInsightConnection;
    // ...
  };
  // ...
  type ContentfulInsightConnection = {
    readonly edges: ReadonlyArray<ContentfulInsightEdge>;
    // ...
  };
  // ...
  type ContentfulInsightEdge = {
    readonly node: ContentfulInsight;
    // ...
  };
  // ...
  type ContentfulInsight = ContentfulEntry & ContentfulReference & Node & {
    readonly slug: Maybe<Scalars['String']>;
    readonly title: Maybe<Scalars['String']>;
    readonly content: Maybe<ContentfulInsightContent>;
    // ...
  };
  // ...
  type InsightBySlugQueryVariables = Exact<{
    slug: Scalars['String'];
  }>;

  type InsightBySlugQuery = {
    readonly site: { readonly siteMetadata: { readonly title: string | null } | null } | null;
    readonly contentfulInsight: {
      readonly title: string | null;
      readonly content: { readonly raw: string | null } | null;
    } | null;
  };
}

What could possibly be causing the issue in my configuration?

Answer №1

To resolve the issue with

ERROR #12100 API.TYPESCRIPT.TYPEGEN
, make sure to update the GraphQL query in gatsby-node.ts as follows:

const request = await graphql<Queries.Query>(`
  {
    allContentfulInsight {
      edges {
        node {
          title
          slug
        }
      }
    }
  }
`);

Additionally, for fixing Insight.tsx, you must correctly define the template props:

import * as React from 'react';
import { graphql } from 'gatsby';

interface InsightTemplateProps {
  data: {
    site: {
      siteMetadata: { title: string };
    };
    contentfulInsight: {
      title: string;
      content: { raw: string };
    };
  };
}

const InsightTemplate: React.FC<InsightTemplateProps> = ({ data }) => {
  const title = data.contentfulInsight.title;

  return (
    <>
      <h1>{title}</h1>
    </>
  );
};
export default InsightTemplate;

export const query = graphql`
  query InsightBySlug($slug: String!) {
    site {
      siteMetadata {
        title
      }
    }
    contentfulInsight(slug: { eq: $slug }) {
      title
      content {
        raw
      }
    }
  }
`;

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Different categories of "areas" found in TypeScript within Visual Studio 2013

In C#, we often use "regions," but unfortunately that feature is missing in TypeScript. Is there a way to group code sections in TypeScript? I came across this article on Stack Overflow discussing the absence of regions in TypeScript. I'm curious if ...

Tips for developing a strongly-typed generic function that works seamlessly with redux slices and their corresponding actions

Currently, I am working with @reduxjs/toolkit and aiming to develop a function that can easily create a slice with default reducers. Although my current implementation is functional, it lacks strong typing. Is there a way to design a function in such a man ...

Restrict the properties of an object to match the properties of a different object

I am currently developing an Object patching utility function with the following code snippet class Test{ a:number; b:number; } var c:Test={a:0,b:1} function patchable<T>(obj:T){ return { patch:function<K>(prop:K){ return patc ...

Failure of VSCode breakpoints to function properly with TypeScript npm linked package

I am developing a Next.js app using TypeScript and my .tsconfig file includes the following configurations: { "compilerOptions": { "baseUrl": "src", "experimentalDecorators": true, "target": & ...

What is the correct way to specify the type in my functional component?

I was trying to define the type in my component in a different way, I know it can be done using classes but is there a way to achieve this with functional components without exporting the interface? Despite my extensive research, I couldn't find any r ...

Enhance Component Reusability in React by Utilizing Typescript

As I embark on developing a React application, my primary goal is to keep my code DRY. This project marks my first experience with Typescript, and I am grappling with the challenge of ensuring reusability in my components where JSX remains consistent acros ...

Steer clear from using the implicit 'any' type while utilizing Object.keys in Typescript

I have a unique situation where I need to loop over an Object while maintaining their type without encountering the error "Element implicitly has an 'any' type because 'ContactList' has no index signature". Despite extensive discussion ...

Is it possible to utilize Typescript and Browserify in tandem?

As I explore the compatibility of TypeScript and Browserify, one perplexing aspect stands out - they both utilize 'require' but for different purposes. TypeScript uses 'require' to import other TS modules, while Browserify employs it to ...

What are some techniques for streamlining this code with Typescript?

I am currently working with the following code snippet: let doNavigate = this.currentScreen === removedFqn; if (doNavigate) { location.reload(); } Does anyone have any suggestions on how I can simplify this code using Typescript? ...

Incorporate Canvg version 4 into a TypeScript project

I am currently facing an issue with an older TypeScript project that has the following tsconfig setup: { "compilerOptions": { "baseUrl": "./src", "outDir": "build/dist", "module": &q ...

What is the proper way to specify the interface as Dispatch<Action>?

My goal is to create an interface with the dispatch function without using Redux. interface DispatchProps { dispatch: (action: { type: string }) => void; } export function addTwoToNumber({ dispatch }: DispatchProps) { dispatch({ type: '@addTwo ...

Extract and preserve elements from an ordered array by segregating them into separate arrays of objects using Angular 8

I have an array called arrayReceived containing 15 objects. My goal is to sort and store the first 6 objects with the lowest amount value in a new array called arraySorted. These objects are sorted based on their amount parameter. There may be multiple obj ...

Issue: Troubleshooting data serialization process using getStaticProps in Next.js

I attempted to retrieve data from an API, but unfortunately encountered the following error: Server Error Error: Issue with serializing .results returned from getServerSideProps in "/". Reason: JSON serialization does not support undefin ...

Changing the button class during an event in Angular 4

In the process of creating an MCQ test, I am looking to implement a feature where selected button options are highlighted in green upon clicking. While I have successfully implemented this feature using Angular 1, I am facing challenges in converting it to ...

Tips for simulating behavior in express using Typescript and the Mocha library

Help with mocking 'Request' in Mocha using express with Typescript needed! Here is the current approach: describe("Authorization middleware", () => { it("Fails when no authorization header", () => { const req = { ...

Dispatching an asynchronous function error in React with TypeScript and Redux - the parameter type is not assignable to AnyAction

Currently, I am in the process of developing a web application that utilizes Firebase as its database, along with Redux and TypeScript for state management. Within my code, I have a dispatch function nested inside a callback function like so: export const ...

Several mat-radio-button options chosen within mat-radio-group

`<mat-radio-group [ngClass]="cssForGroup" name="test"> <mat-radio-button *ngFor="let option of options | filter:searchText" class="cssForRow" [value]="option" ...

How come TypeScript tuples support the array.push method?

In the TypeScript code snippet below, I have specified the role to be of Tuple type, meaning only 2 values of a specified type should be allowed in the role array. Despite this, I am still able to push a new item into the array. Why is the TS compiler not ...

I'm having trouble establishing a connection with the Appwrite platform

Encountered an issue while trying to connect to appwrite. The specific error message is: Uncaught (in promise) TypeError: Failed to construct 'URL': Invalid URL at Account.<anonymous> (appwrite.js?v=d683b3eb:932:19) at Generator.nex ...

Generating step definitions files automatically in cucumber javascript - How is it done?

Is there a way to automatically create step definition files from feature files? I came across a solution for .Net - the plugin called specflow for Visual Studio (check out the "Generating Step Definitions" section here). Is there something similar avail ...