What is the best approach to implement server-side rendering in Next.js while utilizing Apollo React hooks for fetching data from the backend?

I have a Next.js project that is utilizing Apollo GraphQL to retrieve data from the backend. My goal is to render the page using server-side rendering. However, I am encountering an obstacle as the React hooks provided by GraphQL Apollo prevent me from calling the backend within the getServerSideProps function.

How can I overcome this challenge?

import * as React from "react";
import { useExampleQuery } from "graphql/types";

export const getServerSideProps = async ({ params }) => {
  // Here we should probably call graphql function that is now called inside Page
  return { props: { hash: params.hash } };
};

const Page = ({ hash }) => {
  /* 
    I am currently calling my graphql query here using apollo react hooks, 
    that are generated inside graphql/types using @graphql-codegen (typescript)
  */
  const { data, loading } = useExampleQuery({
    variables: {
      hash: hash,
    },
  });

  return loading ? <p>{loading}</p> : <p>{data.example.text}</p>;
};

export default Page;

Answer №1

If you are using the server-side function getServerSideProps, calling apollo query hooks inside it is not possible.

One alternative is to utilize the query method of the apollo client instance.

You can refer to the code example provided below.

import { gql } from '@apollo/client';
import apolloClient from '/path/to/graphql/server/client';

// Example Query
const EXAMPLE_QUERY = gql`
  query EXAMPLE_QUERY($hash: String!) {
    exampleQuery(hash: $hash) {
      ...
    }
  }
`;

export const getServerSideProps = async ({ params }) => {
  const { data } = await apolloClient.query({
    query: EXAMPLE_QUERY,
    variables: { hash: params.hash },
  });

  return {
    props: {
      hash: params.hash,
      data,
    },
  };
};

In case importing your apollo client server instance seems complicated, you have the option to use the graphql-request package for handling graphql requests with a given URL.

Here's an example to demonstrate this approach.

import { GraphQLClient } from "graphql-request";

// Replace GRAPHQL_URL below with the actual URL
const client = new GraphQLClient(<GRAPHQL_URL>);

export const getServerSideProps = async ({ params }) => {

  const { data } = await client.request(EXAMPLE_QUERY, {
      hash: params.hash 
  });

  return {
    props: {
      hash: params.hash,
      data,
    },
  };
};

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

When the Angular Reactive form control does not show any errors, it is designated as ng-invalid

Currently, I am working on an (Angular 10) reactive form that includes multiple dynamically-created input components within an ngFor loop. Here is an example of one of these input components: <div [id]="this.getDivElementId()" class="text ...

Error: Unable to locate module: Unable to resolve 'next/web-vitals'

I keep encountering the following error message: Module not found: Can't resolve 'next/web-vitals' I am interested in utilizing the **useReportWebVitals** feature from next/web-vitals. For more information, please visit: Optimizing: Analyt ...

Implementing delayed loading of Angular modules without relying on the route prefix

In my application, I am using lazy loading to load a module called lazy. The module is lazily loaded like this: { path:'lazy', loadChildren: './lazy/lazy.module#LazyModule' } Within the lazy module, there are several routes def ...

Exploring the retrieval of specific values through bitwise operations in Angular

Currently, I am facing a challenge in retrieving a value that I had initially saved in the database as a sum of bits. My development work is based on Angular 9 using Typescript. I have successfully managed to store the sum of bits in the database. Now, I ...

Imitate a required component in a service

I am currently facing an issue with mocking a dependency in a service. I am not sure what is causing the problem. It's not the most ideal class to test, but I am mainly focused on code coverage. Below is the code for the service: @Injectable() export ...

The code compilation of Typescript in a Dockerfile is not functioning as expected due to the error "Name 'process' cannot be found."

