Visibility & Targeting
This page explains who can see an Operation and which products appear, plus the pricing precedence when multiple offers exist.
Keep in mind
- Visibility depends on status, dates, type (PUBLIC/PRIVATE), store scoping, catalog views, and locale.
- Pricing uses a clear precedence: Operation price → Account → Tag → Public.
🎯 What “visibility” means
- Operation visibility: whether an Operation is available for all Customer Users linked to attached Accounts. (It appears in
/shop/operations). Accounts must beACTIVE. - Product visibility inside an Operation: whether a specific product variant line is displayed and purchasable in the Operation detail view.
- Pricing visibility: which price applies when multiple offers could match.
🔐 PUBLIC vs PRIVATE
- PUBLIC: visible to all Accounts that meet store/date rules. Only Operators can set type=PUBLIC. Once set, the type cannot be changed.
- PRIVATE: visible only to the attached Accounts. The attachment list is managed on the admin side.
Owner & edits
- Only the creator/owner can modify an Operation.
- Customer Users with the proper right may manage Operations they own; Operators can see any Operation.
🏪 Store scoping
- Operations are linked to a Store (or a list of Stores when available). A Customer User only sees Operations for the current Store context.
- If the Store does not match, the Operation does not appear in
/shop/operationsfor that user.
🌐 Locales
- Admin DTOs are multilingual (names and descriptions by locale).
- Front DTOs are single-locale, filtered by an input locale. If a requested locale is missing, a fallback strategy may apply in the UI.
🗺️ Product visibility inside an Operation
A product line is visible only if the Account is entitled to the product via Catalog Views. The visibility status of a product inside an Operation follows the same rules as outside Operations.
Decision flow (summary)
- Operation must be ACTIVE and within
[startDate, endDate]. - For PRIVATE, the current Account must be attached.
- Store must match the user’s context.
- Catalog Views must expose the product for the Account.
- If all checks pass, the product appears in the Operation detail view.
The following diagram gives a high-level decision tree:
graph LR
%% ---------- Eligibility then catalog-views ----------
S[Start] --> STS[Operation ACTIVE<br>and now within dates]
STS -->|Yes| T{Type}
STS -->|No| H0[Not visible]
T -->|PUBLIC| ST[Store matches]
T -->|PRIVATE| ATT[Account attached]
ATT -->|Yes| ST
ATT -->|No| H1[Not visible]
ST -->|Yes| CV[Catalog Views allow<br>this variant]
ST -->|No| H2[Not visible]
CV -->|Yes| OK[Line visible to buyer]
CV -->|No| H3[Hidden in detail]
%% ---------- Styles ----------
classDef total fill:#e8f1ff,stroke:#2f6feb,stroke-width:2px,color:#0b3d91;
classDef diff fill:#fff4e5,stroke:#f59e0b,stroke-width:2px,color:#7a3e00;
classDef acct fill:#f5e9ff,stroke:#8a2be2,stroke-width:2px,color:#3b0764;
classDef view fill:#ede9fe,stroke:#7c3aed,stroke-width:1.5px,color:#1e1b4b;
classDef union fill:#e9d5ff,stroke:#6d28d9,stroke-width:1.5px,color:#3b0764;
classDef visible fill:#ecfdf5,stroke:#10b981,stroke-width:2px,color:#064e3b;
classDef op fill:#e0f7fa,stroke:#06b6d4,stroke-width:2px,color:#065f46;
classDef inter fill:#fee2e2,stroke:#ef4444,stroke-width:2px,color:#7f1d1d;
classDef resp fill:#f2f4f7,stroke:#475569,stroke-width:2px,color:#111827;
class T,STS,ST diff;
class ATT acct;
class ST view;
class CV union;
class OK visible;
class H0,H1,H2,H3 resp;
style STS rx:8,ry:8
style T rx:8,ry:8
style ATT rx:8,ry:8
style ST rx:8,ry:8
style CV rx:8,ry:8
style OK rx:8,ry:8
style H0 rx:8,ry:8
style H1 rx:8,ry:8
style H2 rx:8,ry:8
style H3 rx:8,ry:8
linkStyle 1 stroke:#2f6feb,stroke-width:2px
linkStyle 5 stroke:#10b981,stroke-width:2px
Tip: the same Catalog View rules apply inside and outside Operations.
💶 Pricing precedence
When multiple offers could apply to a product, the precedence is:
- Operation price (if defined for the line). (Not yet released)
- Account price.
- Tag price.
- Public price.
graph LR OP[Operation price] --> ACC[Account price] ACC --> TAG[Tag price] TAG --> PUB[Public price] NOTE[Pick the first available<br>from top to bottom] --> OP %% ---------- Styles ---------- classDef total fill:#e8f1ff,stroke:#2f6feb,stroke-width:2px,color:#0b3d91; classDef diff fill:#fff4e5,stroke:#f59e0b,stroke-width:2px,color:#7a3e00; classDef resp fill:#f2f4f7,stroke:#475569,stroke-width:2px,color:#111827; classDef op fill:#e0f7fa,stroke:#06b6d4,stroke-width:2px,color:#065f46; class OP op; class ACC,TAG total; class PUB resp; class NOTE diff; style OP rx:8,ry:8 style ACC rx:8,ry:8 style TAG rx:8,ry:8 style PUB rx:8,ry:8 style NOTE rx:8,ry:8 linkStyle 0 stroke:#2f6feb,stroke-width:2px linkStyle 2 stroke:#475569,stroke-width:2px
This ladder represents the fallback order. If an Operation price exists, it wins. If not, fall back to Account, then Tag, then Public.
🧩 Examples
Example 1 — PUBLIC campaign
- Type: PUBLIC, Store=FR, Dates: Sep 1 → Oct 15.
- A Customer User on Store FR sees the Operation in
/shop/operations. - Inside the Operation, they see only the products exposed by their Catalog Views. Prices follow the precedence.
Example 2 — PRIVATE assortment
- Type: PRIVATE with Accounts A and B attached.
- Account C does not see the Operation at all.
- Accounts A and B see it; each Account only sees lines that Catalog Views allow. If some lines are hidden by views, they won’t appear.
Example 3 — Mixed pricing
- A line has no Operation price, but the Account has a specific offer. The Account price applies.
- If neither Operation nor Account offers exist, check Tag; otherwise Public.
🔗 API quicklinks
Headers that matter for visibility
dj-client(OPERATOR or ACCOUNT) anddj-api-keyare required on Admin endpoints. Store scoping usesdj-store/dj-store-view. Localized rendering uses optional locale. 
Admin — Operations (discover & scope)
- GET /v1/operations — ADM-OPERATION-550 (List Operations (filters + sorting + locale + store scoping)).
- Key rules you’ll rely on for visibility:
- Store scoping: effective store is the dj-store header (or tenant default). ACCOUNT callers must be attached to that store, otherwise 403.
- Locale: optional locale renders localized fields; must be allowed by the Operation’s store (fallback to store default).
- Sorting supported on createdAt, startDate, endDate, name.
- Filters include status, ids, name, type, startDateFrom/To, endDateFrom/To, locale, idType, and more (see auto-docs). 
- Key rules you’ll rely on for visibility:
- GET /v1/operations/(operationId) — ADM-OPERATION-500 (Get Operation by ID).
- Honors the same store scoping and access control rules (OPERATOR sees any; ACCOUNT must be the owner with the right to read). 
Admin — Targeting accounts (PRIVATE Operations)
These endpoints exist only for PRIVATE Operations. PUBLIC Operations do not expose the accounts list. 
- POST /v1/operations/(operationId)/accounts — ADM-OPERATION-151 (Add accounts to a PRIVATE Operation).
- Constraints: DRAFT-only, ACCOUNT caller must be owner + right (OPERATIONS_ADD_ACCOUNTS) + attached to store; else 403. 
- GET /v1/operations/(operationId)/accounts — ADM-OPERATION-552 (List accounts linked to a PRIVATE Operation).
- Filters: accountIds, accountName. Default sort accountName ASC; multiple sorts allowed. 
- DELETE /v1/operations/(operationId)/accounts — ADM-OPERATION-351 (Remove accounts from a PRIVATE Operation).
- Constraints: DRAFT-only; provided IDs must already be linked; standard store scoping applies. 
Admin — Lines (context for what buyers may see)
- GET /v1/operations/(operationId)/lines — ADM-OPERATION-551 (List Operation product variants with quantity constraints).
- Useful when auditing what an Operation could surface to buyers (final buyer visibility still depends on Catalog Views on the Shop side). Supports filters like variantIds, variantName, minQuantity, maxQuantity, recommendedQuantity, plus sorting. 
Shop (read-only visibility, referenced here)
- GET /v1/shop/operations - OPERATION-550 (List Operations available for a customer user)
- GET /v1/shop/operations/(id) - OPERATION-500 (Get Operation details available for a customer user)
- GET /shop/operations/(id)/lines - OPERATION-551 (List lines for a given operation)
- Buyers see only Operations that are eligible to them (status/date window, store scope, and for PRIVATE: account attached).
⸻
Tip: For a quick “who can see what?” check in Admin, combine:
- GET /v1/operations?type=PRIVATE&… to find the Operation (with store + locale context), then
- GET /v1/operations/(operationId)/accounts to inspect targeting, and
- GET /v1/operations/(operationId)/lines to audit product scope before testing in Shop.   
- Buyer list:
GET /shop/operations— returns only ACTIVE Operations within date and store scope, filtered by Account eligibility. - Buyer detail:
GET /shop/operations/(id)andGET /shop/operations/(id)/lines— only lines visible via Catalog Views will appear. - Admin attach Accounts (PRIVATE):
POST /v1/operations/(id)/accounts(+ GET/DELETE to list or remove).
✅ Checklist before you publish
- Type is correct (PUBLIC or PRIVATE) — remember it cannot be changed later.
- Store is set properly.
- Localized name/description are filled.
- For PRIVATE, Accounts are attached.
- Catalog Views expose all intended products for those Accounts.
- Optional: Operation prices configured where needed.
Updated 23 days ago
