Giter Club home page Giter Club logo

applicationinsights-node.js's Introduction

Application Insights for Node.js

npm version

An experimental / beta version of the SDK is also available. It is built on top of OpenTelemetry, more information about beta version available here.

npm install applicationinsights@beta

Azure Application Insights monitors your backend services and components after you deploy them to help you discover and rapidly diagnose performance and other issues. Add this SDK to your Node.js services to include deep info about Node.js processes and their external dependencies such as database and cache services. You can use this SDK for your Node.js services hosted anywhere: your datacenter, Azure VMs and Web Apps, and even other public clouds.

This library tracks the following out-of-the-box:

You can manually track more aspects of your app and system using the API described in the Track custom telemetry section.

Supported Node.JS versions

Platform Version Supported
Node.JS v18
Node.JS v17
Node.JS v16
Node.JS v15
Node.JS v14
Node.JS v12
Node.JS v10
Node.JS v8

Getting Started

Important: On March 31st, 2025, support for instrumentation key ingestion will end. Instrumentation key ingestion will continue to work, but we’ll no longer provide updates or support for the feature. Transition to connection strings to take advantage of new capabilities.

  1. Create an Application Insights resource in Azure by following these instructions.
  2. Grab the Connection String from the resource you created in step 1. Later, you'll either add it to your app's environment variables or use it directly in your scripts.
  3. Add the Application Insights Node.js SDK to your app's dependencies and package.json:
    npm install --save applicationinsights

    Note: If you're using TypeScript, please install @types/node package to prevent build issues, this npm package contains built-in typings.

  4. As early as possible in your app's code, load the Application Insights package:
    let appInsights = require('applicationinsights');
  5. Configure the local SDK by calling appInsights.setup('YOUR_CONNECTION_STRING');, using the connection string you grabbed in step 2. Or put it in the APPLICATIONINSIGHTS_CONNECTION_STRING environment variable and call appInsights.setup() without parameters.

    For more configuration options see below.

  6. Finally, start automatically collecting and sending data by calling appInsights.start();.

Basic Usage

Important: applicationinsights must be setup and started before you import anything else. There may be resulting telemetry loss if other libraries are imported first.

For out-of-the-box collection of HTTP requests, popular third-party library events, unhandled exceptions, and system metrics:

let appInsights = require("applicationinsights");
appInsights.setup("YOUR_CONNECTION_STRING").start();
  • If the connection string is set in the environment variable APPLICATIONINSIGHTS_CONNECTION_STRING, .setup() can be called with no arguments. This makes it easy to use different connection strings for different environments.

Load the Application Insights library (i.e. require("applicationinsights")) as early as possible in your scripts, before loading other packages. This is needed so that the Application Insights library can prepare later packages for tracking. If you encounter conflicts with other libraries doing similar preparation, try loading the Application Insights library after those.

Because of the way JavaScript handles callbacks, additional work is necessary to track a request across external dependencies and later callbacks. By default this additional tracking is enabled; disable it by calling setAutoDependencyCorrelation(false) as described in the Configuration section below.

Azure Functions

Auto correlation in Azure Functions is supported automatically starting in 2.4.0, if using previous version following code should be added to handle the correlation available in Azure Functions environment.

...

// Default export wrapped with Application Insights FaaS context propagation
export default async function contextPropagatingHttpTrigger(context, req) {
    // Start an AI Correlation Context using the provided Function context
    const correlationContext = appInsights.startOperation(context, req);

    // Wrap the Function runtime with correlationContext
    return appInsights.wrapWithCorrelationContext(async () => {
        const startTime = Date.now(); // Start trackRequest timer

        // Run the Function
        const result = await httpTrigger(context, req);

        // Track Request on completion
        appInsights.defaultClient.trackRequest({
            name: context.req.method + " " + context.req.url,
            resultCode: context.res.status,
            success: true,
            url: req.url,
            time: new Date(startTime),
            duration: Date.now() - startTime,
            id: correlationContext.operation.parentId,
        });
        appInsights.defaultClient.flush();

        return result;
    }, correlationContext)();
};

Configuration

The appInsights object provides a number of methods to setup SDK behavior. They are listed in the following snippet with their default values.

let appInsights = require("applicationinsights");
appInsights.setup("<YOUR_CONNECTION_STRING>")
    .setAutoDependencyCorrelation(true)
    .setAutoCollectRequests(true)
    .setAutoCollectPerformance(true, true)
    .setAutoCollectExceptions(true)
    .setAutoCollectDependencies(true)
    .setAutoCollectConsole(true, false)
    .setUseDiskRetryCaching(true)
    .setAutoCollectPreAggregatedMetrics(true)
    .setSendLiveMetrics(false)
    .setAutoCollectHeartbeat(false)
    .setAutoCollectIncomingRequestAzureFunctions(true)
    .setInternalLogging(false, true)
    .setDistributedTracingMode(appInsights.DistributedTracingModes.AI_AND_W3C)
    .enableWebInstrumentation(false)
    .start();

Please review their descriptions in your IDE's built-in type hinting, or applicationinsights.ts for detailed information on what these control, and optional secondary arguments.

