Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
60 changes: 60 additions & 0 deletions .changeset/identifier-schemas-declared-unenforced-retired.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
---
"@objectstack/spec": minor
---

feat(spec): retire the six branded identifier schemas and EventNameSchema — declared-but-unenforced identifier layers removed (#13612, #13613)

<!-- adr-0087: registered branded-identifier-schemas-retired, event-name-schema-retired -->

**BREAKING** published-export removals from `@objectstack/spec/shared`,
shipped as `minor` under the repo's launch-window convention for breaking
changes; both migration prescriptions are registered under protocol
major 18. Maintainer ruling 2026-09-01 (director decision batch C, verbatim
「同意」: retire) on both cards, under ADR-0049 enforce-or-remove.

**#13612 — the six branded identifier schemas** (`shared/branded-types.zod.ts`,
removed whole): `ObjectNameSchema`, `FieldNameSchema`, `ViewNameSchema`,
`AppNameSchema`, `FlowNameSchema`, `RoleNameSchema`, with their type exports
(`ObjectName`/`ObjectNameParsed` through `RoleName`/`RoleNameParsed`). The
brands promised compile-time safety no consumer could obtain — no schema in
either repository ever composed one, so nothing produced or accepted a
branded value — while the surfaces they were named for are validated by
inline regexes (`data/object.zod.ts`, `data/field.zod.ts`,
`automation/flow.zod.ts`) or bare `SnakeCaseIdentifierSchema`
(`ui/app.zod.ts`, `identity/position.zod.ts`). Those five real validators
are the contract of record and are untouched. Binding was weighed and not
adopted: it would silently change five surfaces' accept sets (the inline
regexes admit a leading underscore the brand base does not).

**#13613 — `EventNameSchema`** and its `EventName` type
(`shared/identifiers.zod.ts`). Its only three binding fields
(`EventTypeDefinitionSchema.name`, `EventSchema.name`,
`EventMessageSchema.eventName`) had zero runtime consumers; the vocabulary
the platform actually checks is the closed literal enums `DataEventType` /
`BulkDataEventType` (`api/events.zod.ts`), which never referenced it. The
three fields stay and widen to plain `z.string()` — every previously valid
document stays valid. The enums are byte-for-byte untouched and stand as the
only event-name contract; `WebSocketEventSchema.channel` stays a deliberate
bare `z.string()` (the ruling adds no constraint there).

FROM → TO:

- `import { ObjectNameSchema, … , RoleNameSchema } from '@objectstack/spec/shared'`
→ removed, no replacement brand layer (TS2305 on upgrade). Fix: parse an
identifier through the schema of the surface that stores it; for a
standalone check use `SnakeCaseIdentifierSchema` or
`SystemIdentifierSchema`, both still published from the same subpath.
- `import { EventNameSchema } from '@objectstack/spec/shared'` → removed
(TS2305 on upgrade). Fix: delete the import; to validate platform event
names, parse through `DataEventType` / `BulkDataEventType` from
`@objectstack/spec/api`.
- Documents parsed by `EventTypeDefinitionSchema`, `EventSchema` or
`EventMessageSchema`: no change required — the `name`/`eventName` accept
set widens from the dot-notation grammar to any string, so no stored
metadata breaks and no source rewrite ships.

No authored document ever embedded a branded value and the event-field
change is a widening, so there is no tombstone, no D2 conversion, and
nothing for `objectstack migrate meta` to rewrite; the
`RETIRED_DEFS_BY_MAJOR` rows (seven `shared/*` defs) plus the two D3
semantic entries are the declaration.
2 changes: 1 addition & 1 deletion content/docs/getting-started/quick-reference.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -206,7 +206,7 @@ from the provider itself, not from hand-written spec files.
|:---------|:-----------|:------------|:--------|
| **[Connector](/docs/references/integration/connector)** | `connector.zod.ts` | Connector | The connector protocol — auth, sync, webhooks, rate limiting |

## Shared Protocol (5 of 8 schemas)
## Shared Protocol (5 of 7 schemas)

Common utilities used across all protocols.

