最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

Debugging bundled javascript in Visual Studio 2015 - Stack Overflow

programmeradmin0浏览0评论

I'm using WebPack with this simple config file to bundle my application.

var path = require('path');

module.exports = {
    debug: true,
    devtool: 'source-map',

    context: path.join(__dirname, 'js'),
    entry: './main.js',
    output: {
        path: path.join(__dirname, 'Built'),
        filename: '[name].bundle.js'
    }
};

This creates source mapping that I can easily use to debug my original javascript files in all popular browsers. However, setting breakpoint inside Visual Studio and running the project doesn't work, the breakpoints are disabled saying "No symbols have been loaded for this document". I'm debugging through IE11, where simple javascript can be debugged right away by Visual Studio, but after bundling this doesn't work anymore.

There is a sign that the sourcemapping works, because I get in console output Unsupported format of the sourcemap. The sourcemap generated the using config above looks like this

{"version":3,"sources":["webpack:///webpack/bootstrap 2919a5f916c286b8e21a","webpack:///./main.js","webpack:///./structure_editor/content.js","webpack:///./structure_editor/test_bundle.js"],"names":[],"mappings":";AAAA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,uBAAe;AACf;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;;AAGA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;;;;;;ACtCA;AACA;;AAEA;AACA;;AAEA;;AAEA;;AAEA;;;;;;;ACVA,8C;;;;;;ACAA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA,6B","file":"main.bundle.js","sourcesContent":[" \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId])\n \t\t\treturn installedModules[moduleId].exports;\n\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\texports: {},\n \t\t\tid: moduleId,\n \t\t\tloaded: false\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.loaded = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(0);\n\n\n\n/** WEBPACK FOOTER **\n ** webpack/bootstrap 2919a5f916c286b8e21a\n **/","document.write(require(\"./structure_editor/content.js\"));\r\nvar TestBundle = require(\"./structure_editor/test_bundle.js\");\r\n\r\nvar test = new TestBundle();\r\ntest.testMe();\r\n\r\n//var StructureEditor = require(\"./structure_editor/structure_editor.js\");\r\n\r\n//var editor = new StructureEditor(0x00FF00);\r\n\r\n//editor.run();\r\n\n\n\n/*****************\n ** WEBPACK FOOTER\n ** ./main.js\n ** module id = 0\n ** module chunks = 0\n **/","module.exports = \"It works from content.js.\";\n\n\n/*****************\n ** WEBPACK FOOTER\n ** ./structure_editor/content.js\n ** module id = 1\n ** module chunks = 0\n **/","var TestBundle = function () {\r\n    \r\n}\r\n\r\nTestBundle.prototype.testMe = function() {\r\n    var a = 10;\r\n    var b = 12;\r\n    var c = a + b;\r\n    document.write(c);\r\n};\r\n\r\nmodule.exports = TestBundle;\n\n\n/*****************\n ** WEBPACK FOOTER\n ** ./structure_editor/test_bundle.js\n ** module id = 2\n ** module chunks = 0\n **/"],"sourceRoot":""}

So I can understand that this format might not be supported because of the webpack:// (although IE does understand it). However, if I knew how the proper format for VS looks like I might be able to tweak webpack to produce such format.

I'm asking for any ideas, tutorials,.. whatever to get this working.

I'm using WebPack with this simple config file to bundle my application.

var path = require('path');

module.exports = {
    debug: true,
    devtool: 'source-map',

    context: path.join(__dirname, 'js'),
    entry: './main.js',
    output: {
        path: path.join(__dirname, 'Built'),
        filename: '[name].bundle.js'
    }
};

This creates source mapping that I can easily use to debug my original javascript files in all popular browsers. However, setting breakpoint inside Visual Studio and running the project doesn't work, the breakpoints are disabled saying "No symbols have been loaded for this document". I'm debugging through IE11, where simple javascript can be debugged right away by Visual Studio, but after bundling this doesn't work anymore.

