9

I would like to create a library that can be used in both - browser and nodejs. For the sake of the argument let's say this is my library:

export default class MyClass {
    public getString(): string {
        return "Message";
    }
}

ES2015 modules are not supported by browsers as of now and I don't want to depend on requirejs or any other module loader when in browser - I would like this library to be consumed just by including the generated .js file using the script tag. It feels that what I want can be achieved by using internal modules (I don't want to pollute the global namespace). However when I wrap my code in namespace/module I am having a hard time to get it compiled to as commonjs module.

What is the proper way of achieving what I want? Or, may be, I am getting completely off the rails here being a typescript and javascript noob?

1
  • 1
    Please explain downvotes. It is fine to downvote as long as I know why - I am trying to learn. (also jquery does seem to do what I want as per https://www.npmjs.com/package/jquery so maybe it's not completely off the rails?) Commented Nov 22, 2016 at 18:56

1 Answer 1

10

I think what you need is UMD. With tsconfig.json containing

{
  "compilerOptions": {
    "module": "umd"
  },
}

generated JavaScript will look like this:

(function (factory) {
        if (typeof module === 'object' && typeof module.exports === 'object') {
            var v = factory(require, exports); if (v !== undefined) module.exports = v;
        }
        else if (typeof define === 'function' && define.amd) {
            define(["require", "exports"], factory);
        }
    })(function (require, exports) {
        "use strict";
        var MyClass = (function () {
            function MyClass() {
            }
            MyClass.prototype.getString = function () {
                return "Message";
            };
            return MyClass;
        }());
        exports.__esModule = true;
        exports["default"] = MyClass;
    });

It works in node (CommonJS) as well as with browsers (CommonJS, AMD). To allow users of your library to just include it through script tag, you need module bundler like Webpack, Browserify or Rollup. Those will produce UMD definition with global export, so default export of main file of your library will be available as some variable in global scope.

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

5 Comments

I tried umd but did not postprocess it with webpack/browserify. I will give it a try.
Looks like with browserify I can create a bundle for all the scripts. I would like to 'bundle' only my library.
What file do you try to "browserify"? Entry point of your library, right?
Got it - I did not use the --standalone and could not make things work.
Can you add a clarification on how to use one of these module bundlers in this case?

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.