Skip to content

Conditional Instrumentation: Environment-based Control for Next.js Instrumentation API #75273

@JamesRobertWiseman

Description

@JamesRobertWiseman

Discussed in #75129

Originally posted by JamesRobertWiseman January 21, 2025

Goals

  1. Enable developers to disable instrumentation in specific environments
  2. Reduce development overhead by skipping unnecessary instrumentation code
  3. Provide a clean, declarative way to manage environment-specific instrumentation 1

Non-Goals

  1. Modify existing instrumentation functionality in production environments
  2. Change how instrumentation works when enabled
  3. Add complexity to the current stable instrumentation API 2

Background

The instrumentation API was stabilized in Next.js 15, providing a way to execute code when a new Next.js server instance starts. Currently, developers need to implement manual environment checks within the instrumentation file.

Starting from Next.js's recommended code:

//  instrumentation.js
export async function register() {
  if (process.env.NEXT_RUNTIME === 'nodejs') {
    await import('./instrumentation-node')
  }
 
  if (process.env.NEXT_RUNTIME === 'edge') {
    await import('./instrumentation-edge')
  }
}

To disable instrumentation in development, developers must add additional environment checks:

//  instrumentation.js
export async function register() {
  if (process.env.NODE_ENV !== 'production') {
    return;
  }

  if (process.env.NEXT_RUNTIME === 'nodejs') {
    await import('./instrumentation-node')
  }
 
  if (process.env.NEXT_RUNTIME === 'edge') {
    await import('./instrumentation-edge')
  }
}

This approach, while functional, leads to:

  1. Boilerplate code in instrumentation files
  2. Potential code bundling of unused imports in development
  3. Less maintainable and harder to understand instrumentation setup
  4. Repetitive environment checks across different instrumentation features

A more elegant solution is needed to handle environment-specific instrumentation.

Proposal

Implement either:

  1. Add disableInstrumentation configuration option in next.config.js that accepts a boolean or function returning boolean:
// next.config.js
module.exports = {
  disableInstrumentation: process.env.NODE_ENV !== 'production'
  // or as a function
  disableInstrumentation: (options) => {
    return process.env.NODE_ENV !== 'production'
  }
}
  1. Introduce environment-specific file conventions:
  • instrumentation.prod.ts|js - Only runs in production
  • instrumentation.dev.ts|js - Only runs in development
  • instrumentation.ts|js - Runs in all environments (maintaining backward compatibility)

I'm interested in contributing to the implementation of this feature. The preferred approach would be option 1, as it provides more flexibility and maintains the single file convention while allowing for simple environment control.

Metadata

Metadata

Assignees

No one assigned

    Labels

    invalid linkThe issue was auto-closed due to a missing/invalid reproduction link. A new issue should be opened.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions