storybookjs / storybook

Storybook is the industry standard workshop for building, documenting, and testing UI components in isolation
https://storybook.js.org
MIT License
84.62k stars 9.31k forks source link

[Bug]: Gatsby link and Storybook #22065

Open darylthornhill opened 1 year ago

darylthornhill commented 1 year ago

Describe the bug

Storybook is great, we've just upgraded gatsby and need to upgrade storybook. Both normally work absolutely fine.

Looking at gatsby's documentation, this hasn't been updated for storybook v7 yet, and parts of the systems working together doesn't work.

I've tried in existing and a fresh gatsby and storybook installation (github linked below)

Example, when using a gatsby <Link> component in a story, the system errors.

image

To Reproduce

https://github.com/darylthornhill/test-gatsby-storybook-error

All i've done is set up a gatsby Link and put it in the Header.tsx in the src/stories folder.

System

Environment Info:

  System:
    OS: macOS 13.2.1
    CPU: (10) arm64 Apple M2 Pro
  Binaries:
    Node: 18.15.0 - ~/.nvm/versions/node/v18.15.0/bin/node
    npm: 9.5.0 - ~/.nvm/versions/node/v18.15.0/bin/npm
  Browsers:
    Safari: 16.3
  npmPackages:
    @storybook/addon-essentials: ^7.0.4 => 7.0.4 
    @storybook/addon-interactions: ^7.0.4 => 7.0.4 
    @storybook/addon-links: ^7.0.4 => 7.0.4 
    @storybook/blocks: ^7.0.4 => 7.0.4 
    @storybook/react: ^7.0.4 => 7.0.4 
    @storybook/react-webpack5: ^7.0.4 => 7.0.4 
    @storybook/testing-library: ^0.0.14-next.2 => 0.0.14-next.2

Additional context

No response

jonniebigodes commented 1 year ago

@darylthornhill thanks for taking the time to open up an issue and follow up with us. To give you some context, we're aware of the fact, and another community member already reached out to us with a similar question (e.g. #21958) regarding Gatsby, and we're gathering information and see how best to address this so that not only you but other Gatsby users are able to set up and use Storybook without any issues and hopefully "cross the bridge" (pardon the bad pun) and follow up with the Gatsby maintainers and make the required changes to the documentation as well.

Edit: I just updated the issue title for clarity. Hope you don't take it the wrong way 🙏

darylthornhill commented 1 year ago

Sure, that makes a lot of sense.

That other issue you mentioned does look slightly different, as that looks like someone is having a problem with a Gatsby repo that has a custom babel setup already conflicting with the one you are providing from storybook (If ive understood that right?!).

The issue I am describing is a fresh Gatsby setup, with a fresh storybook where using anything from Gatsby, in my case Link isn't working.

If that comes under the same boat from your end in your internals though, that would make sense. Either way, any progress would be handy, i'll watch the other issue regardless!

Thanks for your response.

oskari commented 1 year ago

Did you try the steps mentioned in Gatsby docs regarding the preview.js/ts and Gatsby Link?

That other issue you mentioned does look slightly different, as that looks like someone is having a problem with a Gatsby repo that has a custom babel setup already conflicting with the one you are providing from storybook (If ive understood that right?!).

That custom babel setup is just a minimal example from Gatsby docs, it's not really that custom in my opinion. It's actually probably just babel-preset-gatsby what is breaking it, it seems you haven't included it in your repo.

There's myriad of issues and some of them can be bypassed by it seems that there's no easy way to get Storybook 7 to work with Gatsby v4 or v5.

@jonniebigodes Should we have somekind of a umbrella discussion related to these issues with Gatsby? It seems that even the Storybook frontpage -repo is suffering from these same issues: https://github.com/storybookjs/frontpage/compare/main...upgrade-to-sb-7 . I explored these same changes on my own project what @kylegach has done there. The Gatsby docs are hugely outdated and I have no problem to contribute on updating them but I currently have nowhere to go as I'm not really familiar with Storybook and getting anything to work seems to be a huge task.

LekoArts commented 1 year ago

Gatsby maintainer here 👋 Happy to help update/rewrite our docs or give guidance on certain internals to make things work :)

JerzyDamian commented 1 year ago

Hello :) I came here from issue: https://github.com/storybookjs/storybook/issues/21958 We have working Storybook with stories using Storybook 6 and Gatsby 5, but after upgrade Storybook to 7 and follow all guides we have found problem with "Cannot find module". After long hours of trying fixing mentioned problem, I've tried also to init clear Storybook 7 with Gatsby 5 and guess what :D There is the same problem "Cannot find module". It is very strange, cuz Storybook starts but cannot see files?

hazuremon commented 1 year ago

For those who may came across this issue, I managed to get my storybook (7.1) and gatsby (5.11) working with the combination of a few different changes listed above.

