nest-profiler-validator
Types and API of the validation collector.
ValidatorCollectorModuleOptions
Options for ValidatorCollectorModule.forRoot(). The module registers only the Validator panel — the validation pipe is owned by the app via createProfilerValidationPipe — so enabled is its only knob.
Prop
Type
ValidationEntry
One entry per DTO validated during a request (both valid and invalid).
Prop
Type
ViolationEntry
One entry per property that failed validation.
Prop
Type
ValidationStatus
type ValidationStatus = 'valid' | 'invalid';ValidationSource
type ValidationSource = 'body' | 'query' | 'param' | 'custom';Corresponds to the NestJS parameter decorator used: @Body(), @Query(), @Param(), or a custom decorator.
ProfilerValidationPipe
Implements PipeTransform. Built via createProfilerValidationPipe and installed by the app with app.useGlobalPipes(...). It wraps an inner validation pipe (the one you configure) rather than performing validation itself: it delegates to the inner pipe, records a valid entry on success, and on failure runs the configured extractors over the thrown error to record an invalid entry - then always re-throws the original exception. It resolves CLS through nestjs-cls's static ClsServiceManager, so it needs no DI container and degrades to a transparent pass-through when no profile is active.
createProfilerValidationPipe
Builds a ProfilerValidationPipe without the Nest DI container so your application owns its global validation pipe in bootstrap. Pair it with ValidatorCollectorModule.forRoot() (which registers just the panel) to gate the profiler independently of validation.
import {
createProfilerValidationPipe,
createClassValidatorPipe,
} from '@eleven-labs/nest-profiler-validator';
// Validation stays app-owned and always runs — profiler on or off.
app.useGlobalPipes(
createProfilerValidationPipe(createClassValidatorPipe({ whitelist: true, transform: true })),
);Signature: createProfilerValidationPipe(inner: PipeTransform, extractors?: ValidationViolationExtractor[]). The extractors argument defaults to DEFAULT_EXTRACTORS. For class-validator, wrap createClassValidatorPipe(options) rather than a bare new ValidationPipe() so per-property violations reach the panel.
ValidationViolationExtractor
Strategy that turns a validator-specific error into the neutral ViolationEntry[] shape. Return null to defer to the next extractor in the chain.
Prop
Type
Built-in extractors, exported and used in this default order:
import { DEFAULT_EXTRACTORS } from '@eleven-labs/nest-profiler-validator';
// [classValidatorExtractor, zodExtractor, genericExtractor]classValidatorExtractor- recovers the rawValidationError[]attached bycreateClassValidatorPipe.zodExtractor- readsZodError.issues(via nestjs-zod'sgetZodError()or a bareZodError).genericExtractor- anyHttpExceptionexposing amessagestring/array (universal fallback).
createClassValidatorPipe
Builds a class-validator ValidationPipe instrumented for the profiler (it attaches the raw ValidationError[] to the thrown exception so the panel shows per-property constraints). Used as the default inner pipe when pipe is omitted.
import { createClassValidatorPipe } from '@eleven-labs/nest-profiler-validator';
const pipe = createClassValidatorPipe({ whitelist: true, transform: true });Requires class-validator and class-transformer to be installed.
Public exports
import {
ValidatorCollectorModule,
ProfilerValidationPipe,
createProfilerValidationPipe,
ValidatorCollector,
createClassValidatorPipe,
DEFAULT_EXTRACTORS,
classValidatorExtractor,
zodExtractor,
genericExtractor,
} from '@eleven-labs/nest-profiler-validator';
import type {
ValidatorCollectorModuleOptions,
ValidatorCollectorModuleAsyncOptions,
ValidationViolationExtractor,
ViolationExtractorContext,
ValidationEntry,
ViolationEntry,
ValidationStatus,
ValidationSource,
ValidationPipeOptions,
} from '@eleven-labs/nest-profiler-validator';Setup
Install the pipe in main.ts and register the panel with forRoot() — validation runs independently of the profiler's gate:
// main.ts — class-validator (wrap createClassValidatorPipe to keep per-property violations)
app.useGlobalPipes(
createProfilerValidationPipe(createClassValidatorPipe({ whitelist: true, transform: true })),
);
// main.ts — nestjs-zod
app.useGlobalPipes(createProfilerValidationPipe(new ZodValidationPipe()));
// app.module.ts — panel only, gated like every other collector
ConditionalModule.registerWhen(ValidatorCollectorModule.forRoot(), isProfilerEnabled);Since the pipe lives in main.ts, mirror the same useGlobalPipes(...) call when you boot the app manually in e2e tests. A NestJS app uses a single global validation strategy, so use one validator at a time.
Important: Use value imports (not import type) for DTO classes in controllers so that TypeScript emits reflect-metadata for the parameter type:
// ✓ value import - allows TypeScript to emit design:paramtypes
import { CreateArticleDto } from './dto/create-article.dto';
// ✗ type-only import - erases metadata, metatype shows as 'Function'
import type { CreateArticleDto } from './dto/create-article.dto';Prerequisite: install the validator you use (class-validator + class-transformer, or nestjs-zod + zod). For class-validator, emitDecoratorMetadata: true must be set in tsconfig.json.
The panel gates like every other collector: forRoot() / forRootAsync() register only the ValidatorCollector, wrapped in ConditionalModule.registerWhen(..., isProfilerEnabled) (or toggled with the top-level enabled flag).