Refactoring gatsby-node File into separate files not working
Asked Answered
C

1

7

Trying to refactor my gatsby-node file, by outsourcing a bit of code. Right now trying to do this in my gatsby-node:

const createBlogPostPages = require("./gatsby-utils/createBlogPostPages");

exports.createPages = async ({ actions, graphql, reporter }) => {
  //...some code
  await createBlogPostPages({ actions, graphql, reporter });
  //...some code
}

and my createBlogPostPages, which is in a different file, looks like so:

const path = require("path");

module.exports = async function({ actions, graphql, reporter }) {
  const { createPage } = actions;

  const blogArticles = await graphql(`
    {
      allMdx(filter: { fileAbsolutePath: { regex: "/content/blog/.*/" } }) {
        edges {
          node {
            id
            fileAbsolutePath
            fields {
              slug
            }
            frontmatter {
              title
              tags
              date
              tagline
            }
          }
        }
      }
    }
  `);

  blogArticles.data.allMdx.edges.forEach(({ node }) => {
    let imageFileName = ... //some stuff

    createPage({
      path: `${node.fields.slug}`,
      component: path.resolve(`./src/templates/blog-post.js`),
      context: {
        slug: `${node.fields.slug}`,
        id: node.id,
        imageFileName: imageFileName
      }
    });
  });
};

All of this works when its directly in gatsby-node. However, having moved stuff, I now get:

"gatsby-node.js" threw an error while running the createPages lifecycle:

blogArticles is not defined

ReferenceError: blogArticles is not defined

  • gatsby-node.js:177 Object.exports.createPages /Users/kohlisch/blogproject/gatsby-node.js:177:19

  • next_tick.js:68 process._tickCallback internal/process/next_tick.js:68:7

So it looks like it's not waiting for the graphql query to resolve? Or what might this be? I just basically want to move a few things out of my gatsby-node file, into separate functions, so that its not so cluttered. Is this not possible?

Crevasse answered 14/2, 2020 at 11:2 Comment(0)
B
4

There are two rules you need to follow when importing in gatsby-node.js:

1. Use node.js require syntax.

./src/components/util/gatsby-node-functions

const importedFunction = () => {
  return Date.now();
};

module.exports.importedFunction = importedFunction;

gatsby-node.js

const { importedFunction } = require(`./src/components/util/gatsby-node-functions`);

// ...
// Use your imported functions
console.log(importedFunction());

Reference: Gatsby repo issue, also incluces hack how to use ES6 import statement if you want to add complexity just for using an import statement.

2. Do not pass gatsby-node.js specific attributes to your imported functions

If you attempt to outsource for example, your createPages function, actions will be undefined:

const importedFunction = (actions, node) => {
    const {createPage} = actions; // actions is undefined
    createPage({
      path: `${node.fields.slug}`,
      component: path.resolve(`./src/templates/blog-post.js`),
      context: {
        slug: `${node.fields.slug}`,
        id: node.id,
      }
    });
};

module.exports.importedFunction = importedFunction;

Feel free to speculate why you cannot pass the attributes. The Gatsby documentation mentions "Redux" for handling state. Maybe Redux does not supply state outside your gatsby-node.js. Correct me if I'm wrong

Braunite answered 15/2, 2020 at 2:10 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.