DealsOfferCreatedPayload deals.offer.created@1
Generated at from
openvibe-contracts v0.34.2 and
openvibe-sdk v0.5.0.
- Version
- 1.0.0
- Owner
- deals
- Visibility
- first-party
- Status
- active
- Compatibility
- backward
- Schema
https://openvibe.network/contracts/events/payloads/deals.offer.created.v1.json
deals.offer.created v1 (OpenVibe.Deals server/domain/indexing.js emitOffer, called from server/domain/offers.js submit and createImported). A deal was posted: a person submitted a link (submit), or the Sources importer created an offer from a deals-category Sources item (createImported, the only caller that adds imported_from). Written in the transaction that inserted the offer and its first observation, next to deals.index_document.upserted. The payload describes the canonical offer as it now stands: canonical page URL, status, store domain, product, the latest observation (price text exactly as stated, never inferred; null where the source or person stated nothing) with its observed_at, the freshness verdict and the Search-shaped indexability decision. Deliberately left out: the description, the submitter's identity, vote counts and hotness. Envelope: subject { type: offer, id: <offer_id> }, visibility public when the offer is active and the SEO gate lets it be listed, otherwise internal, priority important (default), actor user:<submitter usr_…> for a submission, service:deals for an import. No consumer is built yet.
Fields
| Field | Type | Required | Description | Constraints |
|---|---|---|---|---|
offer_id | string | yes | The canonical (root) offer id. |
|
slug | string | yes | Page slug: the slugified title plus the last six characters of the id. |
|
url | string | yes | Canonical offer page URL on Deals (/d/<slug>). |
|
title | string | yes |
| |
status | const | yes | A new offer is always active. |
|
store | string | null | yes | Store domain: the offer link's host without a leading www.; null when none could be derived. |
|
product_id | string | null | yes | Deals product the offer is attached to, if any. |
|
latest_observation | object | null | yes | The newest observation across the offer's merge group; null only when the group has none. | |
freshness | enum | yes | fresh while the latest observation is younger than DEALS_FRESHNESS_HOURS, stale after, unobserved without one. |
|
indexability | object | yes | The SEO gate decision in Search's shape (index-hooks searchIndexability). |
|
indexability.decision | enum | yes |
| |
indexability.reasons | array of string | yes | Search reason names, e.g. stale_price, expired, takedown, owner_decision (imported or AI text awaiting review). |
|
imported_from | object | Only on imports: the OpenVibe.Sources item the offer was created from. |
| |
imported_from.service | const | yes |
| |
imported_from.type | const | yes |
| |
imported_from.id | string | yes |
|
Examples
From the contract's own test fixtures: valid ones validate, rejected ones must fail.
Valid: import-no-price
{
"offer_id": "dof_01JAB2C3D4E5F6G7H8J9K0MNPR",
"slug": "garden-hose-reel-weekend-sale-k0mnpr",
"url": "https://openvibe.deals/d/garden-hose-reel-weekend-sale-k0mnpr",
"title": "Garden hose reel weekend sale",
"status": "active",
"store": "garden.example",
"product_id": "dpr_01JAB2C3D4E5F6G7H8J9K0MNPS",
"latest_observation": {
"price": null,
"currency": null,
"availability": null,
"observed_at": "2026-09-23T06:00:00.000Z"
},
"freshness": "fresh",
"indexability": {
"decision": "noindex",
"reasons": [
"owner_decision"
]
},
"imported_from": {
"service": "sources",
"type": "item",
"id": "itm_01JAB2C3D4E5F6G7H8J9K0MNPW"
}
}Valid: submission
{
"offer_id": "dof_01JAB2C3D4E5F6G7H8J9K0MNPQ",
"slug": "usb-c-charger-65w-k0mnpq",
"url": "https://openvibe.deals/d/usb-c-charger-65w-k0mnpq",
"title": "USB-C charger 65W",
"status": "active",
"store": "shop.example",
"product_id": null,
"latest_observation": {
"price": "29.99",
"currency": "USD",
"availability": "in_stock",
"observed_at": "2026-09-23T10:15:00.000Z"
},
"freshness": "fresh",
"indexability": {
"decision": "index",
"reasons": []
}
}Rejected: expired-at-creation
{
"offer_id": "dof_01JAB2C3D4E5F6G7H8J9K0MNPQ",
"slug": "usb-c-charger-65w-k0mnpq",
"url": "https://openvibe.deals/d/usb-c-charger-65w-k0mnpq",
"title": "USB-C charger 65W",
"status": "expired",
"store": "shop.example",
"product_id": null,
"latest_observation": {
"price": "29.99",
"currency": "USD",
"availability": "in_stock",
"observed_at": "2026-09-23T10:15:00.000Z"
},
"freshness": "fresh",
"indexability": {
"decision": "index",
"reasons": []
}
}Rejected: missing-indexability
{
"offer_id": "dof_01JAB2C3D4E5F6G7H8J9K0MNPQ",
"slug": "usb-c-charger-65w-k0mnpq",
"url": "https://openvibe.deals/d/usb-c-charger-65w-k0mnpq",
"title": "USB-C charger 65W",
"status": "active",
"store": "shop.example",
"product_id": null,
"latest_observation": {
"price": "29.99",
"currency": "USD",
"availability": "in_stock",
"observed_at": "2026-09-23T10:15:00.000Z"
},
"freshness": "fresh"
}Rejected: numeric-price
{
"offer_id": "dof_01JAB2C3D4E5F6G7H8J9K0MNPQ",
"slug": "usb-c-charger-65w-k0mnpq",
"url": "https://openvibe.deals/d/usb-c-charger-65w-k0mnpq",
"title": "USB-C charger 65W",
"status": "active",
"store": "shop.example",
"product_id": null,
"latest_observation": {
"price": 29.99,
"currency": "USD",
"availability": "in_stock",
"observed_at": "2026-09-23T10:15:00.000Z"
},
"freshness": "fresh",
"indexability": {
"decision": "index",
"reasons": []
}
}Rejected: submitter-identity
{
"offer_id": "dof_01JAB2C3D4E5F6G7H8J9K0MNPQ",
"slug": "usb-c-charger-65w-k0mnpq",
"url": "https://openvibe.deals/d/usb-c-charger-65w-k0mnpq",
"title": "USB-C charger 65W",
"status": "active",
"store": "shop.example",
"product_id": null,
"latest_observation": {
"price": "29.99",
"currency": "USD",
"availability": "in_stock",
"observed_at": "2026-09-23T10:15:00.000Z"
},
"freshness": "fresh",
"indexability": {
"decision": "index",
"reasons": []
},
"submitted_by": "usr_01JAB2C3D4E5F6G7H8J9K0MNPX"
}Validate
const contracts = require('openvibe-contracts');
contracts.validate('deals.offer.created@1', value); // { valid, errors: [{ path, message }] }