Note that by default setAutoCollectConsole is configured to exclude calls to console.log (and other console methods). By default, only calls to supported third-party loggers (e.g. winston, bunyan) will be collected. You can change this behavior to include calls to console methods by using setAutoCollectConsole(true, true).

Note that by default enableWebInstrumentation will use the connection string for SDK initialization. If you want to use a different one, you can set it as enableWebInstrumentation(true, "your-connection-string").

The TelemetryClient object contains a config property with many optional settings. These can be set as follows:

client.config.PROPERTYNAME = VALUE;

These properties are client specific, so you can configure appInsights.defaultClient separately from clients created with new appInsights.TelemetryClient().

Property Description
instrumentationKey Application Insights Instrumentation Key
endpointUrl The ingestion endpoint to send telemetry payloads to
proxyHttpUrl A proxy server for SDK HTTP traffic (Optional, Default pulled from http_proxy environment variable)
proxyHttpsUrl A proxy server for SDK HTTPS traffic (Optional, Default pulled from https_proxy environment variable)
maxBatchSize The maximum number of telemetry items to include in a payload to the ingestion endpoint (Default 250)
maxBatchIntervalMs The maximum amount of time to wait to for a payload to reach maxBatchSize (Default 15000)
disableAppInsights A flag indicating if telemetry transmission is disabled (Default false)
samplingPercentage The percentage of telemetry items tracked that should be transmitted (Default 100)
correlationIdRetryIntervalMs The time to wait before retrying to retrieve the id for cross-component correlation (Default 30000)
correlationHeaderExcludedDomains A list of domains to exclude from cross-component correlation header injection (Default See Config.ts)
ignoreLegacyHeaders Disable including legacy headers in outgoing requests, x-ms-request-id
distributedTracingMode Sets the distributed tracing modes (Default=AI)
enableAutoCollectExternalLoggers Sets the state of console. If true logger activity will be sent to Application Insights
enableAutoCollectConsole Sets the state of logger tracking (enabled by default for third-party loggers only). If true, logger auto collection will include console.log calls (default false)
enableLoggerErrorToTrace Sets tracking error logs from loggers (console, bunyan, and winston) as traces. If true errors will be returned as traces. By default errors are returned as exceptions and non-error properties will not be tracked.
enableAutoCollectExceptions Sets the state of exception tracking (enabled by default). If true uncaught exceptions will be sent to Application Insights
enableAutoCollectPerformance Sets the state of performance tracking (enabled by default). If true performance counters will be collected every second and sent to Application Insights
enableAutoCollectExtendedMetrics Sets the state of performance tracking (enabled by default). If true, extended metrics counters will be collected every minute and sent to Application Insights
enableAutoCollectPreAggregatedMetrics Sets the state of pre aggregated metrics tracking (enabled by default). If true pre aggregated metrics will be collected every minute and sent to Application Insights
enableAutoCollectHeartbeat Sets the state of request tracking (enabled by default). If true HeartBeat metric data will be collected every 15 minutes and sent to Application Insights
enableAutoCollectRequests Sets the state of request tracking (enabled by default). If true requests will be sent to Application Insights
enableAutoCollectDependencies Sets the state of dependency tracking (enabled by default). If true dependencies will be sent to Application Insights
enableAutoDependencyCorrelation Sets the state of automatic dependency correlation (enabled by default). If true dependencies will be correlated with requests
enableAutoCollectIncomingRequestAzureFunctions Enable automatic incoming request tracking when running in Azure Functions (disabled by default).
enableUseAsyncHooks Sets the state of automatic dependency correlation (enabled by default). If true, forces use of experimental async_hooks module to provide correlation. If false, instead uses only patching-based techniques. If left blank, the best option is chosen for you based on your version of Node.js.
enableUseDiskRetryCaching If true events that occurred while client is offline will be cached on disk
enableResendInterval The wait interval for resending cached events.
enableMaxBytesOnDisk The maximum size (in bytes) that the created temporary directory for cache events can grow to, before caching is disabled.
enableInternalDebugLogging Enables debug and warning logging for AppInsights itself. If true, enables debug logging
enableInternalWarningLogging Enables debug and warning logging for AppInsights itself. If true, enables warning logging
enableSendLiveMetrics Enables communication with Application Insights Live Metrics. If true, enables communication with the live metrics service
disableAllExtendedMetrics Disable all environment variables set
extendedMetricDisablers Disable individual environment variables set. "extendedMetricDisablers": "..."
noDiagnosticChannel In order to track context across asynchronous calls, some changes are required in third party libraries such as mongodb and redis. By default ApplicationInsights will use diagnostic-channel-publishers to monkey-patch some of these libraries. This property is to disable the feature. Note that by setting this flag, events may no longer be correctly associated with the right operation.
noPatchModules Disable individual monkey-patches. Set noPatchModules to a comma separated list of packages to disable. e.g. "noPatchModules": "console,redis" to avoid patching the console and redis packages. The following modules are available: azuresdk, bunyan, console, mongodb, mongodb-core, mysql, redis, winston, pg, and pg-pool. Visit the diagnostic-channel-publishers' README for information about exactly which versions of these packages are patched.
noHttpAgentKeepAlive HTTPS without a passed in agent
httpAgent An http.Agent to use for SDK HTTP traffic (Optional, Default undefined)
httpsAgent An https.Agent to use for SDK HTTPS traffic (Optional, Default undefined)
aadTokenCredential Azure Credential instance to be used to authenticate the App. AAD Identity Credential Classes
enableWebInstrumentation Sets the state of automatic web Instrumentation (Optional, disabled by default). If true, web instrumentation will be enabled on valid node server http response with the connection string used for SDK initialization
webInstrumentationConnectionString Sets connection string used for web Instrumentation (Optional, Default undefined)
webInstrumentationSrc Sets web Instrumentation CDN url (Optional). see more details at ApplicationInsights JavaScript SDK
webInstrumentationConfig Sets web Instrumentation config (Optional). see more details at ApplicationInsights JavaScript SDK