From Gatsby recommended changes, apply the configuration needed for main.js and preview.js https://www.gatsbyjs.com/docs/how-to/testing/visual-testing-with-storybook/

You will most likely came across another error ERR! TypeError: Cannot read properties of undefined (reading '0')

As identified by @oskari above, storybook did have similar issue which was fixed by changing config.module.rules[0] to config.module.rules[2] https://github.com/storybookjs/frontpage/compare/main...upgrade-to-sb-7

Once that is working, your storybook will then start building but may left with React is not defined but you can bypass that by removing if (parseInt(React.version) <= 18) { ... }

https://stackoverflow.com/a/75796131

brootle commented 1 year ago

Can somebody create example boilerplate repo at GitHub where Gatsby 5 will work with Storybook 7?

I need Gatsby style import using modules to work out of the box in Storybook as well

import { style1, style2 } from "./MyComponent.module.css"

Plus most of my components are getting data using useStaticQuery So this is just another issue to address.

It seems to me that Gatsby team has no time for Storybook integration? And Storybook team is also busy with their stuff...

vincentreynaud commented 3 months ago

Hi! I'm trying to install storybook on my gatsby project and encountering the same issue with storybook 8.2 and gatsby 5.13.

I can confirm that everything was working fine until i brought a component that used Gatsby link.

I also blocked at TypeError: Cannot read properties of undefined (reading '0') and i've tinkered with the webpack config code in main.ts as suggested by @hazuremon, but nothing that effectively fixes the issue.

Here's where i'm blocking: I've refactored the main.ts webpack config to bypass undefined errors and to pick the rule to be modified by a search string.

.storybook/main.ts

import type { StorybookConfig } from "@storybook/react-webpack5";

const config: StorybookConfig = {
  stories: ["../src/**/*.mdx", "../src/**/*.stories.@(js|jsx|mjs|ts|tsx)"],
  addons: [
    "@storybook/addon-webpack5-compiler-swc",
    "@storybook/addon-links",
    "@storybook/addon-essentials",
    "@chromatic-com/storybook",
    "@storybook/addon-interactions",
    "@storybook/addon-styling-webpack",
    {
      name: "@storybook/addon-postcss",
      options: {
        postcssLoaderOptions: {
          implementation: require("postcss"),
        },
      },
    },
  ],
  framework: {
    name: "@storybook/react-webpack5",
    options: {},
  },
  webpackFinal: async (config: any) => {
    // finding the rule based on targetting the loader to be less random
    const rule = config.module.rules.find((rule: any) => {
      const [useItem] = rule?.use || [];
      if (!useItem) {
        return false;
      } else {
        return useItem?.loader?.includes("webpack"); // i'm assuming we're targetting the webpack loader
      }
    });

    // Transpile Gatsby module because Gatsby includes un-transpiled ES6 code.
    rule.exclude = [/node_modules\/(?!(gatsby|gatsby-script)\/)/];

    // Remove core-js to prevent issues with Storybook
    // ❗️ isn't this overwriting the previous declaration?
    rule.exclude = [/core-js/];

    // Use babel-plugin-remove-graphql-queries to remove static queries from components when rendering in storybook
    if (!rule.use[0]?.options) {
      rule.use[0].options = {
        plugins: [require.resolve("babel-plugin-remove-graphql-queries")],
      };
    } else {
      rule.use[0].options.plugins = [
        ...(rule.use[0].options?.plugins || []),
        require.resolve("babel-plugin-remove-graphql-queries"),
      ];
    }

    config.module.rules = [rule, ...config.module.rules];
    config.resolve.mainFields = ["browser", "module", "main"];
    return config;
  },
};

export default config;

I think i'm doing something similar to the previous suggested configuration, the undefined console errors are gone, but now i get this:

ERROR in ./src/components/ui/link.stories.ts 48:87
Module parse failed: Identifier '__namedExportsOrder' has already been declared (48:87)
File was processed with these loaders:
 * ./node_modules/@storybook/csf-plugin/dist/webpack-loader.js
 * ./node_modules/@storybook/builder-webpack5/dist/loaders/export-order-loader.js
 * ./node_modules/@storybook/builder-webpack5/dist/loaders/export-order-loader.js
 * ./node_modules/swc-loader/src/index.js
You may need an additional loader to handle the result of these loaders.
|     }

maybe something wrong with the 2 export-order-loader.js ?

for reference here's my preview file:

.storybook/preview.ts

import type { Preview } from "@storybook/react";
import { action } from "@storybook/addon-actions";

import "../src/styles/index.css";

global.___loader = {
  enqueue: () => {},
  hovering: () => {},
};

global.__BASE_PATH__ = "/";

window.___navigate = (pathname) => {
  action("NavigateTo:")(pathname);
};

const preview: Preview = {
  parameters: {
    controls: {
      matchers: {
        color: /(background|color)$/i,
        date: /Date$/i,
      },
    },
  },
};

export default preview;

Help would be appreciated 🙏