user3564855 user3564855 -3 years ago 212
TypeScript Question

Typescript Module + Webpack + RequireJS

Working on my first typescript module, which I hope to be able to use in both an Apache Cordova app, and a .Net 4.6 MVC site (for now). After doing exhaustive reading I came to the conclusion that CommonJS would suit my needs best. However I'm struggling to integrate the module into the MVC site.

I'm using webpack with awesome-typescript-loader to bundle my module into a single js file, and then I am using requirejs to load the module onto the MVC site. I have attempted multiple ways to import the module with no success.

Within my typescript module I have a single point of entry (index.ts), in which I am ONLY exporting the main class:

export * from './src/engine';
, and I am using this class as my entry point within webpack:

const path = require('path');
const webpack = require('webpack');
const merge = require('webpack-merge');
const CheckerPlugin = require('awesome-typescript-loader').CheckerPlugin;

module.exports = (env) => {
// Configuration in common to both client-side and server-side bundles
const isDevBuild = false;
const sharedConfig = {
stats: { modules: false },
context: __dirname,
resolve: { extensions: ['.ts', '.tsx'] },
output: {
filename: '[name].js',
publicPath: '/dist/' // Webpack dev middleware, if enabled, handles requests for this URL prefix
},
module: {
loaders: [
{
test: /\.tsx?$/,
loader: 'awesome-typescript-loader'
}
]
},
plugins: [
new CheckerPlugin()
]
};

// Configuration for client-side bundle suitable for running in browsers
const clientBundleOutputDir = './dist';
const clientBundleConfig = merge(sharedConfig, {
entry: { 'engine': './index.ts' },
output: { path: path.join(__dirname, clientBundleOutputDir) },
plugins: [
new webpack.ContextReplacementPlugin(/moment[\\\/]locale$/, /^\.\/(en)$/)
].concat(isDevBuild ? [
// Plugins that apply in development builds only
new webpack.SourceMapDevToolPlugin({
filename: '[file].map', // Remove this line if you prefer inline source maps
moduleFilenameTemplate: path.relative(clientBundleOutputDir, '[resourcePath]') // Point sourcemap entries to the original file locations on disk
})
] : [
// Plugins that apply in production builds only
new webpack.optimize.UglifyJsPlugin()
])
});

return [clientBundleConfig];
};


Once I have the resultant engine.js file I am using requirejs on the MVC site to load the module:

<script data-main="/scripts/main" src="~/Scripts/require.js"></script>


main.js

require(['/scripts/compliance-engine.js']);


With the final aim being that I can call
var compliance = require('compliance-engine');
from javascript, instantiating a new instance of the engine.

Sadly no matter what I try I am unable to get the above working to completion (no errors are thrown at any point, I just can't reference the module on the site).

Answer Source

When using webpack NOTHING is exported unless you explicitly define it, you should add this to your webpack.config.js

output: {
 library: 'MyLibrary'
 libraryTarget: 'var',
}

This will put a variable named MyLibrary on the window and it can be accessed from your other code. There are other options to libraryTarget like umd/amd etc. you can read about it here

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download