Files
skills/docs/media/audio-fx/audio-fx-plugin-phaser/src/schemas/schemas.md
2026-05-29 08:20:56 +01:00

2.8 KiB

phaser/schemas

(no submodules)

Purpose

Zod schemas validating the construction-time options and preset payload of PhaserPlugin. These run on the public boundary between user code and the plugin: any malformed object hitting the constructor or applyPreset is rejected with AUDIO_FX.INVALID_OPTIONS / AUDIO_FX.INVALID_PRESET before it can corrupt runtime state.

Separating schemas from the plugin module lets index.ts re-export them so callers can introspect the option surface (for forms, RPC validation, or storybook controls) without importing the audio implementation.

Features

  • PhaserPluginOptionsSchema — validates all six optional construction fields with their documented ranges.
  • initialStages is z.number().int().min(2).max(12) so non-integer stage counts cannot sneak through.
  • PhaserPresetDataSchema — empty strict object; the phaser has no plugin-specific preset payload, so any extra keys are rejected.
  • All numeric fields use z.number().finite() so NaN and Infinity cannot sneak through.

Usage: Basic Example

import { PhaserPluginOptionsSchema } from "@suaveplan/audio-fx-plugin-phaser";

const parsed = PhaserPluginOptionsSchema.parse({ initialDepth: 0.6 });

Usage: Advanced Example

import {
    PhaserPluginOptionsSchema,
    PhaserPresetDataSchema,
} from "@suaveplan/audio-fx-plugin-phaser";

// Driver for an editor form: pull the keys + ranges from the schema.
const optionFields = PhaserPluginOptionsSchema.keyof().options;
for (const field of optionFields) {
    form.addRow(field);
}

// Reject foreign preset payloads at the IPC boundary.
function isPhaserPreset(blob: unknown): boolean {
    return PhaserPresetDataSchema.safeParse(blob).success;
}

API Reference

  • PhaserPluginOptionsSchema: z.ZodObject<{ initialRateHz?, initialDepth?, initialStages?, initialFeedback?, initialWet?, initialCenterHz? }>
  • PhaserPresetDataSchema: z.ZodObject<{}, "strict">

Implementation Notes

PhaserPresetDataSchema is .strict() so unknown fields are rejected, matching the sibling-plugin policy. The phaser has no plugin-specific preset payload today: every parameter (rate, depth, stages, feedback, wet, center) travels through the universal parameter snapshot that AbstractAudioFxPlugin builds, and the empty presetData field is a marker that the plugin opts out of plugin-specific state.

The maximum feedback is 0.95, not 1.0. Allowing feedback at unity would create a marginally stable system whose output diverges for any non-zero input; clamping at 0.95 leaves enough headroom that even a noise-floor leak stays bounded over arbitrarily long renders. This boundary is the same as for the chorus, delay, and flanger plugins so all four feedback-bearing effects share one mental model.