Gatsby: [Storybook] useStaticQuery fetching fails when used inside stories

Created on 29 Jul 2020  Â·  17Comments  Â·  Source: gatsbyjs/gatsby

Description

Fetching data via useStaticQuery within a story causes Storybook to break.

Steps to reproduce

I setup a reproduction repo, based on gatsby-default starter, following the description how to use Storybook with Gatsby.

Reproduction Repo

Expected result

The Story in the repo is supposed to show the queried title "Gatsby Starter Default".

Actual result

Error message:

The result of this StaticQuery could not be fetched.

This is likely a bug in Gatsby and if refreshing the page does not fix it, please open an issue in https://github.com/gatsbyjs/gatsby/issues
Error: The result of this StaticQuery could not be fetched.

This is likely a bug in Gatsby and if refreshing the page does not fix it, please open an issue in https://github.com/gatsbyjs/gatsby/issues
    at useStaticQuery (http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:28626:11)
    at Reproduction (http://localhost:54134/main.846d47b2b5df26ed1d0b.bundle.js:93:75)
    at http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:2952:21
    at http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:4255:16
    at withSubscriptionTracking (http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:4283:16)
    at http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:2952:21
    at http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:4254:14
    at http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:2980:20
    at storyFn (http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:5367:30)
    at oh (http://localhost:54134/vendors~main.846d47b2b5df26ed1d0b.bundle.js:41118:146)

Environment

System:
OS: macOS 10.15.5
CPU: (16) x64 Intel(R) Core(TM) i9-9880H CPU @ 2.30GHz
Shell: 5.7.1 - /bin/zsh
Binaries:
Node: 13.12.0 - /usr/local/bin/node
Yarn: 1.22.4 - /usr/local/bin/yarn
npm: 6.14.4 - /usr/local/bin/npm
Languages:
Python: 2.7.16 - /usr/bin/python
Browsers:
Chrome: 84.0.4147.89
Firefox: 78.0.2
Safari: 13.1.1
npmPackages:
gatsby: ^2.23.12 => 2.24.13
gatsby-image: ^2.4.9 => 2.4.14
gatsby-plugin-manifest: ^2.4.14 => 2.4.21
gatsby-plugin-offline: ^3.2.13 => 3.2.21
gatsby-plugin-react-helmet: ^3.3.6 => 3.3.10
gatsby-plugin-sharp: ^2.6.14 => 2.6.23
gatsby-source-filesystem: ^2.3.14 => 2.3.23
gatsby-transformer-sharp: ^2.5.7 => 2.5.11

StaticQuery bug

Most helpful comment

@blainekasten @sidharthachatterjee

I have the same problem with the latest version of Gatsby.
I did some research and I think the problem comes from:

1. babel-plugin-remove-graphql-queries still defaults to static/d :

Considering this line:
https://github.com/gatsbyjs/gatsby/blob/289c7f8c154a3d764621c39be585cee0da9c9f1c/packages/babel-plugin-remove-graphql-queries/src/index.js#L199

Recent versions of gatsby (after "2.24.6") host the static query data in page-data/sq/d however the latest version of babel-plugin-remove-graphql-queries still defaults to static/d. I suppose this default is used by the Storybook's babel-loader.

2. babel-plugin-remove-graphql-queries doesn't check against NODE_ENV=production anymore

This pull request edits packages/babel-plugin-remove-graphql-queries/src/index.js with the following diff:

-        [`production`, `test`].includes(process.env.NODE_ENV) &&
+        (process.env.NODE_ENV === `test` ||state.opts.stage === `build-html`) &&

Now as most Storybook + Gatsby workspaces are advised by Gatsby docs to run Storybook with NODE_ENV=production and babel-plugin-remove-graphql-queries after the mentioned PR doesn't check against NODE_ENV=production the queries aren't processed anymore.

Here is what I did to confirm that these two changes are the cause of the problem:

  1. Run Storybook with NODE_ENV=test as babel-plugin-remove-graphql-queries still checks against it and processes the queries.
    NODE_ENV=test start-storybook -s public
  2. Copy queries from page-data/sq/d to static/d.

Viola. The components containing the queries are loaded with the needed queries.

All 17 comments

@r3sMetz just skimming through your repository, the issue could lie with how you're handling the queries themselves. For both Storybook and Gatsby to play nice in terms of data, you'll need to mock out the data you need to provide to the components/pages, as technically all the graphql data is being stripped down from execution in the Storybook webpack configuration. Take a look at this to see how you can use the queries with Storybook and Gatsby.

Feel free to provide feedback

Hey, thanks for reviewing my repo! Your repo seems like a cool way too.

My approach worked before, it's just broken atm.
One disadvantage is that it expects Gatsby to be built already. Storybook then scans the public folder for data in the required format. From how i understand it, the queries get removed from Storybook, but the results of data=useStaticQuery(...) get used just like gatsby-data, because the stories folder is inside the src folder.

I need to query data in the gatsby way because i want to use and test things like gatsby-image.
Is there a way to mock gatsby-images for example?

@r3sMetz no problem and storybook in this case will rely on a build to be made beforehand. as it's expecting a output folder to exist, as it's the case with for instance CRA as when you create a new project based on it a public folder already exists.

Regarding your question about the images. I'm not sure, but you might want to do the following:

  • Issue a development build using gatsby develop.
  • Open http://localhost:8000/__graphql to get the graphql IDE.
  • Create the graphql query for the image.
  • Create a story like this, where the taskDatais the result of query you supplied.

See if what i mentioned helps. Or if your're ok waiting a bit longer. I can update the repo towards the end of the week and report back to you.

Sounds good?

Exactly, in my package.json the storybook script looks something like this NODE_ENV=production clean && build && start-storybook

Sounds pretty good, but don't hurry :)

I filed this issue based on a chat inside another useStaticQuery Issue, i got told that the issue with useStaticQuery inside stories will soon be working again.

As a sidenote to the actual issue, @muescha please do not edit other people's comments. If you have new context to add, please add it in a new comment rather than modifying another person's words, out of respect to them. Thank you!

@marcysutton ok. I removed my change (add link to issue comment)
—-

a chat inside another useStaticQuery Issue

The comment is here: https://github.com/gatsbyjs/gatsby/pull/26077#issuecomment-665605068

Any news on this or some temporary solution? I am using the same method with query results pre-build and all stories for components with useStaticQuery are broken for the moment (it worked before just fine). Somehow gatsby version downgrade didn't work 🤔

I use explicit versions for now and a resolutions object inside my package.json.
Maybe this helps you temporarily, here is my package.json:

{
  "name": "gatsby-starter-default",
  "private": true,
  "description": "A simple starter to get up and developing quickly with Gatsby",
  "version": "0.1.0",
  "author": "Kyle Mathews <[email protected]>",
  "dependencies": {
    "@types/faker": "4.1.12",
    "babel-plugin-module-resolver": "4.0.0",
    "dotenv": "^8.2.0",
    "faker": "4.1.0",
    "gatsby": "2.24.3",
    "gatsby-background-image": "1.1.1",
    "gatsby-image": "2.4.13",
    "gatsby-plugin-manifest": "2.4.18",
    "gatsby-plugin-offline": "3.2.18",
    "gatsby-plugin-postcss": "2.3.11",
    "gatsby-plugin-react-helmet": "3.3.10",
    "gatsby-plugin-sharp": "2.6.19",
    "gatsby-plugin-typescript": "2.4.15",
    "gatsby-source-filesystem": "2.3.19",
    "gatsby-transformer-sharp": "2.5.11",
    "npm-run-all": "^4.1.5",
    "prop-types": "15.7.2",
    "react": "16.13.1",
    "react-dom": "16.13.1",
    "react-helmet": "6.1.0",
    "tailwindcss": "1.5.1"
  },
  "devDependencies": {
    "@babel/core": "7.10.5",
    "@storybook/addon-a11y": "5.3.19",
    "@storybook/addon-actions": "5.3.19",
    "@storybook/addon-backgrounds": "5.3.19",
    "@storybook/addon-links": "5.3.19",
    "@storybook/addon-viewport": "5.3.19",
    "@storybook/addons": "5.3.19",
    "@storybook/react": "5.3.19",
    "autoprefixer": "9.8.5",
    "babel-loader": "8.1.0",
    "babel-preset-gatsby": "0.5.2",
    "babel-preset-react-app": "9.1.2",
    "eslint-import-resolver-babel-module": "5.1.2",
    "eslint-plugin-import": "2.22.0",
    "postcss-cli": "7.1.1",
    "postcss-import": "12.0.1",
    "prettier": "1.19.1"
  },
  "keywords": [
    "gatsby"
  ],
  "license": "MIT",
  "scripts": {
    "build": "gatsby build",
    "develop": "gatsby develop",
    "format": "prettier --write \"**/*.{js,jsx,json,md}\"",
    "start": "npm run develop",
    "serve": "gatsby serve",
    "clean": "gatsby clean",
    "test": "echo \"Write tests! -> https://gatsby.dev/unit-testing\" && exit 1",
    "storybook": "NO_PURGE=true run-s clean build start-storybook",
    "start-storybook": "NODE_ENV=production start-storybook -p 6006 -s ./public",
    "build-storybook": "NODE_ENV=production build-storybook -s ./public"
  },
  "repository": {
    "type": "git",
    "url": "https://github.com/gatsbyjs/gatsby-starter-default"
  },
  "bugs": {
    "url": "https://github.com/gatsbyjs/gatsby/issues"
  },
  "resolutions": {
    "babel-plugin-remove-graphql-queries": "2.9.9"
  }
}

Thanks, @smetzdev! This is really working as temp fix.

Solution in short for other Storybook users:

Static query results loading in Gatsby runtime was added in [email protected] and [email protected], so we need to lock previous versions:

"dependencies": {
  "gatsby": "2.24.6"
},
"resolutions": {
  "babel-plugin-remove-graphql-queries": "2.9.14"
}

Important note: resolutions are yarn feature, so it doen't work with npm. But you can just add babel plugin to dependencies list - it's working too.

_But packages install through npm breaks my Storybook in another way (mdx default styling broke, don't ask...), so i changed my package manager anyway._

Thats cool, i even learned a bit from your answer (tbh, my solution came from some trail and error 😅).

May i ask a little question out of interest:
Do you build your gatsby before starting storybook, or do you run it while also running gatsby develop?

If you build it before you have to restart your storybook everytime you have to update a query inside storybook, but running gatsby develop in parallel with storybook-start runs kind of quirky...

Yeah, if i change query, then i need to run gatsby develop to rebuild public/static folder and then restart Storybook server. But this is not a big problem, because i am using Storybook for pure UI prototyping, and queries changes are relatively rare. I just want to get my components working in Storybook without splitting them into pure components / containers.

@blainekasten @sidharthachatterjee

I have the same problem with the latest version of Gatsby.
I did some research and I think the problem comes from:

1. babel-plugin-remove-graphql-queries still defaults to static/d :

Considering this line:
https://github.com/gatsbyjs/gatsby/blob/289c7f8c154a3d764621c39be585cee0da9c9f1c/packages/babel-plugin-remove-graphql-queries/src/index.js#L199

Recent versions of gatsby (after "2.24.6") host the static query data in page-data/sq/d however the latest version of babel-plugin-remove-graphql-queries still defaults to static/d. I suppose this default is used by the Storybook's babel-loader.

2. babel-plugin-remove-graphql-queries doesn't check against NODE_ENV=production anymore

This pull request edits packages/babel-plugin-remove-graphql-queries/src/index.js with the following diff:

-        [`production`, `test`].includes(process.env.NODE_ENV) &&
+        (process.env.NODE_ENV === `test` ||state.opts.stage === `build-html`) &&

Now as most Storybook + Gatsby workspaces are advised by Gatsby docs to run Storybook with NODE_ENV=production and babel-plugin-remove-graphql-queries after the mentioned PR doesn't check against NODE_ENV=production the queries aren't processed anymore.

Here is what I did to confirm that these two changes are the cause of the problem:

  1. Run Storybook with NODE_ENV=test as babel-plugin-remove-graphql-queries still checks against it and processes the queries.
    NODE_ENV=test start-storybook -s public
  2. Copy queries from page-data/sq/d to static/d.

Viola. The components containing the queries are loaded with the needed queries.

Cool, works for me atm.
Definetly just at temporary workaround, so for now i've added a script to my package.json to copy the files and run it before storybook, which looks something like this:

"scripts": {
    "copy-static-queries": "cp -r ./public/page-data/sq/d ./public/static",
    "prestorybook": "npm run copy-static-queries",
  }

Edit:
I used a locked version (2.9.14) of babel-plugin-remove-graphql-queries so storybook still runs with NODE_ENV=production

@smetzdev It doesn't work for me with NODE_ENV=production in the latest version of babel-plugin-remove-graphql-queries. However NODE_ENV=test works as expected.

It might be that your babel-plugin-remove-graphql-queries is somehow resolving to an earlier version of the plugin.

You're right, i still had it left over in my dependencies without me noticing it.
I've edited my comment above to not mislead anybody.

I still might want to keep it that way, it feels more right to me running build-storybook in NODE_ENV=production
Especially if i host it somewhere.

Do you see any problems there?

@smetzdev I don't think NODE_ENV has any effect on hosting, since your files are compiled and then you host those files. Unless the library you are using for compilation treats different environments in a different manner. For example gatsby treats different envs differently to optimize the compilation for development and production, and it throws when you pass NODE_ENV=test.

I don't think storybook treats them any different. It automatically sets NODE_ENV=development however I have been passing NODE_ENV=production, and recently NODE_ENV=test to get the queries processed by babel-plugin-remove-graphql-queries. I can't say I have noticed any change whatsoever.

Update: As react itself handles NODE_ENV differently to decide whether to export the development bundle or the minified one, it's probably best not to depend on NODE_ENV to process queries. It would be best to introduce a new environment variable for babel-plugin-remove-graphql-queries.

FWIW, @mohsenkhanpour and @smetzdev 's fixes of NODE_ENV=test and cp -r ./public/page-data/sq/d ./public/static above seem to be working for me. It feels a little "hacky" but for now, it's getting the job done. Thanks, guys!

Was this page helpful?
0 / 5 - 0 ratings