如何使用 webpack 加载库源地图?

Posted

技术标签:

【中文标题】如何使用 webpack 加载库源地图?【英文标题】:How to load library source maps using webpack? 【发布时间】:2015-12-18 13:57:26 【问题描述】:

我正在使用 webpack 构建两个项目;一个是另一个图书馆。

在构建我的包装器项目时,是否可以使用我的库项目中的源映射?我希望能够从我的包装 UI 中调试我的库代码。

我的构建工作正常,因为库是内置的。唯一的问题是源映射。我在浏览器调试器中看到的 javascript 是 uglified,因为源映射不可用。

我的项目结构片段:

+-- my-ui/
    +-- dist/
        +-- my-ui.js
        +-- my-ui.js.map
    +-- node_modules/
        +-- my-lib/
            +-- dist/
                +-- bundle.js
                +-- bundle.js.map

来自webpack.config.js的片段:

module.exports = 
    entry: './src/js/main.jsx',
    output: 
        path: path.join(__dirname, 'dist'),
        filename: 'my-ui.js',
        library: 'my-ui',
        libraryTarget: 'umd'
    ,
    devtool: 'source-map',
    module: 
        loaders: [
            test: /\.jsx?$/, loader: 'babel', include: path.join(__dirname, 'src')
        ]
    ,
    plugins: [
        new Clean('dist'),
        new htmlWebpackPlugin(
            template: 'src/index.html',
            inject: true
        )
    ]
;

【问题讨论】:

我没用过,但我认为 source-map-loader 就是你要找的东西。将其分配为preLoader 以获取必要的文件。这是假设 bundle.js 在末尾有源映射注释 嘿@MichelleTilley!我目前正在尝试使用source-map-loader,但我有一个Cannot read property 'substr' of undefined。你知道它可能来自哪里吗?在我的webpack.config.js 我有:devtool: 'source-map', preLoaders: [ test: /\.js$/, loader: "source-map-loader" ],loaders: [ test: /\.ts$/, loader: 'ts-loader' , test: /\.html$/, loader: 'raw-loader' , test: /\.css$/, loader: 'style-loader!css-raw-loader' ] 【参考方案1】:

我正在使用create-react-app,这就是我修复它的方法(不运行eject cmd)

注意:如果您的应用已经使用 react-app-rewired 覆盖了 webpack config,您可以忽略前三个步骤。

npm i react-app-rewired -D - 这将帮助您覆盖 webpack 配置。 package.json - 更改脚本,将 react-scripts 替换为 react-app-rewired
  "scripts": 
    "start": "react-app-rewired start",
    "build": "react-app-rewired build",
    "test": "react-app-rewired test",
    "eject": "react-app-rewired eject"
  

config-overrides.js - 在应用的父级创建此文件。

npm i source-map-loader -D - 加载源映射(假设你的 lib 的 dist 有源映射文件)。使用哪个构建工具(例如:Rollupwebpackparcel)来生成 sourcemap 并不重要。

复制下面的代码到config-overrides.js

module.exports = 
  webpack: (config, env) => 
    // Load source maps in dev mode
    if (env === 'development') 
      config.module.rules.push(
        test: /\.(js|mjs|jsx|ts|tsx)$/,
        use: ['source-map-loader'],
        enforce: 'pre',
      );

      // For `babel-loader` make sure that sourceMap is true.
      config.module.rules = config.module.rules.map(rule => 
        // `create-react-app` uses `babel-loader` in oneOf
        if (rule.oneOf) 
          rule.oneOf.map(oneOfRule => 
            if (
              oneOfRule.loader &&
              oneOfRule.loader.indexOf('babel-loader') !== -1
            ) 
              if (oneOfRule.hasOwnProperty('options')) 
                if (oneOfRule.options.hasOwnProperty('sourceMaps')) 
                  // eslint-disable-next-line no-param-reassign
                  oneOfRule.options.sourceMaps = true;
                
              
            
          );
        
        return rule;
      );
    

    return config;
  ,
;


重新启动您的应用程序(如果它已经在运行)。 source files 根据地图文件中的路径加载到不同的位置。耐心检查所有文件夹:)

注意: 1. 根据从 xxx.js.map 文件中读取的路径,您的源地图将加载到文件夹之一(例如:localhost:3000webpack:///)。 2. 如果你的库使用rollup,请确保在配置文件(output.sourcemapPathTransform)中提供正确的路径,这将有助于在正确的位置加载sourcemaps

【讨论】:

【参考方案2】:

您应该能够使用 Webpack 提供的任何 eval 源映射选项。

实际上,这相当于在您的webpack.config.js 中为my-lib 项目设置正确的devtool 选项。

devtool: 'eval',

evaleval-source-maps 应该都可以工作。

请参阅Webpack source map documentation 了解各种选项。

【讨论】:

这个答案具有误导性 它是如何误导的? ^ 因为这配置了如何为库项目发出源映射 - 但我们也希望从使用该库的外部项目中使用它们。反之亦然 - 如果它定义了 devtool 并发出源映射,则代码可以映射到本地源,但不包括库映射。【参考方案3】:

我终于弄清楚了我的问题......

感谢@BinaryMuse 提供关于source-map-loader 的提示。这确实是正确的方法,尽管它最初对我不起作用。

我最终意识到我需要在“my-lib”“my-ui”中为 webpack 启用 source-map-loader。如果在“my-lib”webpack 配置中没有 source-map-loader,“my-ui”中的 source-map-loader 会出现错误(遗憾的是带有警告消息),因为它无法找到“my-lib”传递依赖项的源映射。显然源映射非常好,source-map-loader 能够窥视依赖关系树的所有方面。

另外值得注意的是,我在使用 source-map-loaderreact-hot-loader 时遇到了一个问题。请看,react-hot-loader 不包括源映射。当source-map-loader 试图找到它们时(因为它只是扫描所有内容),它不能并中止所有内容。

最终,我希望source-map-loader 具有更高的容错性,但如果设置正确,它确实可以工作!

devtool: 'source-map',
module: 
    preLoaders: [
        test: /\.jsx?$/, loader: 'eslint', exclude: /node_modules/,
        test: /\.jsx?$/, loader: 'source-map', exclude: /react-hot-loader/
    ],
    loaders: [
        test: /\.jsx?$/, loader: 'raect-hot!babel', exclude: /node_modules/
    ]

【讨论】:

感谢您的提醒!我也在这个设置中使用 react-hot-loader,它可能为我节省了大量时间。 (因为你得到的错误不是很具体!) 在这种情况下,您可以只测试地图文件,而不是测试每个 js 文件。喜欢: test: /\.js\.map$/, loader: 'source-map' 。这样它就不会在所有其他文件上出错......这就是我所做的,它为我解决了这个问题。但无论如何,感谢我指出正确的方向! :)

以上是关于如何使用 webpack 加载库源地图?的主要内容,如果未能解决你的问题,请参考以下文章

使用 Cmake,如何防止库源包含在我的 IDE 中?

如何将库源附加到 JetBrains Rider

如何在 Eclipse 中附加 Android 支持库源?

在 Pycharm 调试模式下,如何跳出我的代码而不是跳出库源?

如何在带有 webpack 的 React 应用程序中包含“leaflet.css”?

使用 webpack 代码拆分,如何加载块和 HTML 布局?