1

I'm using Lodash, and "npm run start" works to build and start the application. However, when I try to run Karma with "npm run test" it chokes on Lodash. Any ideas?

Here's the error:

404: /base/node_modules/lodash/index.js    
Chrome 55.0.2.883 (Windows 7) ERROR
    {"originalStack": Error: (SystemJS) XHR error (404 Not Found) loading node_modules/lodash/index.js}

Here's a link to a PICTURE of the actual error (I can't embed images yet)

As you can see in the picture, lodash is not the only module that's giving me this error, also one called Wijmo, which is a graphing utility. These aren't the only 3rd party modules I'm using, as you can see in my systemjs.config.js below, so the question is "why are these causing problems while the others are not?"

I have 'node_modules/lodash/lodash.js' in the "files" array of my karma config, as described here: Importing lodash into angular2 + typescript application

... though adding/removing that line doesn't seem to make a difference.

Here is the complete karma.conf.js file, for reference:

module.exports = function(config) {

    var appBase    = 'app/';       // transpiled app JS and map files
    var appSrcBase = 'app/';       // app source TS files
    var appAssets  = '/base/app/'; // component assets fetched by Angular's compiler

    var testingBase    = 'testing/';       // transpiled test JS and map files
    var testingSrcBase = 'testing/';       // test source TS files

    config.set({
        basePath: '',
        frameworks: ['jasmine'],
        plugins: [
            require('karma-jasmine'),
            require('karma-chrome-launcher'),
            require('karma-jasmine-html-reporter'), // click "Debug" in browser to see it
            require('karma-htmlfile-reporter') // crashing w/ strange socket error
        ],

        client: {
            builtPaths: [appBase, testingBase], // add more spec base paths as needed
            clearContext: false // leave Jasmine Spec Runner output visible in browser
        },

        customLaunchers: {
            // From the CLI. Not used here but interesting
            // chrome setup for travis CI using chromium
            Chrome_travis_ci: {
                base: 'Chrome',
                flags: ['--no-sandbox']
            }
        },
        files: [
            'node_modules/lodash/lodash.js',
            // System.js for module loading
            'node_modules/systemjs/dist/system.src.js',

            // Polyfills
            'node_modules/core-js/client/shim.js',
            'node_modules/reflect-metadata/Reflect.js',

            // zone.js
            'node_modules/zone.js/dist/zone.js',
            'node_modules/zone.js/dist/long-stack-trace-zone.js',
            'node_modules/zone.js/dist/proxy.js',
            'node_modules/zone.js/dist/sync-test.js',
            'node_modules/zone.js/dist/jasmine-patch.js',
            'node_modules/zone.js/dist/async-test.js',
            'node_modules/zone.js/dist/fake-async-test.js',

            // RxJs
            { pattern: 'node_modules/rxjs/**/*.js', included: false, watched: false },
            { pattern: 'node_modules/rxjs/**/*.js.map', included: false, watched: false },

            // Paths loaded via module imports:
            // Angular itself
            { pattern: 'node_modules/@angular/**/*.js', included: false, watched: false },
            { pattern: 'node_modules/@angular/**/*.js.map', included: false, watched: false },

            { pattern: 'systemjs.config.js', included: false, watched: false },
            { pattern: 'systemjs.config.extras.js', included: false, watched: false },
            'karma-test-shim.js', // optionally extend SystemJS mapping e.g., with barrels

            // transpiled application & spec code paths loaded via module imports
            { pattern: appBase + '**/*.js', included: false, watched: true },
            { pattern: testingBase + '**/*.js', included: false, watched: true },


            // Asset (HTML & CSS) paths loaded via Angular's component compiler
            // (these paths need to be rewritten, see proxies section)
            { pattern: appBase + '**/*.html', included: false, watched: true },
            { pattern: appBase + '**/*.css', included: false, watched: true },

            // Paths for debugging with source maps in dev tools
            { pattern: appSrcBase + '**/*.ts', included: false, watched: false },
            { pattern: appBase + '**/*.js.map', included: false, watched: false },
            { pattern: testingSrcBase + '**/*.ts', included: false, watched: false },
            { pattern: testingBase + '**/*.js.map', included: false, watched: false}
        ],

        // Proxied base paths for loading assets
        proxies: {
            // required for component assets fetched by Angular's compiler
            "/app/": appAssets
        },

        exclude: [],
        preprocessors: {},
        // disabled HtmlReporter; suddenly crashing w/ strange socket error
        reporters: ['progress', 'kjhtml'],//'html'],

        port: 9876,
        colors: true,
        logLevel: config.LOG_INFO,
        autoWatch: true,
        browsers: ['Chrome'],
        singleRun: false
    })
}

In my systemjs.config.js I have the following:

