Three related bugs fixed:
1. Form save buttons silently failing — valueAsNumber on empty number inputs
produced NaN, which Zod rejected without visible errors on hidden tabs.
Replaced with setValueAs that converts empty strings to undefined.
2. Unique constraint violation on deliverable stage creation — dynamic pipeline
stages without matching global template slugs all fell back to
globalTemplates[0], creating duplicate (deliverableId, templateId) pairs.
Changed constraint from @@unique([deliverableId, templateId]) to
@@unique([deliverableId, stageDefinitionId]).
3. Stage names showing wrong template — all UI components read
stage.template.name exclusively, ignoring stageDefinition from the dynamic
pipeline system. Updated 13 components, 6 services, and all relevant Prisma
queries to prefer stageDefinition over template for display.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>