openvibers/openvibe.contracts Commits

Manifests: every service names its PostgreSQL database (no SQLite left) (#92)

OP OpenVibers committed 11 Oct 2026 · 9953d00b08 · 19 files, +34 −34

* Manifests: every service names its PostgreSQL database (no SQLite left)

The service manifests still described services as running on SQLite: "one process owns X.db (better-sqlite3, single writer)", `world.db`, `jobs.db`, `"database": "SQLite"`. Every service runs on PostgreSQL through `openvibe-sdk/db`, each with its own `ov_<service>` database behind PgBouncer; this was verified on the host today (37 databases, and no SQLite file written in the last day).

- **What changes:** 18 manifests (17 services and Live's repository manifest) now name their PostgreSQL database. The domain rules in the `leases.none` texts stay as they were: compare-and-set, cooldowns, daily caps, one delivery in flight.
- **Network:** the go-live announcement claim is now attributed to Network's `live.stream.started` consumer, since the direct stream-live call went with C-85.
- **No stale mentions left:** `grep -rnE "better-sqlite3|SQLite|sqlite|[a-z_-]+\.db\b" manifests/` finds nothing.

The edits were drafted by a Codex job and reviewed here. `node test/run.js`: 18,420 checks pass, `generated/` is up to date, and there are no breaking changes against v0.136.1.

* Estate: Live's row reads PostgreSQL (ov_live), as its repository record says

Changes

ddiff --git a/docs/ESTATE.md b/docs/ESTATE.md
iindex dcefa92d..c15e5d7b 100644
---- a/docs/ESTATE.md
++++ b/docs/ESTATE.md
@@@ -28,7 +28,7 @@ service id); **Runtime** is `STATUS.json.runtime`; **Database** is inferred from
| OpenVibe.Extensions | — | — | node >=22.0.0 | — | — | — | not deployed | — | W18 |
| OpenVibe.Games | Games | games.* | node 22 | PostgreSQL | openvibe.games, play.openvibe.games | contracts v0.78.0, sdk v0.23.1, shared v2.6.0 | deployed | live | — |
| OpenVibe.Host | Host | host.* | node 22 | PostgreSQL | openvibe.host | contracts v0.83.0, sdk v0.26.0, shared v2.10.1 | loopback only, not launched | live | W21 Stage A + Stage B |
--| OpenVibe.Live | Live | live.* | node 22 | SQLite | openvibe.live, ingest.openvibe.live | contracts v0.83.0, sdk v0.26.0, shared v2.5.0 | deployed | live | — |
++| OpenVibe.Live | Live | live.* | node 22 | PostgreSQL (ov_live) | openvibe.live, ingest.openvibe.live | contracts v0.83.0, sdk v0.26.0, shared v2.5.0 | deployed | live | — |
| OpenVibe.Media | Media | media.* | node 22 | PostgreSQL | openvibe.media | contracts v0.79.0, sdk v0.32.0, shared v2.10.0 | deployed | live | — |
| OpenVibe.Network | Network | identity.*, network.*, theme.*, notification.* | node 22 | PostgreSQL | openvibe.network, auth.openvibe.network, api.openvibe.network, admin.openvibe.network, my.openvibe.network, themes.openvibe.network | contracts v0.106.0, sdk v0.28.0, shared v2.10.1 | deployed | live | — |
| OpenVibe.News | News | news.* | node 22 | PostgreSQL | openvibe.news | contracts v0.97.0, sdk v0.26.0, shared v2.9.0, publishing v1.3.0 | deployed | internal | W17 |
ddiff --git a/manifests/repositories/OpenVibe.Live.json b/manifests/repositories/OpenVibe.Live.json
iindex 008bd62a..fb79ff8c 100644
---- a/manifests/repositories/OpenVibe.Live.json
++++ b/manifests/repositories/OpenVibe.Live.json
@@@ -6,7 +6,7 @@
"stage": "stable",
"version": "1.0.0",
"runtime": "node 22",
-- "database": "SQLite",
++ "database": "PostgreSQL (ov_live)",
"migrations": 1,
"authority": [
"live.*"
ddiff --git a/manifests/services/billing.json b/manifests/services/billing.json
iindex 761f0ac6..e54048c8 100644
---- a/manifests/services/billing.json
++++ b/manifests/services/billing.json
@@@ -93,7 +93,7 @@
"claims": [
{
"what": "a stored provider event (provider_events row) while it is applied",
-- "holder": "the connection that takes the SQLite write lock (IMMEDIATE transaction)",
++ "holder": "the connection that locks the provider_events row in an ov_billing PostgreSQL transaction",
"expires": "at commit or rollback of that transaction",
"fencing": "processed_at is re-read inside the transaction, so a second process or connection that waited applies nothing; ledger postings carry idempotency keys"
}
ddiff --git a/manifests/services/blog.json b/manifests/services/blog.json
iindex d88303af..ef90322b 100644
---- a/manifests/services/blog.json
++++ b/manifests/services/blog.json
@@@ -114,5 +114,5 @@
]
}
},
-- "notes": "Port 4810. Owns blogs, blog_memberships, blog_posts, blog_post_revisions, blog_series, blog_taxonomy, blog_post_terms, blog_schedules, blog_redirects, blog_feed_settings in its own SQLite (openvibe-publishing packages, prefix blog). Consumes OpenVibe.Network (SSO, identity.subject.resolve), OpenVibe.Community (community.comment.write, community.comment.moderate), OpenVibe.Media (media.object.read, namespace blog) and publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads blog.index_document.* from Events."
++ "notes": "Port 4810. Owns blogs, blog_memberships, blog_posts, blog_post_revisions, blog_series, blog_taxonomy, blog_post_terms, blog_schedules, blog_redirects, blog_feed_settings in its own PostgreSQL database ov_blog (openvibe-publishing packages, prefix blog). Consumes OpenVibe.Network (SSO, identity.subject.resolve), OpenVibe.Community (community.comment.write, community.comment.moderate), OpenVibe.Media (media.object.read, namespace blog) and publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads blog.index_document.* from Events."
}
ddiff --git a/manifests/services/codes.json b/manifests/services/codes.json
iindex 0495ad13..b38608f0 100644
---- a/manifests/services/codes.json
++++ b/manifests/services/codes.json
@@@ -67,7 +67,7 @@
"range": ">=0.26.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns codes.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_codes PostgreSQL database; writes are transactions there"
}
},
"notes": "Port 4900, unit openvibe-codes.service. The open coding-agent harness (owner 2026-10-08): the harness catalog and router (GET /api/v1/harnesses, POST /api/v1/harnesses/route), the way to improve OpenVibe (contributing, code of conduct, the contributor ladder) and permanent redirects from the former developer-portal paths to openvibe.services, where the portal moved (manifests, releases, trust, playgrounds, docs, OAuth and webhook tools)."
ddiff --git a/manifests/services/community.json b/manifests/services/community.json
iindex da162175..a492d822 100644
---- a/manifests/services/community.json
++++ b/manifests/services/community.json
@@@ -73,7 +73,7 @@
"Pulse subscription retries, the community.profile scan and the search-document scans stopped",
"stops taking connections; idle keep-alive connections closed (kept 65 s otherwise); requests in flight answered with Connection: close and allowed to finish (4 s at most, then cut)",
"the profile scan in progress (it stops between people), the Discord relay's drain and the events outbox's send awaited; unsent rows stay in their tables",
-- "community.db closed, exit 0"
++ "the ov_community PostgreSQL database closed, exit 0"
],
"note": "server/graceful.js; a stop that passes 5 s exits 1. Only the in-memory rate-limit sweeps end with the process. The unit sets no TimeoutStopSec (systemd's 90 s default applies)"
},
@@@ -107,7 +107,7 @@
"range": ">=0.5.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns community.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_community PostgreSQL database; writes are transactions there"
}
},
"notes": "Community serves the forum (spaces, threads, posts, votes, categories, moderation and the Discord relay), pastes, comments, Pulse and submissions. The forum returned to Community from OpenVibe.Space (owner decision 2026-10-08): the community.* forum capabilities, contracts and events are active again, the community.space.*/thread.read/post.create routes and the /s pages and feeds serve production, and Space no longer serves a forum."
ddiff --git a/manifests/services/coupons.json b/manifests/services/coupons.json
iindex 86b958eb..4934328b 100644
---- a/manifests/services/coupons.json
++++ b/manifests/services/coupons.json
@@@ -127,8 +127,8 @@
"range": ">=0.19.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns coupons.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_coupons PostgreSQL database; writes are transactions there"
}
},
-- "notes": "Port 4850. Owns coupon_merchants, coupon_merchant_domains, coupons, coupon_sources, coupon_restrictions, coupon_validation_reports, coupon_status_history, coupon_application_hints, coupon_watches in its own SQLite, plus extension_installs (cpx_ browser-helper tokens, scopes coupons.lookup and coupons.report, hashed, revocable). Consumes OpenVibe.Network (SSO, JWKS) and OpenVibe.Sources (sources.item.read, category coupons); publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads coupons.index_document.* from Events. The browser helper lives in OpenVibers/OpenVibe.Extensions (ADR-023)."
++ "notes": "Port 4850. Owns coupon_merchants, coupon_merchant_domains, coupons, coupon_sources, coupon_restrictions, coupon_validation_reports, coupon_status_history, coupon_application_hints, coupon_watches in its own PostgreSQL database (ov_coupons), plus extension_installs (cpx_ browser-helper tokens, scopes coupons.lookup and coupons.report, hashed, revocable). Consumes OpenVibe.Network (SSO, JWKS) and OpenVibe.Sources (sources.item.read, category coupons); publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads coupons.index_document.* from Events. The browser helper lives in OpenVibers/OpenVibe.Extensions (ADR-023)."
}
ddiff --git a/manifests/services/deals.json b/manifests/services/deals.json
iindex 0532de44..6c6a9eea 100644
---- a/manifests/services/deals.json
++++ b/manifests/services/deals.json
@@@ -142,8 +142,8 @@
"range": ">=0.19.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns deals.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_deals PostgreSQL database; writes are transactions there"
}
},
-- "notes": "Port 4840. Owns deal_products, deal_product_aliases, deal_offers, deal_offer_sources, deal_votes, deal_hotness_snapshots, deal_watches, deal_price_observations, deal_flags (+ deal_stores) in its own SQLite. Consumes OpenVibe.Network (SSO, identity.subject.resolve), OpenVibe.Sources (sources.item.read; sources.item.* events only wake the pull), OpenVibe.Community (community.comment.write, community.comment.moderate) and publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads deals.index_document.* from Events; OpenVibe.Network turns deals.watch.matched into notifications (server/notifications/events-consumer.js)."
++ "notes": "Port 4840. Owns deal_products, deal_product_aliases, deal_offers, deal_offer_sources, deal_votes, deal_hotness_snapshots, deal_watches, deal_price_observations, deal_flags (+ deal_stores) in its own PostgreSQL database (ov_deals). Consumes OpenVibe.Network (SSO, identity.subject.resolve), OpenVibe.Sources (sources.item.read; sources.item.* events only wake the pull), OpenVibe.Community (community.comment.write, community.comment.moderate) and publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads deals.index_document.* from Events; OpenVibe.Network turns deals.watch.matched into notifications (server/notifications/events-consumer.js)."
}
ddiff --git a/manifests/services/events.json b/manifests/services/events.json
iindex 57e66e6c..30dd6602 100644
---- a/manifests/services/events.json
++++ b/manifests/services/events.json
@@@ -76,7 +76,7 @@
"range": ">=0.5.1 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns events.db (better-sqlite3, single writer); one delivery per subscription is in flight at a time, tracked in memory"
++ "none": "no claims: one process owns the ov_events PostgreSQL database; writes are transactions there; one delivery per subscription is in flight at a time, tracked in memory"
}
},
"notes": "Durable events, subscriptions, signed delivery with retry, dead letters and replay; SSE realtime gateway at /realtime/stream (ADR-005); browsers on any OpenVibe site authenticate a stream with a two-minute, single-use realtime ticket from Network (?ticket=, identity.realtime-ticket-claims@1; ADR-005 amendment 2).",
ddiff --git a/manifests/services/games.json b/manifests/services/games.json
iindex 6ef4e262..ba351a5f 100644
---- a/manifests/services/games.json
++++ b/manifests/services/games.json
@@@ -58,7 +58,7 @@
"lifecycle": {
"liveness": {
"endpoint": "/healthz",
-- "means": "the process is up and answers HTTP; liveness only (world.db and the simulation tick are what /api/ready checks)"
++ "means": "the process is up and answers HTTP; liveness only (the ov_games PostgreSQL database and the simulation tick are what /api/ready checks)"
},
"shutdown": {
"signal": "SIGTERM",
@@@ -71,7 +71,7 @@
"world saved: every session marked dirty and flushed (game.shutdown)",
"requests in flight finish (5 s at most, then cut)",
"the media mirror's pass in progress (2 s at most), the progress-summary writes (1 s) and the outbox's last send (2 s) awaited; unsent rows stay in the outbox",
-- "world.db closed, physics disposed, exit 0"
++ "the ov_games PostgreSQL database closed, physics disposed, exit 0"
],
"note": "clients reconnect on their own after 1012; the whole stop is bounded at 10 s (exit 1 past it), inside the unit's TimeoutStopSec=30"
},
@@@ -79,7 +79,7 @@
"resumes": [
{
"kind": "state",
-- "what": "the world is restored from world.db before the network opens (schema migrated forward first)"
++ "what": "the world is restored from the ov_games PostgreSQL database before the network opens (schema migrated forward first)"
},
{
"kind": "outbox",
@@@ -100,16 +100,16 @@
"automatic: ovhost deploy games (strategy pnpm-build) restores the previous sha, rebuilds and restarts when the ready URL does not answer 2xx after the restart",
"manual: sudo ovhost rollback games --to <sha> (rebuilds the workspace)"
],
-- "window": "as long as world.db has not been migrated past the older build's SCHEMA_VERSION",
++ "window": "as long as the ov_games PostgreSQL database has not been migrated past the older build's SCHEMA_VERSION",
"blockers": [
-- "a build refuses a world.db whose meta.schema_version is newer than its own (SCHEMA_VERSION 13 today, forward-only migrations): going back past a schema bump fails at boot"
++ "a build refuses the ov_games PostgreSQL database whose meta.schema_version is newer than its own (SCHEMA_VERSION 13 today, forward-only migrations): going back past a schema bump fails at boot"
]
},
"contracts": {
"range": ">=0.8.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns world.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_games PostgreSQL database; writes are transactions there"
}
},
"notes": "Scraplandia (browser runtime). Players are keyed by canonical Network subjects (ADR-0006 in the repo). Calls Events (events.event.publish), Media (media.object.upload, namespace games: map-editor assets) and Network identity (identity.subject.resolve, batch legacy adoption) with the games client-credentials principal. Mods: games-content@1 declarative packs only; executable mods wait for OpenVibe.Host Stage C. No achievement system exists, so there are no games.achievement.* events."
ddiff --git a/manifests/services/network.json b/manifests/services/network.json
iindex 116b47d8..821c5b2f 100644
---- a/manifests/services/network.json
++++ b/manifests/services/network.json
@@@ -124,7 +124,7 @@
"maintenance timers (notifications, email queue, retired-module sweep, session cleanup), the analytics prune, the ecosystem, deploy-drift and library-tag pollers, the frame refreshes and the profile-event and grant-expiry timers stopped",
"stops taking connections; idle keep-alive connections closed; requests in flight answered with Connection: close and allowed to finish (8 s at most, then cut)",
"the developer, profile and grant event relay's send in progress awaited (unsent rows stay in the outbox)",
-- "analytics flushed and closed; network.db closed; exit 0"
++ "analytics flushed and closed; the ov_network PostgreSQL database closed; exit 0"
],
"note": "openvibe-sdk/service; a stop that passes 10 s exits 1. Only the Discord link's in-memory state sweep ends with the process; the email queue and the outboxes resume from the database on the next start"
},
@@@ -163,7 +163,7 @@
"range": ">=0.2.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns network.db (better-sqlite3, single writer); a stream-live announcement is claimed per streamer with a cooldown and a daily cap in the same database"
++ "none": "no claims: one process owns the ov_network PostgreSQL database; Network's live.stream.started consumer claims a stream-live announcement per streamer with a cooldown and a daily cap in one transaction there"
}
}
}
ddiff --git a/manifests/services/news.json b/manifests/services/news.json
iindex f6fed852..216d19d6 100644
---- a/manifests/services/news.json
++++ b/manifests/services/news.json
@@@ -140,8 +140,8 @@
"range": ">=0.19.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns news.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_news PostgreSQL database; writes are transactions there"
}
},
-- "notes": "Port 4820. Owns news_topics, news_source_items, news_story_clusters, news_stories, news_story_revisions, news_story_sources, news_perspectives, news_timeline_entries, news_editorial_flags in its own SQLite (openvibe-publishing packages, prefixes news_story and news). Consumes OpenVibe.Sources (sources.item.read, optionally sources.source.read) through an Events subscription (sources.item.*, sources.fetch.failed; events.subscription.manage) and a cursor pull; OpenVibe.Network (SSO, identity.subject.resolve); optionally OpenVibe.AI (ai.run.create, namespace news) for news.summarize_story and news.compare_perspectives drafts; publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads news.index_document.* from Events."
++ "notes": "Port 4820. Owns news_topics, news_source_items, news_story_clusters, news_stories, news_story_revisions, news_story_sources, news_perspectives, news_timeline_entries, news_editorial_flags in its own PostgreSQL database ov_news (openvibe-publishing packages, prefixes news_story and news). Consumes OpenVibe.Sources (sources.item.read, optionally sources.source.read) through an Events subscription (sources.item.*, sources.fetch.failed; events.subscription.manage) and a cursor pull; OpenVibe.Network (SSO, identity.subject.resolve); optionally OpenVibe.AI (ai.run.create, namespace news) for news.summarize_story and news.compare_perspectives drafts; publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads news.index_document.* from Events."
}
ddiff --git a/manifests/services/reviews.json b/manifests/services/reviews.json
iindex 3895b2d5..6170b449 100644
---- a/manifests/services/reviews.json
++++ b/manifests/services/reviews.json
@@@ -138,7 +138,7 @@
"range": ">=0.19.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns reviews.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_reviews PostgreSQL database; writes are transactions there"
}
},
"notes": "Entities with aliases and typed links; resolution of OpenVibe.Sources review items by deterministic rules (source binding, URL, GTIN/SKU/MPN) with editor confirmation for name-only and conflicting matches; merges that rewrite nothing and splits that restore attribution exactly, both audited; typed signals with provenance (source item, item revision, retrieval time, licence note) and trust metadata; aggregates computed only from signals present (method reviews-aggregate@1, inputs and exclusions exposed, absent without qualifying signals, a new revision on every change); editor-written or AI-drafted-and-approved summaries whose points cite signals and never carry a rating; source removal withdraws signals, flags citing summaries and prepares a pending revision; corrections queue; Community discussion referenced, not copied. Server-rendered pages useful without JavaScript; AggregateRating/Product/Review JSON-LD only when signals back it; sitemaps, feeds and Search index events from the openvibe-publishing v0.2.0 gate. Deployed internally (loopback only), not launched publicly: openvibe.reviews serves the OpenVibe.Sites placeholder until the launch rule holds."
ddiff --git a/manifests/services/search.json b/manifests/services/search.json
iindex 47584784..48d706f6 100644
---- a/manifests/services/search.json
++++ b/manifests/services/search.json
@@@ -80,10 +80,10 @@
"range": ">=0.7.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns search.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_search PostgreSQL database; writes are transactions there"
}
},
-- "notes": "Canonical index document (search.index-document@1), event-fed and direct indexing with revision ordering and tombstones, permission-aware query over SQLite FTS5 (docs/adr-engine.md). Anonymous queries need no token.",
++ "notes": "Canonical index document (search.index-document@1), event-fed and direct indexing with revision ordering and tombstones, permission-aware query over PostgreSQL full-text search in ov_search (docs/adr-engine.md). Anonymous queries need no token.",
"site": {
"name": "Search",
"icon": "search",
ddiff --git a/manifests/services/sources.json b/manifests/services/sources.json
iindex 51b12d13..05f09a88 100644
---- a/manifests/services/sources.json
++++ b/manifests/services/sources.json
@@@ -76,7 +76,7 @@
"range": ">=0.7.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns sources.db (better-sqlite3, single writer); a second run of a source already in flight is refused in memory"
++ "none": "no claims: one process owns the ov_sources PostgreSQL database; writes are transactions there; a second run of a source already in flight is refused in memory"
}
},
"notes": "Source registry and ingestion workers (RSS/Atom, sitemaps, JSON-LD, mapped official APIs, manual). Every item carries provenance; every fetch is a recorded run with an explicit state; failures never create or modify items."
ddiff --git a/manifests/services/tips.json b/manifests/services/tips.json
iindex a0b94ea9..798ca495 100644
---- a/manifests/services/tips.json
++++ b/manifests/services/tips.json
@@@ -153,7 +153,7 @@
"range": ">=0.11.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns tips.db (better-sqlite3, single writer); an effect moves with a compare-and-set on its state"
++ "none": "no claims: one process owns the ov_tips PostgreSQL database; an effect moves with a compare-and-set on its state in one transaction"
}
},
"notes": "Creator support (roadmap Wave 9): tip interactions whose payment state mirrors OpenVibe.Billing (keyed by Billing transaction id) and whose delivery state is Tips' own; goals derived from settled interactions; paid messages, TTS and media requests created on settlement; scoped revocable overlay tokens with SSE overlays; simulation mode. Tips never moves money (ADR-012). Alpha: deployed internally (loopback only), not launched publicly: openvibe.tips serves the OpenVibe.Sites placeholder until the launch rule in README.md holds."
ddiff --git a/manifests/services/tools.json b/manifests/services/tools.json
iindex 5cb127c5..f68b096a 100644
---- a/manifests/services/tools.json
++++ b/manifests/services/tools.json
@@@ -61,7 +61,7 @@
"timers, pollers and job workers stopped: the gateway's catalog, services and satellite pollers and search indexer; the retention timers and job workers of img, audio and docs (open job event streams end); yt's download cleanup",
"stops taking connections; idle keep-alive connections closed; requests in flight answered with Connection: close and allowed to finish (4 s at most, then cut); open event streams closed (EventSource reconnects)",
"recent-tool usage flushed to Network (1 s at most)",
-- "analytics flushed and closed; jobs store and worker pools closed (running jobs stay running in jobs.db for the next boot); guard closed; the gateway's cutoff store closed",
++ "analytics flushed and closed; jobs store and worker pools closed (running jobs stay running in the ov_tools PostgreSQL database for the next boot); guard closed; the gateway's cutoff store closed",
"exit 0"
],
"note": "every Tools process (the gateway, openvibe-tools.service, and the seven satellites) stops through apps/_shared/graceful.js; a stop that passes 5 s exits 1. The units set no TimeoutStopSec (systemd's 90 s default applies)"
@@@ -70,7 +70,7 @@
"resumes": [
{
"kind": "jobs",
-- "what": "jobs left running in img, audio and docs jobs.db are re-queued while attempts remain (onRestart requeue), else failed as retryable"
++ "what": "jobs left running in the ov_tools PostgreSQL database for img, audio and docs are re-queued while attempts remain (onRestart requeue), else failed as retryable"
},
{
"kind": "outbox",
@@@ -96,8 +96,8 @@
"range": ">=0.7.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns each app's jobs.db (better-sqlite3, single writer); a job is taken with a compare-and-set (queued \u2192 running)"
++ "none": "no claims: each app's process uses the ov_tools PostgreSQL database; a job is taken with a compare-and-set (queued \u2192 running) in one transaction"
}
},
-- "notes": "Public at openvibe.tools: 169 tools in 9 families on the gateway (port 4001) and its satellites, catalogue at GET /api/catalog.json (re-served by Network). Asynchronous jobs (Wave 11) run on the img, audio and docs satellites only (POST /api/v1/jobs, GET/DELETE /api/v1/jobs/:id, POST /api/v1/jobs/:id/retry, PUT|DELETE /api/v1/jobs/:id/references/:ref, SSE events, result files); the gateway has no /api/v1/jobs yet. Job results are stored as private Media objects (TOOLS_JOB_RESULTS=media: Tools holds media.object.upload and media.object.read, namespace tools) and job lifecycle events tools.job.created|started|succeeded|failed are published to OpenVibe.Events through an outbox in each satellite's jobs.db (EVENTS_URL set; events.event.publish). The tool registry (ADR-027, tools.tool.read) is served: GET /api/v1/tools[/:id[/schema]] on the gateway, for all 169 tools, and on the img, audio, docs, text, yt, maps and food satellites for their own. Planned (ADR-027): the uniform run API POST /api/v1/tools/:id/run (tools.tool.run; network probes need tools.net.probe), a jobs facade on the gateway, tiered quotas and a pseudonymous abuse log; the legacy /api/process, /api/net/* and /api/dev/* routes keep working with Deprecation and Sunset (2026-12-31) headers. GET /api/ready is truthful on the gateway (it checks every satellite) and on each satellite."
++ "notes": "Public at openvibe.tools: 169 tools in 9 families on the gateway (port 4001) and its satellites, catalogue at GET /api/catalog.json (re-served by Network). Asynchronous jobs (Wave 11) run on the img, audio and docs satellites only (POST /api/v1/jobs, GET/DELETE /api/v1/jobs/:id, POST /api/v1/jobs/:id/retry, PUT|DELETE /api/v1/jobs/:id/references/:ref, SSE events, result files); the gateway has no /api/v1/jobs yet. Job results are stored as private Media objects (TOOLS_JOB_RESULTS=media: Tools holds media.object.upload and media.object.read, namespace tools) and job lifecycle events tools.job.created|started|succeeded|failed are published to OpenVibe.Events through an outbox in the ov_tools PostgreSQL database (EVENTS_URL set; events.event.publish). The tool registry (ADR-027, tools.tool.read) is served: GET /api/v1/tools[/:id[/schema]] on the gateway, for all 169 tools, and on the img, audio, docs, text, yt, maps and food satellites for their own. Planned (ADR-027): the uniform run API POST /api/v1/tools/:id/run (tools.tool.run; network probes need tools.net.probe), a jobs facade on the gateway, tiered quotas and a pseudonymous abuse log; the legacy /api/process, /api/net/* and /api/dev/* routes keep working with Deprecation and Sunset (2026-12-31) headers. GET /api/ready is truthful on the gateway (it checks every satellite) and on each satellite."
}
ddiff --git a/manifests/services/trade.json b/manifests/services/trade.json
iindex 1332cfdb..cdd85f52 100644
---- a/manifests/services/trade.json
++++ b/manifests/services/trade.json
@@@ -146,8 +146,8 @@
"range": ">=0.19.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns trade.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_trade PostgreSQL database; writes are transactions there"
}
},
-- "notes": "Port 4860. Informational only (ADR-025): no custody, order execution, escrow, listings between users or personalised advice. Owns trade_instruments, trade_instrument_aliases, trade_watchlists, trade_watchlist_items, trade_market_observations, trade_source_documents, trade_alert_rules, trade_alert_deliveries, trade_context_revisions in its own SQLite. Reads OpenVibe.Sources (sources.item.read, sources.source.read, category trade) by cursor and wakes on signed sources.* webhook deliveries; consumes OpenVibe.AI trade.summarize_market_context output as reviewed drafts; publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads trade.index_document.* from Events."
++ "notes": "Port 4860. Informational only (ADR-025): no custody, order execution, escrow, listings between users or personalised advice. Owns trade_instruments, trade_instrument_aliases, trade_watchlists, trade_watchlist_items, trade_market_observations, trade_source_documents, trade_alert_rules, trade_alert_deliveries, trade_context_revisions in its own PostgreSQL database (ov_trade). Reads OpenVibe.Sources (sources.item.read, sources.source.read, category trade) by cursor and wakes on signed sources.* webhook deliveries; consumes OpenVibe.AI trade.summarize_market_context output as reviewed drafts; publishes through OpenVibe.Events (events.event.publish); OpenVibe.Search reads trade.index_document.* from Events."
}
ddiff --git a/manifests/services/vip.json b/manifests/services/vip.json
iindex c795e8ea..7b5420c8 100644
---- a/manifests/services/vip.json
++++ b/manifests/services/vip.json
@@@ -138,7 +138,7 @@
"range": ">=0.14.0 <1.0.0"
},
"leases": {
-- "none": "no claims: one process owns vip.db (better-sqlite3, single writer)"
++ "none": "no claims: one process owns the ov_vip PostgreSQL database; writes are transactions there"
}
},
"notes": "Memberships (ADR-012): plans, immutable versioned plan terms, perks, product bindings, member preferences and gated-resource policy. OpenVibe.Billing holds subscriptions, charges, renewals, refunds and the canonical entitlements; VIP keeps a short-lived projection of them (valid_until, authoritative fallback, 'unknown' never authorizes). Alpha: deployed internally (loopback only), not launched publicly: openvibe.vip serves the OpenVibe.Sites placeholder until the launch rule holds."