Repository: storybook
Issue: [Bug]: `run storybook` crashes because of a TypeError (Vue3 + Webpack 5 + Typescript)
Labels: bug,typescript,vue3,builder-webpack5

I installed Storybook to a existing project which is using Vue3 and Webpack 5 (```npx storybook@latest init```):

<details>
  <summary>
    <h4>
      Install bash log
    </h4>
  </summary>

```bash
╭───────────────────────────────────────────────────────╮
│                                                       │
│   Adding Storybook version 7.6.10 to your project..   │
│                                                       │
╰───────────────────────────────────────────────────────╯
 • Detecting project type. ✓
 • Preparing to install dependencies. ✓


 • Installing dependencies

removed 833 packages, changed 1 package, and audited 1010 packages in 10s

120 packages are looking for funding
  run `npm fund` for details

1 moderate severity vulnerability

To address all issues (including breaking changes), run:
  npm audit fix --force

Run `npm audit` for details.
. ✓
 • Adding Storybook support to your "Vue 3" app • Detected webpack project. Setting builder to webpack. ✓

  ✔ Getting the correct version of 11 packages
√ We have detected that you're using ESLint. Storybook provides a plugin that gives the best experience with Storybook and helps follow best practices: https://github.com/storybookjs/eslint-plugin-storybook#readme

Would you like to install it? ... yes
    Configuring Storybook ESLint plugin at .eslintrc.json
  ✔ Installing Storybook dependencies
. ✓
 • Preparing to install dependencies. ✓


 • Installing dependencies

up to date, audited 1843 packages in 2s

261 packages are looking for funding
  run `npm fund` for details

1 moderate severity vulnerability

To address all issues (including breaking changes), run:
  npm audit fix --force

Run `npm audit` for details.
. ✓
╭──────────────────────────────────────────────────────────────────────────────╮
│                                                                              │
│   Storybook was successfully installed in your project! 🎉                   │
│   To run Storybook manually, run npm run storybook. CTRL+C to stop.          │
│                                                                              │
│   Wanna know more about Storybook? Check out https://storybook.js.org/       │
│   Having trouble or want to chat? Join us at https://discord.gg/storybook/   │
│                                                                              │
╰──────────────────────────────────────────────────────────────────────────────╯
```

</details>

Everything went well, until here. But when it comes to start the application, this happens:

```bash
Running Storybook

> MY_VUE_PROJECT@1.0.0 storybook
> storybook dev -p 6006 --quiet

@storybook/cli v7.6.10

info => Starting manager..
info => Starting preview..
info Using SWC compiler
info Addon-docs: using MDX2
info => Using implicit CSS loaders
info => Using default Webpack5 setup
=> Failed to build the preview
TypeError: validate is not a function
    at wdm (.\node_modules\webpack-dev-middleware\dist\index.js:171:3)
    at starter (.\node_modules\@storybook\builder-webpack5\dist\index.js:1:8952)
    at async Module.start (.\node_modules\@storybook\builder-webpack5\dist\index.js:1:11672)
    at async storybookDevServer (.\node_modules\@storybook\core-server\dist\index.js:66:2459)
    at async buildOrThrow (.\node_modules\@storybook\core-server\dist\index.js:60:8290)
    at async buildDevStandalone (.\node_modules\@storybook\core-server\dist\index.js:120:1397)
    at async withTelemetry (.\node_modules\@storybook\core-server\dist\index.js:65:3948)
    at async dev (.\node_modules\@storybook\cli\dist\generate.js:503:401)
    at async Command.<anonymous> (.\node_modules\@storybook\cli\dist\generate.js:518:225)
```

I'm not sure how to fix this. Do I have to update some parts of my TypeScript config? My code does contain a function called `validate`, but my webpack build does work well.

### To Reproduce