Here's the Dockerfile I'm working with: FROM node:latest WORKDIR /usr/src/app ENV NODE_ENV=production COPY package*.json . RUN npm install && npm i -g typescript COPY . . RUN tsc CMD [ "node", "./dist/index.js&qu ...

Tips for building an extensive checklist page using React

Looking to create a webpage featuring an extensive checklist of 100 items that can be retrieved from and updated in a Firestore document. Here is my current strategy: // Here, we define states that store the checkbox values const [checkA, setCheckA] = u ...

How can I generate codegen types using typeDefs?

I have been exploring the capabilities of graphql-codegen to automatically generate TypeScript types from my GraphQL type definitions. However, I encountered an issue where I received the following error message: Failed to load schema from code file " ...

Set up a SQS queue to receive notifications from an SNS topic located in another AWS account by using AWS CDK in TypeScript

Looking to establish a connection between an SQS queue and an SNS topic located in a different account using CDK (TypeScript). Presented below is the code snippet (contained within a stack) that I believe should facilitate this integration. However, I have ...

What is the mechanism for accessing the state of React-Hot-Toast through an export statement?

How does react-hot-toast enable changing its state from other components simply by exporting the components in react-hot-toast/src/index.ts using: export default toast; Example Usage in Nextjs14: =Layout.tsx: import { Toaster } from "react-hot-toast ...

The issue with Angular 2's router.navigate not functioning as expected within a nested JavaScript function

Consider the app module: import { NgModule } from '@angular/core'; import { BrowserModule } from '@angular/platform-browser'; import { FormsModule } from '@angular/forms'; import { RouterModule } from '@angul ...

Expanding the capabilities of generic functions in TypeScript using type variables

When working with generics in TypeScript, it is often beneficial for a function that accepts generically-typed arguments to have knowledge of the type. There exists a standard approach to achieve this using named functions: interface TestInterface<T> ...

To avoid TS2556 error in TypeScript, make sure that a spread argument is either in a tuple type or is passed to a rest parameter, especially when using

So I'm working with this function: export default function getObjectFromTwoArrays(keyArr: Array<any>, valueArr: Array<any>) { // Beginning point: // [key1,key2,key3], // [value1,value2,value3] // // End point: { // key1: val ...

What is the method for retrieving properties from a generic in typescript?

In my code snippet, I am dealing with a generic type variable called data and I am looking for a way to access the values of its properties. The method hasOwnProperty isn't effective in this case due to the generic nature of the data. const data: T = ...

Having trouble getting Jest to manually mock in Nestjs?

When setting up a mock service like this: // /catalogue/__mock__/catalogue.service.ts export const CatalogueService = jest.fn().mockImplementation(() => { return { filterRulesFor: jest.fn().mockImplementation((role: Roles): Rule[] => rules.filt ...

The element 'flat' is not found within the specified type

My challenge involves utilizing the flat() method in a TypeScript script. In my tsconfig.json file, I have set the target to es2017 and defined an interface for the input variable. However, I keep encountering this error message: Property 'flat' ...

Typescript in React is throwing an error that says you cannot destructure the property 'colored' from the 'boxShadows' object because it is undefined

After downloading the material dashboard react theme from an open source GitHub project, I tried to convert the project into Typescript (React + Typescript). However, I encountered the following error (See Attached Image) https://i.stack.imgur.com/YZKpK.p ...

What is the best way to specify a type for an object without altering its underlying implicit type?

Suppose we have a scenario where an interface/type is defined as follows: interface ITest { abc: string[] } and then it is assigned to an object like this: const obj: ITest = { abc: ["x", "y", "z"] } We then attempt to create a type based on the valu ...

Using React.ReactNode as an argument in Storybook

This is a unique button component type that I have created import React from 'react' export type ButtonProps = { label: string; color?:'primary' | 'secondary' | 'tertiary'; size?:'mobile' | 'tabl ...

Is it possible to import in TypeScript using only the declaration statement?

Is there a way to use a node module in TypeScript without explicitly importing it after compilation? For example: I have a global variable declared in a file named intellisense.ts where I have: import * as fs from 'fs'; Then in another file, ...