Expand Down
4 changes: 2 additions & 2 deletions content/docs/references/api/websocket.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -213,7 +213,7 @@ const result = AckMessageSchema.parse(data);
| **type** | `'event'` | ✅ | |
| **timestamp** | `string` | ✅ | ISO 8601 datetime when message was sent |
| **subscriptionId** | `string` | ✅ | Subscription ID this event belongs to |
| **eventName** | `string` | ✅ | Event name |
| **eventName** | `string` | ✅ | Event name (dot notation by convention; the platform-checked event vocabulary is the closed DataEventType / BulkDataEventType enums) |
| **object** | `string` | optional | Object name the event relates to |
| **payload** | `any` | ✅ | Event payload data |
| **userId** | `string` | optional | User who triggered the event |
Expand Down Expand Up @@ -519,7 +519,7 @@ This schema accepts one of the following structures:
| **type** | `'event'` | ✅ | |
| **timestamp** | `string` | ✅ | ISO 8601 datetime when message was sent |
| **subscriptionId** | `string` | ✅ | Subscription ID this event belongs to |
| **eventName** | `string` | ✅ | Event name |
| **eventName** | `string` | ✅ | Event name (dot notation by convention; the platform-checked event vocabulary is the closed DataEventType / BulkDataEventType enums) |
| **object** | `string` | optional | Object name the event relates to |
| **payload** | `any` | ✅ | Event payload data |
| **userId** | `string` | optional | User who triggered the event |
Expand Down
11 changes: 5 additions & 6 deletions content/docs/references/index.mdx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
---
title: Protocol Reference
description: Every schema published by @objectstack/spec — 1598 schemas across 14 protocol modules
description: Every schema published by @objectstack/spec — 1591 schemas across 14 protocol modules
---

{/* ⚠️ AUTO-GENERATED — DO NOT EDIT. Run build-docs.ts to regenerate. Hand-written docs live in the module folders under content/docs/. */}
Expand Down Expand Up @@ -29,11 +29,11 @@ counts are sums of the rows they head. Regenerate with
| [Kernel Protocol](/docs/references/kernel) | 30 | 163 | Plugin lifecycle and manifests, capabilities and security, metadata loading, service registry. |
| [QA Protocol](/docs/references/qa) | 1 | 8 | Declarative test suites — scenarios, steps, actions and assertions. |
| [Security Protocol](/docs/references/security) | 5 | 29 | Permission sets, row-level security, sharing rules, tenancy posture. |
| [Shared Protocol](/docs/references/shared) | 8 | 32 | Primitives used across every protocol — identifiers, HTTP, expressions, error maps, enums. |
| [Shared Protocol](/docs/references/shared) | 7 | 25 | Primitives used across every protocol — identifiers, HTTP, expressions, error maps, enums. |
| [Studio Protocol](/docs/references/studio) | 3 | 35 | Studio designer metadata — the authoring surfaces for the protocols above. |
| [System Protocol](/docs/references/system) | 36 | 291 | The runtime environment — logging, jobs, cache, metrics, notifications, i18n and compliance. |
| [UI Protocol](/docs/references/ui) | 16 | 153 | Apps, pages, views, dashboards, reports, actions and themes — the ObjectUI layer. |
| **Total** | **200** | **1598** | 14 protocol modules |
| **Total** | **199** | **1591** | 14 protocol modules |

---

Expand Down Expand Up @@ -286,17 +286,16 @@ Permission sets, row-level security, sharing rules, tenancy posture.

## Shared Protocol

**Source:** `packages/spec/src/shared/` · **Import:** `@objectstack/spec/shared` · **8 pages, 32 schemas**
**Source:** `packages/spec/src/shared/` · **Import:** `@objectstack/spec/shared` · **7 pages, 25 schemas**

Primitives used across every protocol — identifiers, HTTP, expressions, error maps, enums.

| File | Schemas |
| :--- | :--- |
| [`branded-types.zod.ts`](/docs/references/shared/branded-types) | `AppName`, `FieldName`, `FlowName`, `ObjectName`, `RoleName`, `ViewName` |
| [`enums.zod.ts`](/docs/references/shared/enums) | `IsolationLevelEnum`, `MutationEventEnum`, `SortDirectionEnum`, `SortItem` |
| [`expression.zod.ts`](/docs/references/shared/expression) | `CronExpressionInput`, `Expression`, `ExpressionDialect`, `ExpressionInput`, `ExpressionMeta`, `Predicate`, `PredicateInput`, `TemplateExpressionInput` |
| [`http.zod.ts`](/docs/references/shared/http) | `CorsConfig`, `HttpMethod`, `HttpMethodSubset`, `HttpRequest`, `RateLimitConfig`, `StaticMount` |
| [`identifiers.zod.ts`](/docs/references/shared/identifiers) | `EventName`, `MetadataItemName`, `SnakeCaseIdentifier`, `SystemIdentifier` |
| [`identifiers.zod.ts`](/docs/references/shared/identifiers) | `MetadataItemName`, `SnakeCaseIdentifier`, `SystemIdentifier` |
| [`mapping.zod.ts`](/docs/references/shared/mapping) | `FieldMapping` |
| [`metadata-types.zod.ts`](/docs/references/shared/metadata-types) | `BaseMetadataRecord`, `MetadataFormat` |
| [`protection.zod.ts`](/docs/references/shared/protection) | `Protection` |
Expand Down
2 changes: 1 addition & 1 deletion content/docs/references/kernel/events-bus.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ const result = EventBusConfigSchema.parse(data);

