Instrumentation
Instrumentation is the process of using code to integrate monitoring and logging tools into your application. This allows you to track the performance and behavior of your application, and to debug issues in production.
Convention​
To set up instrumentation, create instrumentation.ts|js file in the root directory of your project (or inside the src folder if using one).
Then, export a register function in the file. This function will be called once when a new Next.js server instance is initiated.
For example, to use Next.js with OpenTelemetry and @vercel/otel:
import { registerOTel } from '@vercel/otel'
export function register() {
registerOTel('next-app')
}
import { registerOTel } from '@vercel/otel'
export function register() {
registerOTel('next-app')
}
See the Next.js with OpenTelemetry example for a complete implementation.
Good to know
- This feature is experimental. To use it, you must explicitly opt in by defining
experimental.instrumentationHook = true;in yournext.config.js.- The
instrumentationfile should be in the root of your project and not inside theapporpagesdirectory. If you're using thesrcfolder, then place the file insidesrcalongsidepagesandapp.- If you use the
pageExtensionsconfig option to add a suffix, you will also need to update theinstrumentationfilename to match.
Examples​
Importing files with side effects​
Sometimes, it may be useful to import a file in your code because of the side effects it will cause. For example, you might import a file that defines a set of global variables, but never explicitly use the imported file in your code. You would still have access to the global variables the package has declared.
We recommend importing files using JavaScript import syntax within your register function. The following example demonstrates a basic usage of import in a register function:
export async function register() {
await import('package-with-side-effect')
}
export async function register() {
await import('package-with-side-effect')
}
Good to know:
We recommend importing the file from within the
registerfunction, rather than at the top of the file. By doing this, you can colocate all of your side effects in one place in your code, and avoid any unintended consequences from importing globally at the top of the file.
Importing runtime-specific code​
Next.js calls register in all environments, so it's important to conditionally import any code that doesn't support specific runtimes (e.g. Edge or Node.js). You can use the NEXT_RUNTIME environment variable to get the current environment:
export async function register() {
if (process.env.NEXT_RUNTIME === 'nodejs') {
await import('./instrumentation-node')
}
if (process.env.NEXT_RUNTIME === 'edge') {
await import('./instrumentation-edge')
}
}
export async function register() {
if (process.env.NEXT_RUNTIME === 'nodejs') {
await import('./instrumentation-node')
}
if (process.env.NEXT_RUNTIME === 'edge') {
await import('./instrumentation-edge')
}
}