1. Install Laminar

npm add @lmnr-ai/lmnr

2. Initialize Laminar

We suggest to disable Next.js OpenTelemetry instrumentation to avoid excessive tracing.

export NEXT_OTEL_FETCH_DISABLED=1

Observing entire application

To instrument your entire Next.js app, place Laminar initialization in instrumentation.ts file. Learn more about instrumentation.ts here.

instrumentation.ts
export async function register() {
  // prevent this from running in the edge runtime
  if (process.env.NEXT_RUNTIME === 'nodejs') {

    const { Laminar } = await import('@lmnr-ai/lmnr');
    Laminar.initialize({
      projectApiKey: process.env.LMNR_API_KEY,
    });
  }
}

instrumentation.ts is experimental in Next.js < 15.

If you use Next.js < 15, add the following to your next.config.js:

next.config.js
module.exports = {
    experimental: { instrumentationHook: true }
};

Observing specific routes

If you want to instrument a specific app router route, initialize Laminar at the top of your route file.

import { Laminar } from '@lmnr-ai/lmnr';

Laminar.initialize({ projectApiKey: process.env.LMNR_PROJECT_API_KEY });

Simple initialization may not work for all cases.

The best workaround is to selectively pass instrumentModules to .initialize(). The example below shows how to do this for OpenAI and Anthropic.

app/.../route.ts
import OpenAI from 'openai';
import * as anthropic from '@anthropic-ai/sdk';
import { Laminar } from '@lmnr-ai/lmnr';

Laminar.initialize({
    projectApiKey: process.env.LMNR_PROJECT_API_KEY,
    instrumentModules: { openAI: OpenAI, anthropic: anthropic }
});

If you want to try it quickly without manually importing and instrumenting all modules, you can do simple initialization, however, you will need to import and initialize Laminar before importing LLM client libraries. This is because JavaScript binds the imported module to its name at import time, so introducing instrumentation afterwards statically is not possible.