Your data. Anywhere you go.

New Relic for iOS or Android


Download on the App Store    Android App on Google play


New Relic Insights App for iOS


Download on the App Store


Learn more

Close icon

Relic Solution: Webpack workaround via externals and instrumentLoadedModule

levelup
relicsolutions
webpack

#1

webpack tends to bypass the usual module loading system, which is where the Node agent hooks in to apply instrumentation (more details in our webpack level up post here). While webpack is not officially supported, we do recognize the popularity of webpack. You may be able to get data to successfully report to New Relic by configuring the agent as an external and global, then using our instrumentLoadedModule() API call as a workaround.

We recently released the instrumentLoadedModule API call which “…allows you to add stock instrumentation to specific modules in situations where it’s impossible to have require('newrelic'); as the first line of your app’s main module.”(Docs link here).

The following example shows how the API call can be used to get an Express application using webpack to report:

  1. First, you will need a file that loads your bundled file, in the example below those files are index.js and bundle.js respectively. Since the agent is configured to be an external in webpack, it is assumed to be exposed to the script globally - this allows the agent to load properly by the usual means. This can be achieved with the following code:
//index.js

global.newrelic = require('newrelic'); // Expose the agent in the global scope
require('./bundle.js'); // Load the output of the webpack build
  1. Next you will need to set newrelic as an external in your webpack.config.js file:
//webpack.config.js

module.exports = {
entry: './app.js',
target: 'node',
output: {
path: __dirname,
filename: 'bundle.js'
},
externals: {
newrelic: 'newrelic'
}
};
  1. You will need to use the instrumentLoadedModule() API call in your to-be-bundled application like so. Please note that the API call must be inserted after the module is required but before any of the module’s functionality is used:
//app.js

const express = require('express');
newrelic.instrumentLoadedModule(
'express', // the module's name, as a string
express // the module instance
);
const app = express();
…

Once all the above steps have been implemented you will need to re-bundle your application. After it finishes bundling go ahead and start your application via node index.js and after a few minutes, you should see data reporting in the express namespace in your transactions.

Important Deployment Note:

You need to deploy your unbundled node_modules folder with this method or you will run into instrumentation issues.

Other Notes:

The instrumentLoadedModule cannot instrument any arbitrary module. Its purpose is to register modules that were missed because the agent was not able to instrument while loading (e.g. agent was loaded late, or usual loading methods are circumvented a la webpack, etc). The instrumentLoadedModule method can only instrument modules the agent would normally instrument.

You can see a list of these modules in the agent’s lib/instrumentations.js module here.

To officially support webpack, please submit your input to our feature idea thread here:

instrumentLoadedModule public docs:

Node.js Agent and webpack Level-up post:


Getting strange error when building with gitlab and docker