All these properties except httpAgent, httpsAgent and aadTokenCredential could be configured using configuration file applicationinsights.json located under root folder of applicationinsights package installation folder, Ex: node_modules/applicationinsights. These configuration values will be applied to all TelemetryClients created in the SDK.

{
    "samplingPercentage": 80,
    "enableAutoCollectExternalLoggers": true,
    "enableAutoCollectExceptions": true,
    "enableAutoCollectHeartbeat": true,
    "enableSendLiveMetrics": true,
    ...
}
  

Custom JSON file could be provided using APPLICATIONINSIGHTS_CONFIGURATION_FILE environment variable.

process.env.APPLICATIONINSIGHTS_CONFIGURATION_FILE = "C:/applicationinsights/config/customConfig.json"

// Application Insights SDK setup....

Alternatively, instead of using a configuration file, you can specify the entire content of the JSON configuration via the environment variable APPLICATIONINSIGHTS_CONFIGURATION_CONTENT.

Sampling

By default, the SDK will send all collected data to the Application Insights service. If you collect a lot of data, you might want to enable sampling to reduce the amount of data sent. Set the samplingPercentage field on the Config object of a Client to accomplish this. Setting samplingPercentage to 100 (the default) means all data will be sent, and 0 means nothing will be sent.

If you are using automatic correlation, all data associated with a single request will be included or excluded as a unit.

Add code such as the following to enable sampling:

const appInsights = require("applicationinsights");
appInsights.setup("<YOUR_CONNECTION_STRING>");
appInsights.defaultClient.config.samplingPercentage = 33; // 33% of all telemetry will be sent to Application Insights
appInsights.start();

Multiple roles for multi-component applications

If your application consists of multiple components that you wish to instrument all with the same Instrumentation Key and still see these components as separate units in the Portal as if they were using separate Instrumentation Keys (for example, as separate nodes on the Application Map) you may need to manually configure the RoleName field to distinguish one component's telemetry from other components sending data to your Application Insights resource. (See Monitor multi-component applications with Application Insights (preview))

Use the following to set the RoleName field:

const appInsights = require("applicationinsights");
appInsights.setup("<YOUR_CONNECTION_STRING>");
appInsights.defaultClient.context.tags[appInsights.defaultClient.context.keys.cloudRole] = "MyRoleName";
appInsights.start();

Automatic web Instrumentation

For node server with configuration enableWebInstrumentation set to true or environment variable APPLICATIONINSIGHTS_WEB_INSTRUMENTATION_ENABLED = true, web Instrumentation will be enabled on node server response when all of the following requirements are met:

  • Response has status code 200.
  • Response method is GET.
  • Sever response has Content-Type html.
  • Server response must have both <head> and </head> Tags.
  • If response is compressed, it must have only one Content-Encoding type, and encoding type must be one of gzip, br or deflate.
  • Response does not contain current /backup web Instrumentation CDN endpoints. (current and backup Web Instrumentation CDN endpoints here)

web Instrumentation CDN endpoint can be changed by setting environment variable APPLICATIONINSIGHTS_WEB_INSTRUMENTATION_SOURCE = "web Instrumentation CDN endpoints". web Instrumentation connection string can be changed by setting environment variable APPLICATIONINSIGHTS_WEB_INSTRUMENTATION_CONNECTION_STRING = "web Instrumentation connection string"

Note: web Instrumentation may slow down server response time, especially when response size is large or response is compressed. For the case in which some middle layers are applied, it may result in web Instrumentation not working and original response will be returned.

Automatic third-party instrumentation

In order to track context across asynchronous calls, some changes are required in third party libraries such as mongodb and redis. By default ApplicationInsights will use diagnostic-channel-publishers to monkey-patch some of these libraries. This can be disabled by setting the APPLICATION_INSIGHTS_NO_DIAGNOSTIC_CHANNEL environment variable. Note that by setting that environment variable, events may no longer be correctly associated with the right operation. Individual monkey-patches can be disabled by setting the APPLICATION_INSIGHTS_NO_PATCH_MODULES environment variable to a comma separated list of packages to disable, e.g. APPLICATION_INSIGHTS_NO_PATCH_MODULES=console,redis to avoid patching the console and redis packages.