There is a sign that the sourcemapping works, because I get in console output Unsupported format of the sourcemap. The sourcemap generated the using config above looks like this

{"version":3,"sources":["webpack:///webpack/bootstrap 2919a5f916c286b8e21a","webpack:///./main.js","webpack:///./structure_editor/content.js","webpack:///./structure_editor/test_bundle.js"],"names":[],"mappings":";AAAA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;AAEA;AACA;AACA,uBAAe;AACf;AACA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;AACA;;;AAGA;AACA;;AAEA;AACA;;AAEA;AACA;;AAEA;AACA;;;;;;;ACtCA;AACA;;AAEA;AACA;;AAEA;;AAEA;;AAEA;;;;;;;ACVA,8C;;;;;;ACAA;;AAEA;;AAEA;AACA;AACA;AACA;AACA;AACA;;AAEA,6B","file":"main.bundle.js","sourcesContent":[" \t// The module cache\n \tvar installedModules = {};\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId])\n \t\t\treturn installedModules[moduleId].exports;\n\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\texports: {},\n \t\t\tid: moduleId,\n \t\t\tloaded: false\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.loaded = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"\";\n\n \t// Load entry module and return exports\n \treturn __webpack_require__(0);\n\n\n\n/** WEBPACK FOOTER **\n ** webpack/bootstrap 2919a5f916c286b8e21a\n **/","document.write(require(\"./structure_editor/content.js\"));\r\nvar TestBundle = require(\"./structure_editor/test_bundle.js\");\r\n\r\nvar test = new TestBundle();\r\ntest.testMe();\r\n\r\n//var StructureEditor = require(\"./structure_editor/structure_editor.js\");\r\n\r\n//var editor = new StructureEditor(0x00FF00);\r\n\r\n//editor.run();\r\n\n\n\n/*****************\n ** WEBPACK FOOTER\n ** ./main.js\n ** module id = 0\n ** module chunks = 0\n **/","module.exports = \"It works from content.js.\";\n\n\n/*****************\n ** WEBPACK FOOTER\n ** ./structure_editor/content.js\n ** module id = 1\n ** module chunks = 0\n **/","var TestBundle = function () {\r\n    \r\n}\r\n\r\nTestBundle.prototype.testMe = function() {\r\n    var a = 10;\r\n    var b = 12;\r\n    var c = a + b;\r\n    document.write(c);\r\n};\r\n\r\nmodule.exports = TestBundle;\n\n\n/*****************\n ** WEBPACK FOOTER\n ** ./structure_editor/test_bundle.js\n ** module id = 2\n ** module chunks = 0\n **/"],"sourceRoot":""}

So I can understand that this format might not be supported because of the webpack:// (although IE does understand it). However, if I knew how the proper format for VS looks like I might be able to tweak webpack to produce such format.

I'm asking for any ideas, tutorials,.. whatever to get this working.

Share Improve this question asked Sep 7, 2015 at 20:32 RavenRaven 4,9039 gold badges48 silver badges75 bronze badges 4
  • Asking for tutorials is off-topic – Thomas Weller Commented Sep 7, 2015 at 22:05
  • @Thomas This might not be the case, when after spending two full days searching for solution there was nothing working or plete to be found. There might be however an article somewhere, which doesn't get much attention and could be brought to me. Anyway, the tone of that last sentence should indicate that I will really appreciate any help. – Raven Commented Sep 7, 2015 at 23:35
  • I also came across same issue. I made couple attempts with VS'13 but with no success. Now I'm using debugger in Chrome but I'd be very happy if someone found a solution. – Eduard Lepner Commented Sep 17, 2015 at 5:35
  • 1 I was able to get it working for typescript by embedding the sourcemaps into the javascript github./macromaniac/exbundle – dog Commented Jan 13, 2017 at 19:15
Add a ment  | 

2 Answers 2

Reset to default 6