(function (global) {
    System.config({
        paths: {
            // paths serve as alias
            'npm:': 'node_modules/'
        },
        // map tells the System loader where to look for things
        map: {
            // our app is within the app folder
            app: 'app',
            // angular bundles
            '@angular/core': 'npm:@angular/core/bundles/core.umd.js',
            '@angular/common': 'npm:@angular/common/bundles/common.umd.js',
            '@angular/compiler': 'npm:@angular/compiler/bundles/compiler.umd.js',
            '@angular/platform-browser': 'npm:@angular/platform-browser/bundles/platform-browser.umd.js',
            '@angular/platform-browser-dynamic': 'npm:@angular/platform-browser-dynamic/bundles/platform-browser-dynamic.umd.js',
            '@angular/http': 'npm:@angular/http/bundles/http.umd.js',
            '@angular/router': 'npm:@angular/router/bundles/router.umd.js',
            '@angular/forms': 'npm:@angular/forms/bundles/forms.umd.js',

            // other libraries
            'rxjs':                      'npm:rxjs',
            'angular-in-memory-web-api': 'npm:angular-in-memory-web-api/bundles/in-memory-web-api.umd.js',
            'ng2-translate':             'npm:ng2-translate/bundles',
            'lodash':                    'npm:lodash',
            'socket.io-client':          'npm:socket.io-client/socket.io.js',
            'mydatepicker':              'npm:mydatepicker',
            'wijmo':                     'npm:wijmo'
        },
        // packages tells the System loader how to load when no filename and/or no extension
        packages: {
            app: {
                main: './main.js',
                defaultExtension: 'js'
            },
            rxjs: {
                defaultExtension: 'js'
            },
            'ng2-translate': {
                main: 'ng2-translate',
                defaultExtension: 'umd.js'
            },
            'socket.io-client': {
                defaultExtension: 'js'
            },
            'mydatepicker': {
                main: './dist/index.js',
                defaultExtension: 'js'
            },
            lodash: {
                main: './index.js',
                defaultExtension: 'js'
            },
            wijmo: {
                defaultExtension: 'js'
            }
        }
    });
})(this);

And in my components, I am loading Lodash like this:

import * as _ from "lodash";

If I try to import it without the "* as" it throws an error, saying lodash doesn't have any default exports.

Finally, here is my "test" script from package.json, which is called when I type "npm run test":

"test": "tsc && concurrently \"tsc -w\" \"karma start karma.conf.js\"",
Community
  • 1
  • 1
David
  • 1,620
  • 3
  • 20
  • 39
  • update: after some more research, I think it might have something to do with how I'm setting the base path in Karma... maybe. Although the file exists that's returning a 404, I noticed it DOESN'T exist relative to the karma localhost, only my build's localhost. – David Jan 31 '17 at 15:44
  • 1
    Is the Karma config file in the parent directory of your node_modules folder so that the 'node_modules/lodash' file reference is relative to it? If not you might need to set the basePath config in your Karma config. Also, when Karma is running, can you hit the path http://localhost:9876/base/node_modules/lodash/index.js without a 404? Something else to check: shouldn't the systemjs.config.js use 'lodash': '/base/node_modules/lodash' rather than 'lodash': 'node_modules/lodash' ? – Brady Holt Jan 31 '17 at 22:06
  • Yes, my karma config file is in the parent directory of the node_modules folder. And no, I cannot access that URL when karma is running, it returns a 404 "NOT FOUND" on the screen (not sure what to do about this). As for putting /base/ at the beginning of the lodash location, I gave that a shot and it didn't seem to make a difference. Without making this change, I can see in the console that it's getting a 404 on /base/node_modules/lodash/index.js, so I think it's inserting the base part already. I have updated my post to give you more info - hopefully that's helpful. Thanks for your help – David Feb 01 '17 at 13:39
  • Karma config pointing to 'node_modules/lodash/lodash.js' whereas SystemJS config is pointing to 'node_modules/lodash/index.js'. Can you hit localhost:9876/base/node_modules/lodash/lodash.js without a 404? I think it might be because you're trying to reference .../index.js and it is ..../lodash.js – Brady Holt Feb 01 '17 at 15:25
  • It worked!!! I changed the package definition in systemjs.config to look for './lodash.js' instead of './index.js' and no more error! Thank you!!!!! What a relief! If you want the rep for your answer, put it as a potential answer and I'll mark it as the accepted answer. – David Feb 02 '17 at 14:47

1 Answers1

0

Karma config is pointing to 'node_modules/lodash/lodash.js' whereas SystemJS config is pointing to 'node_modules/lodash/index.js'. I think it might be because you're trying to reference .../index.js and it is ..../lodash.js.

Brady Holt
  • 2,844
  • 1
  • 28
  • 34