The following modules are available: azuresdk, bunyan, console, mongodb, mongodb-core, mysql, redis, winston, pg, and pg-pool. Visit the diagnostic-channel-publishers' README for information about exactly which versions of these packages are patched.

Automatic instrumentation for several Azure SDKs is also enabled, currently Cognitive Search, Communication Common and Cosmos DB SDKs are not supported. Javascript Azure SDKs

The bunyan, winston, and console patches will generate Application Insights Trace events based on whether setAutoCollectConsole is enabled. The rest will generate Application Insights Dependency events based on whether setAutoCollectDependencies is enabled. Make sure that applicationinsights is imported before any 3rd-party packages for them to be instrumented successfully.

Live Metrics

To enable sending live metrics of your app to Azure, use setSendLiveMetrics(true). Filtering of live metrics in the Portal is currently not supported.

Extended Metrics

Note: The ability to send extended native metrics was added in version 1.4.0

To enable sending extended native metrics of your app to Azure, simply install the separate native metrics package. The SDK will automatically load it when it is installed and start collecting Node.js native metrics.

npm install applicationinsights-native-metrics

Currently, the native metrics package performs autocollection of Garbage Collection CPU time, Event Loop ticks, and heap usage:

  • Garbage Collection: The amount of CPU time spent on each type of garbage collection, and how many occurrences of each type.
  • Event Loop: How many ticks occurred and how much CPU time was spent in total.
  • Heap vs Non-Heap: How much of your app's memory usage is in the heap or non-heap.

Distributed Tracing Modes

By default, this SDK will send headers understood by other applications/services instrumented with an Application Insights SDK. You can optionally enable sending/receiving of W3C Trace Context headers in addition to the existing AI headers, so you will not break correlation with any of your existing legacy services. Enabling W3C headers will allow your app to correlate with other services not instrumented with Application Insights, but do adopt this W3C standard.

const appInsights = require("applicationinsights");
appInsights
  .setup("<YOUR_CONNECTION_STRING>")
  .setDistributedTracingMode(appInsights.DistributedTracingModes.AI_AND_W3C)
  .start()

Track custom telemetry

You can track any request, event, metric or exception using the Application Insights client. Examples follow:

let appInsights = require("applicationinsights");
appInsights.setup().start(); // assuming connection string is in environment variables. start() can be omitted to disable any non-custom data
let client = appInsights.defaultClient;
client.trackEvent({name: "my custom event", properties: {customProperty: "custom property value"}});
client.trackException({exception: new Error("handled exceptions can be logged with this method")});
client.trackMetric({name: "custom metric", value: 3});
client.trackTrace({message: "trace message"});
client.trackDependency({target:"http://dbname", name:"select customers proc", data:"SELECT * FROM Customers", duration:231, resultCode:0, success: true, dependencyTypeName: "ZSQL"});
client.trackRequest({name:"GET /customers", url:"http://myserver/customers", duration:309, resultCode:200, success:true});
 
let http = require("http");
http.createServer( (req, res) => {
  client.trackNodeHttpRequest({request: req, response: res}); // Place at the beginning of your request handler
});

Note that custom properties are converted to their string representation before being sent, see Using properties for more information.

An example utility using trackMetric to measure how long event loop scheduling takes:

function startMeasuringEventLoop() {
  var startTime = process.hrtime();
  var sampleSum = 0;
  var sampleCount = 0;

  // Measure event loop scheduling delay
  setInterval(() => {
    var elapsed = process.hrtime(startTime);
    startTime = process.hrtime();
    sampleSum += elapsed[0] * 1e9 + elapsed[1];
    sampleCount++;
  }, 0);

  // Report custom metric every second
  setInterval(() => {
    var samples = sampleSum;
    var count = sampleCount;
    sampleSum = 0;
    sampleCount = 0;

    if (count > 0) {
      var avgNs = samples / count;
      var avgMs = Math.round(avgNs / 1e6);
      client.trackMetric({name: "Event Loop Delay", value: avgMs});
    }
  }, 1000);
}

Preprocess data with Telemetry Processors

public addTelemetryProcessor(telemetryProcessor: (envelope: Contracts.Envelope, context: { http.RequestOptions, http.ClientRequest, http.ClientResponse, Error, correlationContext }) => boolean)

You can process and filter collected data before it is sent for retention using Telemetry Processors. Telemetry processors are called one by one in the order they were added before the telemetry item is sent to the cloud.

If a telemetry processor returns false that telemetry item will not be sent.

All telemetry processors receive the telemetry data and its envelope to inspect and modify. They also receive a context object. The contents of this object is defined by the contextObjects parameter when calling a track method for manually tracked telemetry. For automatically collected telemetry, this object is filled with available request information and the persistent request context as provided by appInsights.getCorrelationContext() (if automatic dependency correlation is enabled).

The TypeScript type for a telemetry processor is:

telemetryProcessor: (envelope: ContractsModule.Contracts.Envelope, context: { http.RequestOptions, http.ClientRequest, http.ClientResponse, Error, correlationContext }) => boolean;

For example, a processor that removes stack trace data from exceptions might be written and added as follows:

function removeStackTraces ( envelope, context ) {
  if (envelope.data.baseType === "ExceptionData") {
    var data = envelope.data.baseData;
    if (data.exceptions && data.exceptions.length > 0) {
      for (var i = 0; i < data.exceptions.length; i++) {
        var exception = data.exceptions[i];
        exception.parsedStack = null;
        exception.hasFullStack = false;
      }
    }
    // Add extra properties
    var originalError = context["Error"];
    if(originalError && originalError.prop){
      data.properties = data.properties || {};
      data.properties.customProperty = originalError.prop;
    }
  }
  return true;
}

appInsights.defaultClient.addTelemetryProcessor(removeStackTraces);

More info on the telemetry API is available in the docs.

Use multiple Application Insights resources

You can create multiple Azure Application Insights resources and send different data to each by using their respective connection string. For example:

let appInsights = require("applicationinsights");

// configure auto-collection under one Connection String
appInsights.setup("<YOUR_CONNECTION_STRING>").start();

// track some events manually under another connection string
let otherClient = new appInsights.TelemetryClient("<YOUR_CONNECTION_STRING>");
otherClient.trackEvent({name: "my custom event"});

Examples

  • Track dependencies

    let appInsights = require("applicationinsights");
    let client = new appInsights.TelemetryClient();
    
    var success = false;
    let startTime = Date.now();
    // execute dependency call here....
    let duration = Date.now() - startTime;
    success = true;
    
    client.trackDependency({target:"http://dbname", name:"select customers proc", data:"SELECT * FROM Customers", duration:duration, resultCode:0, success: true, dependencyTypeName: "ZSQL"});
  • Assign custom properties to be included with all events

    appInsights.defaultClient.commonProperties = {
      environment: process.env.SOME_ENV_VARIABLE
    };
  • Manually track all HTTP GET requests

    Note that all requests are tracked by default. To disable automatic collection, call .setAutoCollectRequests(false) before calling start().

    appInsights.defaultClient.trackRequest({name:"GET /customers", url:"http://myserver/customers", duration:309, resultCode:200, success:true});

    Alternatively you can track requests using trackNodeHttpRequest method:

    var server = http.createServer((req, res) => {
      if ( req.method === "GET" ) {
          appInsights.defaultClient.trackNodeHttpRequest({request:req, response:res});
      }
      // other work here....
      res.end();
    });
  • Track server startup time

    let start = Date.now();
    server.on("listening", () => {
      let duration = Date.now() - start;
      appInsights.defaultClient.trackMetric({name: "server startup time", value: duration});
    });

Self-diagnostics

"Self-diagnostics" refers to internal logging from Application Insights Node.js SDK.

This functionality can be helpful for spotting and diagnosing issues with Application Insights itself.

By default, Application Insights Node.js SDK logs at warning level to console, following code demonstrate how to enable debug logging as well and generate telemetry for internal logs:

let appInsights = require("applicationinsights");
appInsights.setup("<YOUR_CONNECTION_STRING>")
    .setInternalLogging(true, true) // Enable both debug and warning logging
    .setAutoCollectConsole(true, true) // Generate Trace telemetry for winston/bunyan and console logs
    .start();

Debug Logs could be enabled as well using APPLICATION_INSIGHTS_ENABLE_DEBUG_LOGS environment variable, and APPLICATION_INSIGHTS_DISABLE_WARNING_LOGS environment variable to disable warnings. Logs could be put into local file using APPLICATIONINSIGHTS_LOG_DESTINATION environment variable, supported values are file and file+console, a file named applicationinsights.log will be generated on tmp folder by default, including all logs, /tmp for *nix and USERDIR/AppData/Local/Temp for Windows. Log directory could be configured using APPLICATIONINSIGHTS_LOGDIR environment variable.

process.env.APPLICATIONINSIGHTS_LOG_DESTINATION = "file";
process.env.APPLICATIONINSIGHTS_LOGDIR = "C:/applicationinsights/logs"

// Application Insights SDK setup....

Branches

  • Ongoing development takes place on the develop branch. Please submit pull requests to this branch.
  • Releases are merged to the master branch and published to npm.

Contributing

This project welcomes contributions and suggestions. Most contributions require you to agree to a Contributor License Agreement (CLA) declaring that you have the right to, and actually do, grant us the rights to use your contribution. For details, visit https://cla.microsoft.com.

When you submit a pull request, a CLA-bot will automatically determine whether you need to provide a CLA and decorate the PR appropriately (e.g., label, comment). Simply follow the instructions provided by the bot. You will only need to do this once across all repositories using our CLA.

This project has adopted the Microsoft Open Source Code of Conduct. For more information see the Code of Conduct FAQ or contact [email protected] with any additional questions or comments.

Data Collection

As this SDK is designed to enable applications to perform data collection which is sent to the Microsoft collection endpoints the following is required to identify our privacy statement.

The software may collect information about you and your use of the software and send it to Microsoft. Microsoft may use this information to provide services and improve our products and services. You may turn off the telemetry as described in the repository. There are also some features in the software that may enable you and Microsoft to collect data from users of your applications. If you use these features, you must comply with applicable law, including providing appropriate notices to users of your applications together with a copy of Microsoft’s privacy statement. Our privacy statement is located at https://go.microsoft.com/fwlink/?LinkID=824704. You can learn more about data collection and use in the help documentation and our privacy statement. Your use of the software operates as your consent to these practices.

