Skip to content

Guide: Create a new content type

Mario Vercellotti edited this page May 2, 2024 · 4 revisions

This guide shows the steps needed to add a new content type to Drupal, and render its content in the frontend.

Setting up the content type in Drupal

  1. Create a new content type, add the fields. In this case we have called the content type "Test content" and we will have the body field, and a textfield called Testfield: image
  2. In order to use the preview functionality, you have to add the new content type to the next-drupal setup:

image 3. configure the graphql_compose schema for the new content type, configure as follows: (note that we are enabling all checkboxes) image

  1. Add a test node of your new content type: image

Frontend changes needed

  1. Since we have modified the graphql schema, we now need to run lando npm run grapqhl-codegen to update the type definitions
  2. Edit next/lib/graphql/fragments/nodes.ts and add a new fragment for this node type:
export const FRAGMENT_NODE_TESTCONTENT = graphql(`
  fragment FragmentNodeTestcontent on NodeTestContent {
    body {
      ...FragmentTextSummary
    }
    testfield
  }
`);

then, add this fragment to the existing FragmentNodeUnion fragment, together with the other existing fragments:

export const FRAGMENT_NODE_UNION = graphql(`
  fragment FragmentNodeUnion on NodeInterface {
    [...]
    ...FragmentNodeArticle
    ...FragmentNodeFrontpage
    ...FragmentNodePage
    ...FragmentNodeTestcontent // <- Our new fragment
  1. Now, we will need to create a type for the new content type, by adding this to next/types/graphql.ts:
/**
 * From TypedRouteEntity, create a type for Test Content data
 */
export type TestContentType = Extract<
  TypedRouteEntity,
  { __typename: "NodeTestContent" }
>;
  1. Add a new component, by creating a file: next/components/node/node--test-content.tsx
import { FormattedText } from "@/components/formatted-text";
import type { TestContentType } from "@/types/graphql";

export function NodeTestContent({
  testContent,
}: {
  testContent: TestContentType;
}) {
  return (
    <div className="grid gap-4">
      <h2>{testContent.title}</h2>
      <FormattedText html={testContent.body?.processed} />
      {testContent.testfield}
    </div>
  );
}
  1. Modify the existing next/components/node/node--test-content.tsx file, adding a new case for the switch (remember to also import the new component)
import { NodeTestContent } from "@/components/node/node--test-content";
[...]
    case "NodeTestContent": {
      return <NodeTestContent testContent={node} />;
    }