How to fix your node dependencies’ es6 causing browser errors

How to fix your node dependencies’ es6 causing browser errors

If you’re doing anything with modern JavaScript this day and age you’re probably using es6 and using babel to transpile it back to es5, which works with most browsers.

This works fine for the code you write, but what about your dependencies? Usually they themselves provide transpiled code so it’s not something to worry about. However, some of them may not (especially if their primary focus wasn’t to be used on the browser and, well… you may get the errors like the below in older browsers (such as IE11):

   
    SCRIPT1014: Invalid character
    SCRIPT5009: 'webpackJsonp' is undefined
A screenshot of the IE11 error screen showing ‘Invalid character’ and ‘webpackJsonp’ is undefined
A screenshot of the IE11 error screen showing ‘Invalid character’ and ‘webpackJsonp’ is undefined

Your first instinct may be to leave the industry and go herd baby goats.

A baby pygmy goat looking out of a cave at Mudchute park & farm
A baby pygmy goat looking out of a cave at Mudchute park & farm

However, there is an alternative. Or at least, I found a solution on github after much hair pulling googling:

First of all, you unfortunately need to figure out which module is causing the problem. Thankfully, your browser should show the code where the error occurs. In this case, this module was using es6 template string, which IE11 does not support:

A screenshot of the IE11 debug console showing an error occuring because the module in question was using es6 template strings If you’re bundling your dependencies, it’s not immediately obvious where the error is. In this case, I got lucky, and easily found the culprit with a bit of scrolling up; it turned out to be csv-parse (and yep, my evil experiments have me parsing CSV files in the browser…)

A screenshot of the debug console showing part of csv-parse’s code where you can clearly see its name in a comment

Once you find out what the problem is, what you have to do is essentially tell babel to transpile that module as well, since you would normally be excluding all of node_modules.

First of all if you have exclude: /node_modules in your webpack.config.json, you have to get rid of that.

Instead, use include: ['src'] (or whatever your source directory is).

Now you have to add the problematic module as well. In this case, this is what my config looks now (replace csv-parse with the name of the module that is the problem):

 

  
  {
      test: /\.js$/,
      include: ['src', require.resolve('csv-parse') ],
      use: {
        loader: 'babel-loader',
        options: {
        }
      }
    },

Also, make sure that you are using babel-polyfill to get es5 polyfills for all the es6 code.

For example, I changed my entry to this:

        entry: [ 'babel-polyfill', './src/client/index.ts' ],

That’s it. Once you’ve done those things, after you re-compile, all the errors should go away and you should have plain old es5 code compiled from your es6 dependencies!

Here is the full diff of what I changed for comparison:

    diff --git a/.babelrc b/.babelrc
    index 76a26b7..244d28b 100644
    --- a/.babelrc
    +++ b/.babelrc
    @@ -1,4 +1,3 @@
     {
    -    "presets": [ "es2015" ],
    -    "plugins": ["transform-runtime"]
    +    "presets": [ "es2015" ]
     }
    diff --git a/webpack.config.js b/webpack.config.js
    index 3796b22..3112198 100644
    --- a/webpack.config.js
    +++ b/webpack.config.js
    @@ -6,7 +6,7 @@ const env = process.env.NODE_ENV
     const UglifyJSPlugin = require('uglifyjs-webpack-plugin')

     module.exports = {
    -  entry: [ './src/client/index.ts' ],
    +  entry: [ 'babel-polyfill', './src/client/index.ts' ],
       output: {
         filename: 'dist/public/bundle.js'
       },
    @@ -21,11 +21,10 @@ module.exports = {
           },
           {
             test: /\.js$/,
    -        exclude: /(node_modules|bower_components)/,
    +        include: ['src', require.resolve('csv-parse') ],
             use: {
               loader: 'babel-loader',
               options: {
    -            presets: ['[@babel/preset-env](http://twitter.com/babel/preset-env)']
               }
             }
           },

Huge thanks to KagamiChan and johnwebbcole on github who found this issue and published a solution, I am merely reporting in case it helps someone else, and not trying to take credit 🙂

    Leave a Reply

    Your email address will not be published. Required fields are marked *

    This site uses Akismet to reduce spam. Learn how your comment data is processed.