I don't have a full solution to the problem but I did narrow it down a bit.

The first thing to ensure is that the paths to both the source map and the original files are available to Visual Studio. I found that some of these request were getting the login page as a response. I granted anonymous access to the map and ts files. I did try using absolute, file system paths for the ts files which worked for Visual Studio but the browsers did not seem very happy about it.

From what I understand, the following is a shortcut for configuration of the SourceMapDevToolPlugin plugin. Going direct to the plugin will give you more control over the source maps that are generated.

devtool: 'source-map'

That would mean replacing the line above with something like the following.

config.plugins.push(new webpack.SourceMapDevToolPlugin({
    filename: '[file].map',
    moduleFilenameTemplate: "[resource-path]",
    fallbackModuleFilenameTemplate: "[resource-path]?[hash]"
}));

Note the [absolute-resource-path] macro which will result in file system paths that Visual Studio can use to access the files without loading them through the website. These are output in the sources property with backslashes escaped with a second backslash (C:\Projects\... for example). As I noted above though, this broke debugging in the browsers.

Also, the [resource-path] macro appears to be resolved during debugging as if it is relative to the folder that contains the source maps. This was not correct for my setup. I added a prefix and used something similar to the following to sort that out.

"../../app/[resource-path]"

The next issue was with the last segments for some of the lines within the mappings property (within the map files). This explanation of the source map format was very helpful here but pretty much, all you need to know is that semi colons separate lines and that each line can have multiple segments separated by mas. The segments can encode the following information.

  • Generated column
  • Original file this appeared in
  • Original line number
  • Original column
  • And if available original name.

I found that if I removed any short segments from the ends of lines that Visual Studio could process the map and I could set breakpoints etc. in the original files (Typescript files that were converted to javascript which was then bundled in my case).

To remove the short segments I used the following, manual process in Visual Studio for each of the map files. Note that I found it easier to interpret the files after I had formatted them by right clicking in the body of the document and selecting Format Document from the context menu.

  • Perform a replace operation with regular expressions enabled. Use the following expression in the find field and $1 as the value to replace.

    ,\s*[^\s\";]{1,3}?(;|\")

This will replace any segments that contain only 1, 2 or 3 characters at the end of lines.

It is possible that there will be problems setting breakpoints at the ends of lines but I have not been able to break it so far. I did notice though that when there were errors that caused execution to stop in the debugger that the lines did not always match up - maybe a result of this manipulation?

I also wrote a little console application that will perform this modification on all map files in a given folder. I run this automatically at the end of our build.

    static void Main(string[] args)
    {
        var sourceMapFolder = new DirectoryInfo(args[0]);

        foreach (var sourceMapFile in sourceMapFolder.EnumerateFiles("*.map"))
        {
            var sourceMapFilePath = sourceMapFile.FullName;

            var regex = new Regex(",\\s*[^\\s\\\";]{1,3}?(;|\\\")");

            var oldContent = File.ReadAllText(sourceMapFilePath);

            var newContent = regex.Replace(oldContent, "$1");

            File.WriteAllText(sourceMapFilePath, newContent);
        }
    }

I am unsure as to whether it is Webpack which should not be generating the segments or Visual Studio which should be handling them.

Update: I created a Bug on the Connect site for Visual Studio which covers this issue.

I found a solution for your problem.

In the webpack.config.js add this plugin

plugins: [
  new webpack.SourceMapDevToolPlugin(
    sourceMapFilename, null,
    "[absolute-resource-path]", "[absolute-resource-path]")
]

sourceMapFilename should be the name of your bundle.
You can also use the [name] tag if you use multiple entry points.

remove this from your webpack.config.js

devtool: 'source-map'

Now when you start debugging in VS with Internet Explorer you should hit the breakpoints you set up in your .ts files.

source: https://github./webpack/webpack/issues/238

Hope this helps.

发布评论

评论列表(0)

  1. 暂无评论