| Property | Type | Required | Description |
| :--- | :--- | :--- | :--- |
| **name** | `string` | ✅ | Event type name (lowercase with dots) |
| **name** | `string` | ✅ | Event type name (dot notation by convention, e.g. order.created; the platform-checked event vocabulary is the closed DataEventType / BulkDataEventType enums) |
| **version** | `string` | optional (default: `"1.0.0"`) | Event schema version |
| **schema** | `any` | optional | JSON Schema for event payload validation |
| **description** | `string` | optional | Event type description |
Expand Down
4 changes: 2 additions & 2 deletions content/docs/references/kernel/events-core.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ const result = EventSchema.parse(data);
| Property | Type | Required | Description |
| :--- | :--- | :--- | :--- |
| **id** | `string` | optional | Unique event identifier |
| **name** | `string` | ✅ | Event name (lowercase with dots, e.g., user.created, order.paid) |
| **name** | `string` | ✅ | Event name (dot notation by convention, e.g. user.created, order.paid; the platform-checked event vocabulary is the closed DataEventType / BulkDataEventType enums) |
| **payload** | `any` | ✅ | Event payload schema |
| **metadata** | `{ source: string; timestamp: string; userId?: string; tenantId?: string; … }` | ✅ | Event metadata |

Expand Down Expand Up @@ -93,7 +93,7 @@ const result = EventSchema.parse(data);

| Property | Type | Required | Description |
| :--- | :--- | :--- | :--- |
| **name** | `string` | ✅ | Event type name (lowercase with dots) |
| **name** | `string` | ✅ | Event type name (dot notation by convention, e.g. order.created; the platform-checked event vocabulary is the closed DataEventType / BulkDataEventType enums) |
| **version** | `string` | optional (default: `"1.0.0"`) | Event schema version |
| **schema** | `any` | optional | JSON Schema for event payload validation |
| **description** | `string` | optional | Event type description |
Expand Down
4 changes: 2 additions & 2 deletions content/docs/references/kernel/events-dlq.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ const result = DeadLetterQueueEntrySchema.parse(data);
| Property | Type | Required | Description |
| :--- | :--- | :--- | :--- |
| **id** | `string` | optional | Unique event identifier |
| **name** | `string` | ✅ | Event name (lowercase with dots, e.g., user.created, order.paid) |
| **name** | `string` | ✅ | Event name (dot notation by convention, e.g. user.created, order.paid; the platform-checked event vocabulary is the closed DataEventType / BulkDataEventType enums) |
| **payload** | `any` | ✅ | Event payload schema |
| **metadata** | `{ source: string; timestamp: string; userId?: string; tenantId?: string; … }` | ✅ | Event metadata |

Expand Down Expand Up @@ -74,7 +74,7 @@ const result = DeadLetterQueueEntrySchema.parse(data);
| Property | Type | Required | Description |
| :--- | :--- | :--- | :--- |
| **id** | `string` | optional | Unique event identifier |
| **name** | `string` | ✅ | Event name (lowercase with dots, e.g., user.created, order.paid) |
| **name** | `string` | ✅ | Event name (dot notation by convention, e.g. user.created, order.paid; the platform-checked event vocabulary is the closed DataEventType / BulkDataEventType enums) |
| **payload** | `any` | ✅ | Event payload schema |
| **metadata** | `{ source: string; timestamp: string; userId?: string; tenantId?: string; … }` | ✅ | Event metadata |

Expand Down
94 changes: 0 additions & 94 deletions content/docs/references/shared/branded-types.mdx

This file was deleted.

15 changes: 3 additions & 12 deletions content/docs/references/shared/identifiers.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -12,22 +12,13 @@ description: Identifiers protocol schemas
## TypeScript Usage

```typescript
import { EventNameSchema, MetadataItemNameSchema, SnakeCaseIdentifierSchema, SystemIdentifierSchema } from '@objectstack/spec/shared';
import type { EventName, MetadataItemName, SnakeCaseIdentifier, SystemIdentifier } from '@objectstack/spec/shared';
import { MetadataItemNameSchema, SnakeCaseIdentifierSchema, SystemIdentifierSchema } from '@objectstack/spec/shared';
import type { MetadataItemName, SnakeCaseIdentifier, SystemIdentifier } from '@objectstack/spec/shared';

// Validate data
const result = EventNameSchema.parse(data);
const result = MetadataItemNameSchema.parse(data);
```