Trademarks

This project may contain trademarks or logos for projects, products, or services. Authorized use of Microsoft trademarks or logos is subject to and must follow Microsoft’s Trademark & Brand Guidelines. Use of Microsoft trademarks or logos in modified versions of this project must not cause confusion or imply Microsoft sponsorship. Any use of third-party trademarks or logos are subject to those third-party’s policies.

License

MIT

applicationinsights-node.js's People

Contributors

alexbulankou avatar apokalypt avatar asklar avatar christopheranderson avatar dependabot[bot] avatar ejizba avatar gzepeda avatar hajohn avatar hectorhdzg avatar jackhorton avatar jacksonweber avatar jasongin avatar joshgav avatar karlie-777 avatar lgodmer avatar lukehoban avatar lukekim avatar markwolff avatar martincostello avatar mslaguana avatar osvaldorosado avatar pavelustinovms avatar ramthi avatar sergey-shandar avatar southwood avatar spike008t avatar t-andrea avatar tolu avatar willmorgan avatar xiao-lix avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

applicationinsights-node.js's Issues

Collect system metrics

I just realized the require("os"); module provides a way to track cpu/memory/network.

https://nodejs.org/api/os.html

The application insights user interface now supports custom metrics so the idea here is to collect custom metrics to capture system performance. This will be exposed similar to appInsights.trackAllHttpServerRequets, maybe appInsights.trackSystemMetrics() and it will capture aggregate metrics at a configurable interval.

App hangs after trackEvent is called

Run the code below and the app won't exit after console.log()

var appInsights = require("applicationinsights");

var c = appInsights.getClient("key");
c.trackEvent('some event', {'version': 'foo'});
console.log('All done'); 

Clients should not share a sequence number.

Currently, clients share a sequence number counter:

class Client { 
    private static _sequencePrefix = 
        Util.int32ArrayToBase64([ 
            Util.random32(), 
            Util.random32(), 
            Util.random32(), 
            Util.random32()]) + 
        ":"; 
    private static _sequenceNumber = 0;
    //...
}

The sequence number should be unique for each client.

Update TravisCI badge

The TravisCI badge on the home page points to the fork I created a few weeks ago. It would be better to enable TravisCI for the main repo and update the badge to point to that.

Unhandled exception tracking doesn't work in node 0.12