~~I don't want to share my whole project. So, I paste here single parts of it:~~
Got it now: [https://stackblitz.com/edit/fsd7873udj](https://stackblitz.com/edit/fsd7873udj)

<details>
  <summary>
    <h4>
      Source files
    </h4>
  </summary>

**vue.config.js**

```javascript
/* eslint-env node */
/* eslint-disable @typescript-eslint/no-var-requires */

// This file is needed for tests to be configured

const path = require('path');

module.exports = {
    pluginOptions: {
        jestSerializer: {
            // All available options: https://github.com/beautify-web/js-beautify/blob/master/js/src/html/options.js
            formatting: {
                indent_char: ' ',
                indent_inner_html: true,
                indent_size: 4,
                inline: [],
                sep: '\n',
                unformatted: ['code', 'pre'],
            },
            removeClassTest: false,
            removeComments: false,
            removeDataTest: true,
            removeDataTestid: true,
            removeDataTestId: true,
            removeDataQa: false,
            removeDataVId: true,
            removeIdTest: false,
            removeServerRendered: true,
            stringifyObjects: false,
        },
    },
};
```

**tsconfig.json**

```json
{
    "compilerOptions": {
        "baseUrl": "./",
        "target": "es2021",
        "module": "es2020",
        "moduleResolution": "node",
        "jsx": "preserve",
        "sourceMap": true,
        "strict": true,
        "downlevelIteration": true, // This flag is to enable support for a more accurate implementation of how modern JavaScript iterates through new concepts in older JavaScript runtimes
        "esModuleInterop": true,
        "noImplicitAny": false,
        "noImplicitReturns": true,
        "noImplicitThis": true,
        "allowSyntheticDefaultImports": true,
        "lib": ["es6", "dom", "es2017", "es2016.array.include", "es2018.promise", "ES2020.String"],
        "paths": {
            "@VueForms/*": ["../Tts.Portal.VueForms/src/*"],
            "@/*": ["src/*"],
            "*": ["node_modules/*"]
        }
    }
}
```

**webpack.config.js**

```javascript
/* eslint-env node */
/* eslint-disable @typescript-eslint/no-var-requires */

const path = require('path');
const webpack = require('webpack');

const VueLoaderPlugin = require('vue-loader/dist/plugin').default;
const MiniCssExtractPlugin = require('mini-css-extract-plugin');

const ncp = require('ncp').ncp;
const sass = require('sass');
const Dotenv = require('dotenv-webpack');
const ForkTsCheckerWebpackPlugin = require('fork-ts-checker-webpack-plugin');
const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin;

const vueFormsBundlesDir = '../web/vue-forms-bundles';

const config = {
    entry: {
        'cart-page': './src/bundles/cartPage.ts',
        'checkout-page': './src/bundles/checkoutPage.ts',
        'confirmation-commerce-page': './src/bundles/confirmationCommercePage.ts',
        'shipping-hint': './src/bundles/shippingHint.ts',
        'cart-service': './src/bundles/cartService.ts',
        'products-teaser-slider': './src/bundles/productsTeaserSlider.ts',
        'product-price-information': './src/bundles/productPriceInformationContainer.ts',
        'similar-jobs': './src/bundles/jobDetailsPage.ts',
        'global-vue-frontend-container': './src/bundles/globalContainer.ts',
        'order-overview-page': './src/bundles/orderOverviewPage.ts',
        'order-quick-view': './src/bundles/orderQuickView.ts',
        'order-detail-page': './src/bundles/orderDetailPage.ts',
    },
    output: {
        path: path.resolve(__dirname, vueFormsBundlesDir),
        filename: '[name]-bundle.js',
    },
    resolve: {
        extensions: ['.ts', '.js', '.vue', '.json'],
        modules: [path.resolve(__dirname, 'node_modules')],
        alias: {
            'fuse.js': 'fuse.js/dist/fuse.min.js',
            '@': path.resolve('src'),
        },
    },
    module: {
        rules: [
            {
                test: /\.vue$/,
                loader: 'vue-loader',
                options: {
                    compilerOptions: {
                        isCustomElement: (tag) => tag === 'lottie-player',
                    },
                },
            },
            {
                test: /\.ts$/,
                exclude: /node_modules/,
                use: {
                    loader: 'ts-loader',
                    options: {
                        onlyCompileBundledFiles: true,
                        appendTsSuffixTo: [/\.vue$/],
                        transpileOnly: true,
                    },
                },
            },
            {
                test: /\.scss$/,
                use: [
                    'vue-style-loader',
                    'css-loader',
                    {
                        loader: 'sass-loader',
                        options: {
                            implementation: sass,
                            sourceMap: false, // On chrome there is an issue that when changing css in dev console, it breaks page. No source map fixes it.
                            sassOptions: {
                                quietDeps: true, // Disable warning messages from dependencies
                            },
                        },
                    },
                ],
            },
        ],
    },
    watchOptions: {
        ignored: /node_modules/,
        aggregateTimeout: 150,
    },
    plugins: [
        new webpack.DefinePlugin({
            __VUE_OPTIONS_API__: true,
            __VUE_PROD_DEVTOOLS__: false,
        }),
        new ForkTsCheckerWebpackPlugin({
            async: true,
            typescript: {
                extensions: {
                    vue: {
                        enabled: true,
                        compiler: '@vue/compiler-sfc',
                    },
                },
            },
            issue: { exclude: [{ code: 'TS1192' }] }, // ignore `no default export` errors as known plugin issue
        }),
        // new BundleAnalyzerPlugin(),
    ],
    optimization: {
        splitChunks: {
            cacheGroups: {
                vendor: {
                    test: /[\\/]node_modules[\\/]((?!(awesome-phonenumber)).*)[\\/]/,
                    name: 'vendors-vue-3',
                    chunks: 'all',
                    minChunks: 3,
                    reuseExistingChunk: true,
                },
            },
        },
    },
};

module.exports = (env, argv) => {
    config.plugins.push(
        new Dotenv({
            path: `./.env`,
        })
    );

    if (argv.mode === 'development') {
        config.devtool = 'source-map';
        config.watch = true;
        config.watchOptions = {
            aggregateTimeout: 250,
            ignored: ['node_modules'],
        };
    }

    return config;
};
```

**package.json**

```json
{
  "name": "MY_VUE_PROJECT",
  "version": "1.0.0",
  "scripts": {
    "format": "npm run format:templates && npm run lint:fix",
    "format:templates": "html-beautify --replace ./src/**/*.vue",
    "lint": "eslint ./src/** --color --config ../../.eslintrc.json",
    "lint:quiet": "eslint ./src/** --quiet --config ../../.eslintrc.json",
    "lint:fix": "eslint ./src/** --fix --config ../../.eslintrc.json",
    "npm-auth": "npx vsts-npm-auth -T \"%USERPROFILE%/.npmrc\" -C ./.npmrc",
    "webpack:dev": "webpack --mode=development --progress --stats normal",
    "webpack:prod": "webpack --mode=production --progress --stats errors-only",
    "webpack:inspect": "webpack --profile --json > stats.json",
    "test:unit": "jest",
    "test:update": "jest -u",
    "test:watch": "jest --watch",
    "storybook": "storybook dev -p 6006",
    "build-storybook": "storybook build"
  },
  "browserslist": [
    "> 1%",
    "last 2 versions"
  ],
  "private": true,
  "devDependencies": {
    "@babel/core": "^7.23.7",
    "@babel/helper-compilation-targets": "^7.23.6",
    "@babel/preset-env": "^7.23.8",
    "@paypal/paypal-js": "^5.1.1",
    "@storybook/addon-essentials": "^7.6.10",
    "@storybook/addon-interactions": "^7.6.10",
    "@storybook/addon-links": "^7.6.10",
    "@storybook/blocks": "^7.6.10",
    "@storybook/test": "^7.6.10",
    "@storybook/vue3": "^7.6.10",
    "@storybook/vue3-webpack5": "^7.6.10",
    "@stripe/stripe-js": "^1.48.0",
    "@types/googlemaps": "^3.43.3",
    "@types/jest": "^29.5.11",
    "@types/jquery": "^3.5.16",
    "@typescript-eslint/eslint-plugin": "^5.46.1",
    "@typescript-eslint/parser": "^5.46.1",
    "@vee-validate/rules": "4.5.11",
    "@vue/babel-preset-app": "^5.0.8",
    "@vue/compiler-sfc": "^3.4.15",
    "@vue/test-utils": "2.4.1",
    "@vue/vue3-jest": "^29.2.6",
    "awesome-phonenumber": "^3.2.0",
    "axios": "^0.27.2",
    "babel-jest": "^29.7.0",
    "css-loader": "^6.7.1",
    "dotenv-webpack": "^7.0.3",
    "eslint": "^8.29.0",
    "eslint-config-prettier": "^8.5.0",
    "eslint-plugin-jest": "^27.1.6",
    "eslint-plugin-prettier-vue": "^4.2.0",
    "eslint-plugin-storybook": "^0.6.15",
    "eslint-plugin-vue": "^9.19.2",
    "fork-ts-checker-webpack-plugin": "^6.5.2",
    "jest": "^29.7.0",
    "jest-environment-jsdom": "^29.7.0",
    "jest-serializer-vue-tjw": "^3.20.0",
    "jest-transform-stub": "^2.0.0",
    "jest-watch-typeahead": "^2.2.0",
    "js-beautify": "^1.14.7",
    "jwt-decode": "^3.1.2",
    "lodash": "^4.17.21",
    "mini-css-extract-plugin": "^2.6.0",
    "ncp": "^2.0.0",
    "nswag": "^13.15.10",
    "prettier": "^2.8.1",
    "react": "^18.2.0",
    "react-dom": "^18.2.0",
    "sass": "^1.51.0",
    "sass-loader": "^12.6.0",
    "storybook": "^7.6.10",
    "ts-jest": "^29.1.1",
    "ts-loader": "^9.5.1",
    "tslib": "^2.6.2",
    "typescript": "5.3.3",
    "vee-validate": "4.5.11",
    "vue": "3.4.7",
    "vue-loader": "^17.4.2",
    "vue-style-loader": "^4.1.3",
    "vuex": "^4.1.0",
    "webpack": "^5.72.1",
    "webpack-bundle-analyzer": "^4.5.0",
    "webpack-cli": "^4.9.2",
    "yup": "^0.32.11"
  },
  "devDependenciesComments": "@vue/test-utils version 2.4.2 breaks setProps. Should be fixed with https://github.com/vuejs/test-utils/pull/2242",
  "files": [
    "/dist/**"
  ],
  "engines": {
    "node": ">=14.0.0",
    "npm": ">=7.0.0",
    "vscode": "^1.57.0"
  }
}
```
</details>

### System

```bash
Storybook Environment Info:

  System:
    OS: Windows 10 10.0.19045
    CPU: (16) x64 12th Gen Intel(R) Core(TM) i7-1270P
  Binaries:
    Node: 20.5.0 - C:\Program Files\nodejs\node.EXE
    npm: 9.8.0 - C:\Program Files\nodejs\npm.CMD <----- active
  Browsers:
    Edge: Chromium (120.0.2210.144)
  npmPackages:
    @storybook/addon-essentials: ^7.6.10 => 7.6.10
    @storybook/addon-interactions: ^7.6.10 => 7.6.10
    @storybook/addon-links: ^7.6.10 => 7.6.10
    @storybook/blocks: ^7.6.10 => 7.6.10
    @storybook/test: ^7.6.10 => 7.6.10
    @storybook/vue3: ^7.6.10 => 7.6.10
    @storybook/vue3-webpack5: ^7.6.10 => 7.6.10
    eslint-plugin-storybook: ^0.6.15 => 0.6.15
    storybook: ^7.6.10 => 7.6.10
```


### Additional context

_No response_