---

## EventName

Event name (lowercase with dot notation for namespacing)

**Type:** `string`


---

## MetadataItemName
Expand Down
1 change: 0 additions & 1 deletion content/docs/references/shared/index.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@ description: Complete reference for all shared protocol schemas
This section contains all protocol schemas for the shared layer of ObjectStack.

<Cards>
<Card href="/docs/references/shared/branded-types" title="Branded Types" description="Source: packages/spec/src/shared/branded-types.zod.ts" />
<Card href="/docs/references/shared/enums" title="Enums" description="Source: packages/spec/src/shared/enums.zod.ts" />
<Card href="/docs/references/shared/expression" title="Expression" description="Source: packages/spec/src/shared/expression.zod.ts" />
<Card href="/docs/references/shared/http" title="Http" description="Source: packages/spec/src/shared/http.zod.ts" />
Expand Down
1 change: 0 additions & 1 deletion content/docs/references/shared/meta.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
{
"title": "Shared Protocol",
"pages": [
"branded-types",
"enums",
"expression",
"http",
Expand Down
2 changes: 1 addition & 1 deletion packages/spec/ZOD_SCHEMA_AUDIT_REPORT.md
Original file line number Diff line number Diff line change
Expand Up @@ -643,7 +643,7 @@ ObjectStack UI protocol provides three paths:

**Strengths:**
- Perfect foundational layer — small, focused, widely imported
- `identifiers.zod.ts` is the naming convention enforcer (SystemIdentifierSchema, SnakeCaseIdentifierSchema, EventNameSchema)
- `identifiers.zod.ts` is the naming convention enforcer (SystemIdentifierSchema, SnakeCaseIdentifierSchema)
- `connector-auth.zod.ts` uses `z.discriminatedUnion` perfectly (5 auth types)

**Key Files:**
Expand Down
20 changes: 0 additions & 20 deletions packages/spec/api-surface/shared.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,6 @@
"description": "Every exported `name (kind)` of one published entry point of @objectstack/spec — the breadth half of the ADR-0059 backward-compatibility gate. Sharded by entry point (#5837) so two PRs touching different entry points never share a file. Reads the BUILT dist/*.d.ts: regenerate with `pnpm --filter @objectstack/spec gen:api-surface` after a real build.",
"entry": "./shared",
"exports": [
"AppName (type)",
"AppNameParsed (type)",
"AppNameSchema (const)",
"ApplyProtectionContext (interface)",
"BaseMetadataRecord (type)",
"BaseMetadataRecordSchema (const)",
Expand All @@ -15,8 +12,6 @@
"CronExpressionInputSchema (const)",
"EXTERNAL_ERROR_CODES (const)",
"EXTERNAL_ERROR_HTTP_STATUS (const)",
"EventName (type)",
"EventNameSchema (const)",
"Expression (type)",
"ExpressionDialect (type)",
"ExpressionInput (type)",
Expand All @@ -31,12 +26,6 @@
"F (const)",
"FieldMapping (type)",
"FieldMappingSchema (const)",
"FieldName (type)",
"FieldNameParsed (type)",
"FieldNameSchema (const)",
"FlowName (type)",
"FlowNameParsed (type)",
"FlowNameSchema (const)",
"HttpMethod (type)",
"HttpMethodSubset (type)",
"HttpMethodSubsetSchema (const)",
Expand All @@ -59,9 +48,6 @@
"MutationEvent (type)",
"MutationEventEnum (const)",
"NormalizeStackInputOptions (interface)",
"ObjectName (type)",
"ObjectNameParsed (type)",
"ObjectNameSchema (const)",
"ObjectStackRawIssue (type)",
"P (const)",
"PLURAL_TO_SINGULAR (const)",
Expand All @@ -76,9 +62,6 @@
"RateLimitConfigParsed (type)",
"RateLimitConfigSchema (const)",
"ResilientFetchOptions (interface)",
"RoleName (type)",
"RoleNameParsed (type)",
"RoleNameSchema (const)",
"SINGULAR_TO_PLURAL (const)",
"SchemaDiffEntry (interface)",
"SchemaDiffEntryKind (type)",
Expand All @@ -97,9 +80,6 @@
"TemplateExpressionInputSchema (const)",
"VISIBILITY_ALIAS_KEYS (const)",
"VISIBILITY_STRICT_OPTIONS (const)",
"ViewName (type)",
"ViewNameParsed (type)",
"ViewNameSchema (const)",
"applyProtection (function)",
"canonicalMetaUrlType (function)",
"cel (function)",
Expand Down
Loading
Loading