Files
daily-notification-plugin/contracts/notification.v1.schema.json
Matthew Raymer 114843edd5 feat(contract): Add Contract v1 freeze with schema and validation
- Add contracts/NotificationContract.v1.ts (frozen TypeScript interface)
- Add contracts/notification.v1.schema.json (JSON Schema)
- Add contracts/notification.v1.hash (SHA-256 hash for integrity)
- Add scripts/generate-contract-schema.js (schema generator)
- Add scripts/check-contract.sh (validation script)

Contract v1 is now frozen as single source of truth for cross-platform
notification content. All platforms must conform to this contract.

See docs/0017-Daily-Notification-Contract-Freeze.md for details.
2025-11-12 11:23:43 +00:00

66 lines
1.6 KiB
JSON

{
"$schema": "http://json-schema.org/draft-07/schema#",
"additionalProperties": false,
"description": "Contract v1 for notification content (FROZEN)",
"properties": {
"body": {
"description": "Notification body text (optional)",
"type": "string"
},
"dedupeKey": {
"description": "Deduplication key (for idempotency)",
"type": "string"
},
"fetchTime": {
"description": "When this content was fetched (epoch ms, required)",
"minimum": 0,
"type": "number"
},
"id": {
"description": "Unique identifier for this notification",
"type": "string"
},
"mediaUrl": {
"description": "Optional image URL for rich notifications",
"format": "uri",
"type": "string"
},
"metadata": {
"additionalProperties": true,
"description": "Additional metadata (opaque to plugin)",
"type": "object"
},
"priority": {
"description": "Notification priority level",
"enum": [
"min",
"low",
"default",
"high",
"max"
],
"type": "string"
},
"scheduledTime": {
"description": "When this notification should be displayed (epoch ms, optional)",
"minimum": 0,
"type": "number"
},
"title": {
"description": "Notification title (required)",
"type": "string"
},
"ttlSeconds": {
"description": "Cache TTL in seconds (how long this content is valid)",
"minimum": 0,
"type": "number"
}
},
"required": [
"id",
"title",
"fetchTime"
],
"title": "NotificationContent v1",
"type": "object"
}