0

I'm trying to require the xml-js module (https://www.npmjs.com/package/xml-js) to do some XML parsing in my existing Electron + Typescript project.

What I'm slightly confused about is why it is throwing an error.

First of all, the tsconfig.json file is the following:

{
    "compilerOptions": {
        "target": "es5",
        "module": "commonjs",
        "moduleResolution": "node",
        "sourceMap": true,
        "emitDecoratorMetadata": true,
        "experimentalDecorators": true,
        "removeComments": false,
        "noImplicitAny": false,
        "outDir":   "dist"
    },
    "exclude": [
        "node_modules"
    ]
}

the relevant part of the systemjs config is here:

    paths: {
      'npm:': 'node_modules/'
    },
    map: {
      'xml-js': 'npm:xml-js'
    },
    packages: {
      app: {
        main: './main.js',
        defaultExtension: 'js'
      },
    rxjs: {
       defaultExtension: 'js'
     }
    }

So the module is located in node_modules/xml-js (like many others).

When I build my application, I get the following error:

file://<path>/Documents/projectFolder/electron-angular2-rc6/ng2-electron/node_modules/xml-js Failed to load resource: net::ERR_FILE_NOT_FOUND

and :

index.html:18 Error: (SystemJS) XHR error loading file://<path>/Documents/projectFolder/electron-angular2-rc6/ng2-electron/node_modules/xml-js

I'm attempting to load the module through:

const parser = require("xml-js");

(so, as vanilla JS), in my typescript component (application.component.ts).

The relevant part of my index.html is:

<script src="systemjs.config.js"></script>
    <script>
        System.import('app').catch(function(err){ console.error(err); });

        document.addEventListener('dragover',function(event){
            event.preventDefault();
            return false;
        },false);

        document.addEventListener('drop',function(event){
            event.preventDefault();
            return false;
        },false);
    </script>

The module has been installed through:

npm install xml-js --save-dev

And exists in the directory node_modules/xml-js

I have tons of other modules (including rxjs and angular-in-memory-web-api) along with the regular @angular ones: all of them are working properly and throwing no error, but the xml-js one seems to be not working whatsoever.

5
  • I'm not sure, but are DEV-dependencies available in electron at runtime? Have you tried installing it as a normal dependency: npm install xml-js --save - instead of npm install xml-js --save-dev or moving it to the <dependencies> zone? Commented Dec 20, 2016 at 12:20
  • @OvidiuDolha: tried installing with --save but nothing changed. All the other modules are visible though, so I really can't guess what is happening here. If I try to force a main file in the systemjs config it throws another error though, like if it's trying to resolve another file. (it says it can't find lib.js, though lib is a directory, it looks like it is importing it as an ES6 module instead of regular nodejs ECMAscript5 one). Commented Dec 20, 2016 at 12:23
  • it is odd indeed... you could try installing it from the github repo and see if there's a difference, but probably not; also you could try mapping systemjs more direct: map: { 'xml-js': './node_modules/xml-js/index.js' } or even into its lib sub-folder map: { 'xml-js': './node_modules/xml-js/lib/index.js' } Commented Dec 20, 2016 at 12:33
  • @OvidiuDolha: Unluckily it still doesn't work and throws the same error. Surprisingly, now, regardless the module is mapped or not it throws me the error anyway, so my guess is that the problem is rather related to system-js itself looking for all the modules installed in node_modules. Commented Dec 20, 2016 at 14:35
  • @OvidiuDolha: I've found the issue: there is NO way to include xml-js with systemjs directly (at least not without relying on jspm). The reason is that systemjs does not support natively the modules format exported by nodejs. The only solution, to me, is to find another module which is "UDM" (universal module definition), so that you can import it regularly with no issues. Commented Dec 20, 2016 at 15:13

1 Answer 1

1

After a couple of hours of documentation and, being honest, disappointment, I've found out that you can't directly include node modules with systems, because systemjs cannot interprete them directly.

I had to change the whole library, and relied on this one: https://www.npmjs.com/package/jxon which says "A complete, bidirectional, JXON (lossless JavaScript XML Object Notation) library. Packed as UMD.". I've check what "UMD" means, which means "Universal Module Definition": https://github.com/umdjs/umd

So, you likely can use the UMD tools to wrap the modules in your application, else you can rely on existing ones available somewhere.

In my case, using jxon, I had to change my code a bit:

  1. First of all, in package.json I've removed xml-js and added jxon
  2. In my systemjs.config.js file I've added the module in the map list (along with the other ones): 'jxon':'npm:jxon'
  3. Still in the systemjs.config.js file, I had to tell in the "packages" section that the defaultextension was JS and that the main file was jxon.min.js: packages: { jxon: { defaultExtension: 'js', main: 'jxon.min.js' } }
  4. Last but not least, I could include it regularly in my typescript file with no errors, and could use the prototypes it offered to accomplish my goals (I've required it using "require", not "import", but it should work aswell with something like import * as jxonparser from 'jxon', though I've used: const jxon_parser = require('jxon');

So, in a very concise nutshell: you can't include node modules with systemjs unless they are either as UMD or that can be interpreted from systemjs. If you want to check the formats supported by systemjs, check this: https://github.com/systemjs/systemjs/blob/master/docs/module-formats.md

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.