User Journey: Import as a party-scoped user
Table of Contents
This page documents a user journey: An operations user imports into their own party and sees only what that party may see, while a tenant administrator imports for the tenant.
A user journey describes what one person is trying to do, before anything is built. It is a design document that outlives any sprint, so it names the screens, the entity fields each screen shows, and the operations and messages each step needs.
1. Goal
"I want to bring data into the party I work in, and I want to see only that party's data afterwards." The journey is done when the import is scoped to the session's party, the person can read what they imported, and a party they do not work in is neither a target nor a result.
2. Actor and trigger
The actor is an operations user signed in to one party. The tenant administrator runs the same journey with the same subject and a wider scope. The trigger is a file that belongs to the person's party, not to the tenant.
The actor's permissions decide which half of the journey is reachable today. A
tenant administrator or super administrator holds every permission the imports
need, because their role carries a wildcard. An operations user holds
refdata::conventions:write but not the run-document write, the trade write or
the market-data import write. So an operations user cannot drive a portfolio, a
run or a market data import today, and the journey is an administrator journey in
practice.
3. Steps
- Sign in to the party. The person signs in, or switches party. The session carries the party, and every read and write is scoped to it.
- Choose the file. The person has an ORE input directory, a run directory, or a quotes and fixings pair. The file's party is not in the file. The session decides it.
- Import. The person runs the verb. The system checks the session's permissions for each write, and refuses a call whose session has no party.
- Name a party, or not. If the person passes
--party-idfor a party other than the session's, the shell refuses and names the session's party. The conventions save takes no party argument at all. The read path can name a party only when the session acts for none, as a workflow step does. - Read the result. The person reads the imported rows in their own party. The world conventions the tenant owns are visible alongside the party's own, and the screens mark which is which.
- Check the boundary. The person confirms that a book or portfolio of another party is absent, and that an import for another party was refused.
4. On success
The import reports the counts. The rows carry the session's party. The person sees the party's conventions and trades, plus the tenant's world conventions where the model shares them. Another party's rows are absent.
5. On failure
A session with no party is refused with a message that names the missing party.
A --party-id that differs from the session is refused before the import runs.
A read of another party's book is refused or returns nothing. A write refused by
a missing permission returns a plain refusal from the owning service.
6. What must never happen
- An import must never write a row into a party other than the session's.
- A party must never see another party's trades, books or conventions. The tenant's world conventions are the one shared set, and they are marked as world data.
- A party-scoped user must never be shown another party's import result or workflow instance.
- A refusal must never be reported as an empty success.
7. Screens and entry points
There is no import screen. The entry points are the shell verbs. The web UI shows conventions and market data under the session's party, and the access screens show which parties an account may act for. The party switcher changes the session, not the import.
8. Entities composed
| Entity | What it contributes | Model |
|---|---|---|
party |
The scope of every row the import writes | |
account, role, permission |
Who may run which import | |
conventions_bundle |
The party rows, plus the tenant's world rows | |
trade, portfolio, book |
The trade data the session owns | |
sandbox |
The sample sandbox the trade import lands in |
9. Operations and messages
| Step | Operation | Subject | Status |
|---|---|---|---|
| Sign in to the party | Establish the session | the sign-in operation | exists |
| Import | Start the trade import | workflow.v1.ops.ore_import |
exists |
| Import | Start the run import | ore.v1.ops.import_run_configuration |
exists |
| Import | Store the conventions document | refdata.v1.conventions_documents.put |
exists |
| Import | Import market data | marketdata.v1.ops.import_market_data |
exists |
| Read the result | Read the conventions for a party | refdata.v1.conventions_documents.get |
exists |
| Check the boundary | Read a book's rights | refdata.v1.books.get and the rights read |
exists |
10. What is missing
- No party argument on the import verbs. The session is the only scope. That is safe, but it means a tenant administrator cannot stage a party's import without switching to it.
- No import permission of its own. Each import borrows the write permissions of the rows it creates, so granting "may import" means granting every write. No role today means "may import for a party".
- No per-party import history. There is no list of who imported what, into which party.
- No screen. The party scope is not visible on any import surface because there is no import surface.
11. Related journeys
- Onboard a party with its conventions and portfolio - the administrator's version.
- Import one dataset in isolation - a narrower write in the same party.
- Operations - the group whose actors run the installation.
- Entry - signing in and switching party.
12. Related knowledge
13. See also
- Data exchange journeys - the group hub.