This used to work in 0.10 (and I think 0.11), but in 0.12 the process exits before the post request is able to transmit data (https://github.com/Microsoft/AppInsights-node.js/blob/master/applicationInsights.ts#L138-L147).

I don't think there's a good way to fix this, the Error should be re-thrown immediately after it is tracked to avoid letting the app continue in an unstable state. It might work to do a synchronous file stream write before re-throwing the error, then reading the data from disk when the app starts.

I'm leaving it as-is since people might be using it in older versions of node without issue, but it would be good to find a better long-term solution.

Unable to properly setup App Insight logging to Azure Portal

I have a Node app running on my localhost, and I'm receiving the following error when I invoke my trackEvent method. Not sure if there's a limitation with using app insight via browserify, as Im able to write logs to my instance when I run the same code below in my server.js script.

Fetch API cannot load http://dc.services.visualstudio.com/v2/track. Request header field content-encoding is not allowed by Access-Control-Allow-Headers in preflight response.
index.debug.js:1245 ApplicationInsights:Sender [TypeError: Failed to fetch
at TypeError (native)]0: TypeError: Failed to fetch
at TypeError (native)length: 1__proto__: Array[0]

Here's my code.

import appInsights from 'applicationinsights';
import env_properties from '../../config';

setupLogging(){
appInsights.setup(env_properties.APPINSIGHTS_INSTRUMENTATIONKEY).start();
appInsights.client.trackEvent("login", {message: "Logging worked"});
},

Here's the outputted request header from verbose logging
headers: Object
Content-Encoding: "gzip"
Content-Length: 473
Content-Type: "application/x-json-stream"

support TrackPageView()?

Hi,
I am using the library in my client side node.js project and I need to track the pageview data. However, I found this function is not implemented in the latest version('0.15.11') yet.
Wondering if there is a plan to implement this function? Is there a workaround for the current version?

Operation name missing in portal when calling trackDependency

I'm calling trackDependency to track calls to Azure Storage and although I'm passing an operation name as the second parameter it's not appearing in the portal:

metricsClient.trackDependency(blobService.host.primaryHost, 'listBlobsSegmented', (new Date().getTime() - started), !err);

screen shot 2015-11-30 at 1 05 18 pm

Requests and Traces aren't related in Application Insights

This could be something I'm doing wrong, but the following results in a request and a trace being logged in Application Insights - but for neither of those to be related to the other (not showing in 'Related Items').

appInsights.trackRequest(req, res);
appInsights.trackTrace(JSON.stringify(trace));

Insights cookies not sent with tracking functions

It appears that the trackEvent function (as well as others) are not sending the session cookies to App Insights with the event.

Ex. I have a App Insights configured on the browser of a webpage served up by node. The client side script creates the ai_session and ai_user cookies. When I post that form, I get those cookies back in the form post on the server, but the event tracking isn't identifying those cookies automatically like when I use the C# package for App Insights.

Is there another way to send the App Insights cookies through the trackEvent function so that I can tie my end user's page view and server telemetry together? Should it be set as metadata?

Documentation says that the trackException method takes a third parameter named measurements, but it is not actually defined in the method definition

https://github.com/Microsoft/ApplicationInsights-node.js/blob/master/Library/Client.ts#L88

/**
     * Log an exception you have caught.
     * @param   exception   An Error from a catch clause, or the string error message.
     * @param   properties  map[string, string] - additional data used to filter events and metrics in the portal. Defaults to empty.
     * @param   measurements    map[string, number] - metrics associated with this event, displayed in Metrics Explorer on the portal. Defaults to empty.
     */
    public trackException(exception:Error, properties?:{ [key: string]: string; }) {
        if(!Util.isError(exception)) {
            exception = new Error(<any>exception);
        }

        var data = ExceptionTracking.getExceptionData(exception, true, properties)
        this.track(data);
    }

Sampling

Is it possibile to enable sampling?

Exceptions are stored on disk even if offline mode is off and are never sent

I've noticed this odd (probably wrong) behavior associated to the AutoCollection of Exceptions. In a brief: if "enableOfflineMode" if off, unhandled exceptions are not sent and pile up on disk.

Details follow:
If AutoCollection is enabled, all uncaught exceptions are trapped by "uncaughtException" event on the process. This causes the exception data to be sent to "handleCrash" method on Channel object with "isNodeCrashing" set to true. "handleCrash" sends the exception data to "saveOnCrash" and this method does not check if "_enableOfflineMode" is true. It just stores on disk.

If "_enableOfflineMode" if false, 2 (bad) things happen: Files are stored on disk even if this functionality is off. It may still make sense, since it's the only way to make unhandled exception collection work. But since "_enableOfflineMode" is false, files stored on disk are never sent.

So, ultimately:

  1. Files will pile up forever on disk
  2. Unhandled Exceptions will not be sent

Maybe it would be better to:

  1. Not store exceptions to disk, since they will not be sent. It may happen that on first run offline mode is off, then switched on later. But its an odd scenario. If this is not the case, Exception files will be piled up forever.
  2. Try to send exceptions (only) on next start even if offline mode is off.

What do you think?

Auto collected CPU metric is rejected by app insights endpoint

The CPU metrics being sent by the node sdk are being rejected by the app insights endpoint.
If you enable verbose logging you can see this response from the endpoint:
WaWorkerHost.exe Information: 0 : ApplicationInsights:Sender [ '{"itemsRecieved":58,"itemsAccepted":42,"errors":[{"index":0,"statusCode":400,"message":"Metric at index[0] '% cpu[0] user' name contains invalid character '['"},{"index":1,"statusCode":400,"message":"Metric at index[0] '% cpu[1] user' name contains invalid character '['"},{"index":2,"statusCode":400,"message":"Metric at index[0] '% cpu[2] user' name contains invalid character '['"},{"index":3,"statusCode":400,"message":"Metric at index[0] '% cpu[3] user' name contains invalid character '['"},{"index":4,"statusCode":400,"message":"Metric at index[0] '% cpu[4] user' name contains invalid character '['"},{"index":5,"statusCode":400,"message":"Metric at index[0] '% cpu[5] user' name contains invalid character '['"},{"index":6,"statusCode":400,"message":"Metric at index[0] '% cpu[6] user' name contains invalid character '['"},{"index":7,"statusCode":400,"message":"Metric at index[0] '% cpu[7] user' name contains invalid character '['"},{"index":29,"statusCode":400,"message":"Metric at index[0] '% cpu[0] user' name contains invalid character '['"},{"index":30,"statusCode":400,"message":"Metric at index[0] '% cpu[1] user' name contains invalid character '['"},{"index":31,"statusCode":400,"message":"Metric at index[0] '% cpu[2] user' name contains invalid character '['"},{"index":32,"statusCode":400,"message":"Metric at index[0] '% cpu[3] user' name contains invalid character '['"},{"index":33,"statusCode":400,"message":"Metric at index[0] '% cpu[4] user' name contains invalid character '['"},{"index":34,"statusCode":400,"message":"Metric at index[0] '% cpu[5] user' name contains invalid character '['"},{"index":35,"statusCode":400,"message":"Metric at index[0] '% cpu[6] user' name contains invalid character '['"},{"index":36,"statusCode":400,"message":"Metric at index[0] '% cpu[7] user' name contains invalid character '['"}]}' ]

Device Id is always node

It would be nice if Device Id could identify instances of the application running from the same device. "node" is not unique enough to group events coming from multiple instances running on different devices.

trackMetric does not support setting custom properties

Unlike the .NET (or browser JavaScript) library, this library does not allow you to pass in additional properties to the .trackMetric function.

You can do it for the other types of telemetry like events and dependencies, but not metrics.

ContractsModule.Contracts.MetricData object has a spot for properties, so doesn't seem like it would break the model.

How to get severity level values

Hi,
I'm working on a transport for Winston logger and I'd like to map Winston log levels to AI's trace levels. I've seen an enumeration of supported levels in the "Contracts" module, but I am not sure on how to extract those values for using in my code. What's the suggested way?
Thanks!

Cannot find module applicationinsights

After running npm install applicationinsights, I get the following error:

  • test.js
var ai = require('applicationinsights')
>node test.js
module.js:338
    throw err;
          ^
Error: Cannot find module 'applicationinsights'
    at Function.Module._resolveFilename (module.js:336:15)
    at Function.Module._load (module.js:278:25)
    at Module.require (module.js:365:17)
    at require (module.js:384:17)
    at Object.<anonymous> (C:\cb\td\win8\temp\test.js:1:72)
    at Module._compile (module.js:460:26)
    at Object.Module._extensions..js (module.js:478:10)
    at Module.load (module.js:355:32)
    at Function.Module._load (module.js:310:12)
    at Function.Module.runMain (module.js:501:10)

Device.Id in metrics

Hi,
I've added a tag to my client context for setting my custom device id. It works well on traces, but I don't see the device id as a grouping criteria in metrics. Is it supported and correctly sent in metrics?
Thanks!

trackMetric not working

For some reason I can't get trackMetric to work.
My code is something like

var appInsights = require("applicationinsights");
appInsights.setup("<id>").start();

appInsights.client.trackEvent("Hello World");        
appInsights.client.trackMetric("RegisteredPushChannels", Math.random * 1000);

The event Hello World shows up but I cannot find anywhere RegisteredPushChannels in the Metrics Explorer.

Any ideas?

Best regards

Ferdinand

Cannot track request with custom properties determined during request processing

In our node server we collect various properties about the request throughout processing and place them in a context object. Whenever we log any app insights telemetry we add this context to the custom property bag. The only type for which this doesn't work is requests.

For requests tracking, we want to do something like this:

var context;
// process the request and add items to logging context throughout the pipeline
response.on('finish', function() {
    appInsights.client.trackrequest(request, response, context);
});

Unfortunately this doesn't work because in the trackRequest implementation it actually listens for the response.on('finish') event which has already fired at this point. Here's the relevant snippet from the trackRequest method in the sdk:

if (response && response.once) {
    response.once("finish", function () { return processRequest(); });
}

Additionally we want to set the operationId, userId, and operationParentId to our own custom values so we can correlate the request telemetry with other telemetry from inside and outside this application:

appInsights.client.context.tags[appInsights.client.context.keys.operationId] = loggingContext.requestId;
appInsights.client.context.tags[appInsights.client.context.keys.userId] = loggingContext.userId;
appInsights.client.context.tags[appInsights.client.context.keys.operationParentId] = loggingContext.clientRequestId;

But this doesn't work because the request is actually logged asynchronously and this context could have been reset by another request at that point.

I'm open to suggestions on how to implement this either in our client, or in the SDK itself. I think we basically need a trackRequest method that is synchronous.

Provide a sync flush call

If an application immediately shuts down after logging an event, for example, it can happen that the events are dropped and never written to disk for later submission. It seems that there is a sync implementation of it, but it is not exposed in the API.

If it were, we could always call that method when listening on process exit: process.on('exit'...

Dispose not removing timers and exception handlers

As per subject, the public "dispose()" method in the main ApplicationInsights class calls "dispose()" on each internal static instances of console, exceptions, performance and requests. But in the implementation of those methods, not all resources are released. As an example:

https://github.com/Microsoft/ApplicationInsights-node.js/blob/master/AutoCollection/Exceptions.ts

class AutoCollectExceptions {
...
    public enable(isEnabled: boolean) {
        if(isEnabled) {
...
                process.on("uncaughtException", this._exceptionListenerHandle);
            }
        } else {
...
                process.removeListener("uncaughtException", this._exceptionListenerHandle);
...
            }
        }
    }

    public dispose() {
        AutoCollectExceptions.INSTANCE = null;
        // <<<<---- What about calling "this.enable(false)" here?
        this._isInitialized = false;
    }

Same goes for performance.

In my tests I use the "dispose()" method to reset AI's SDK to a pristine state. This is required because AI creates a global singleton and even reloading it with another require(), the same instance is returned due to node's module caching.
After some tests, node complains about an handler leek because handlers are added on each test.

My suggestion is to call "enable(false)" in the dispose call if you agree. I can make a PR for this if you like.

Exception type and failed method incorrect for objects that are instances of Error subclass

Some modules (example) subclass Error. When obj is an instance of such, Util.isError(...) returns false.

// "[object Object]" !== "[object Error]"
return Object.prototype.toString.call(obj) === "[object Error]";

This issue causes the "Exception type" and "Failed method" properties in Azure Portal's Application Insights blade to display the error type and method name from this line in the Application Insights SDK for Node.js:

Error at Client.trackException

...instead of from the original error. Example:

OriginalErrorTypeName at originalFunctionName

I believe the implementation of Util.isError(...) should be:

return obj instanceof Error;

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.