Files
skills/docs/api-stack/api/api-plugin-audit/src/plugin/plugin.md
2026-05-29 08:20:56 +01:00

3.4 KiB

plugin/plugin

(no submodules)

Purpose

Top-level factory for the audit plugin. createAuditPlugin(options) Zod-validates the caller's options at the boundary, builds the resolved AuditPluginConfig, and returns a typed PluginDescriptor<AuditPluginConfig> whose onInit hook performs the canonical 4-step lifecycle: resolve app, construct AuditLogger, register auditService, install the global middleware. The descriptor's onClose clears the cached logger reference.

This is the only entry point operators interact with. Everything else in the package is reachable through the descriptor or the ServiceRegistry slot the descriptor installs.

Features

  • Zod-validated options via AuditPluginOptionsSchema; failures throw AuditPluginError(AUDIT_PLUGIN_INVALID_INPUT) with the ZodError as cause.
  • Defaults supply MemoryAuditAdapter when no sink is injected (dev fallback).
  • Warns when the dev-default secret key is used so production operators notice.
  • onInit raises AUDIT_PLUGIN_SERVICE_NOT_AVAILABLE when app is missing, listing ["app"] in context.missing.
  • onInit raises AUDIT_PLUGIN_SINK_INIT_FAILED when new AuditLogger(...) throws (e.g. missing/invalid secret key).
  • onInit is idempotent in the sense that re-invocation rebuilds the logger and re-installs the middleware (Hono app.use("*", ...) chaining is additive, so callers should treat the descriptor as one-shot per registry).

Usage: Basic

import { MemoryAuditAdapter } from "@suaveplan/audit-logging";
import { createAuditPlugin } from "@suaveplan/api-plugin-audit";

const plugin = createAuditPlugin({
    sink: new MemoryAuditAdapter(),
    secretKey: process.env.AUDIT_SECRET_KEY,
});
// register on your PluginRegistry alongside auth, tenant, etc.

Usage: Advanced

import { createAuditPlugin } from "@suaveplan/api-plugin-audit";
import { MemoryAuditAdapter } from "@suaveplan/audit-logging";

const plugin = createAuditPlugin({
    sink: new MemoryAuditAdapter(),
    secretKey: process.env.AUDIT_SECRET_KEY,
    samplingRate: 0.1, // record 10% of requests
    excludePaths: ["/health", "/metrics", "/openapi.json"],
    redactBodyFields: ["password", "ssn", "card_number"],
    redactHeaders: ["authorization", "cookie", "x-internal-key"],
    redactQueryParams: ["token", "code", "state", "session"],
    recordRequestBody: true,
    enableChainIntegrity: true,
});

API Reference

  • createAuditPlugin(options: AuditPluginOptions): PluginDescriptor<AuditPluginConfig>
    • Validates options via AuditPluginOptionsSchema.
    • Returns a descriptor with name: "audit", version: "0.1.0", resolved defaults, onInit, onClose.

Implementation Notes

The factory captures the resolved config and a small AuditPluginState (currently just the cached logger) in a closure shared between onInit and onClose. The dev-default secret-key warning fires every time onInit runs — operators see it once per boot, which is the right cadence (loud enough to notice, quiet enough not to spam). The plugin does NOT depend on @suaveplan/api; it depends only on @suaveplan/api-plugin (for definePlugin + the context types) plus @suaveplan/audit-logging (for the runtime), @suaveplan/error / @suaveplan/types, hono, and zod. This keeps the dep graph small and lets the plugin attach to any Hono-based host.