Make create-operation semantics consistent across all project-scoped catalog entities (create-or-fail vs upsert)
Maintainers usually reply within 1 day
Nobody has claimed this yet.
Assessment
- Difficulty
- 5/5
- Estimated time
- Over a week
- Newbie friendliness
- 42/100
- Issue type
- Feature
- Clarity
- Mostly clear
- Activity status
- Quiet
- Tech stack
- typescript
- Domain
- api, backend-api-design, full-stack
Research direction
Start by re-confirming the listed create behaviors for each catalog entity across the API, portal, and CLI. Decide whether each entity should use create-or-fail or an explicitly documented upsert path, then align the affected clients and add duplicate-create tests and documentation for every entity. Done means the convention, exceptions, API responses, portal behavior, and CLI handling are consistent and covered.
Written by the indexing model from the issue text.
Description
Original author: @cedricvidal
Summary
Create (POST) operations across our project-scoped catalog entities are inconsistent: some behave as create-or-update-if-exists (silent upsert / overwrite), others as create-or-fail-if-exists (409 on duplicate). We should pick one convention and apply it uniformly across the API, portal, and CLI.
This was surfaced while fixing the MCP "Add Server" duplicate-slug bug (PR #1241), where the create flow was silently overwriting an existing server. MCP was moved to create-or-fail (409) there; this issue tracks reconciling the rest.
Current behavior (audit)
| Entity | API create behavior | Portal client-side guard? |
|---|---|---|
| mcp-servers | CREATE-OR-FAIL (409) — fixed in #1241 | Yes (inline + toast) |
| criteria | CREATE-OR-FAIL | Yes |
| prompt-features | CREATE-OR-FAIL (409) | No — API rejects but portal doesn't pre-check |
| report-templates | CREATE-OR-FAIL (409) | Unverified |
| codebases | CREATE-OR-FAIL (unique-index E11000) | n/a |
| skills | UPSERT (findOne → updateOne/insertOne, 200/201) | n/a |
| extensions | UPSERT (same pattern as skills) | n/a |
| agents | UPSERT (explicit "upsert" semantics, 200/201) | — |
| agent-versions | UPSERT (by agentVersion) |
— |
| task-prompts | findOrCreate (always 201) | — |
File:line citations were gathered during the audit and can be reattached in the implementing PR. Treat the table as the starting inventory; each row should be re-confirmed before changing.
Problems
- Inconsistent, surprising semantics — the same "create" verb silently overwrites for some entities and rejects for others. A user re-adding an existing skill silently mutates it; re-adding an MCP server now errors.
- Data-loss risk — silent upsert on create can overwrite a record a user didn't intend to touch (the exact MCP bug).
- API/portal mismatch —
prompt-featuresreturns 409 from the API but the portal offers no client-side duplicate guard, so the user only discovers the conflict after submitting.
Proposed direction (to be decided)
Adopt create-or-fail (409) as the standard for user-facing catalog creates, with updates done explicitly via PUT. Rationale: least-surprise, no accidental overwrite, matches the MCP + criteria pattern.
- Some entities may have intentional idempotent re-import semantics (skills/extensions re-import, agent-version registration from workers). Those need an explicit decision: keep upsert (and document it) OR split into distinct create vs. update paths. Do not blanket-change without confirming each intent.
- Wherever the API is create-or-fail, add a matching portal client-side duplicate guard (inline error + disabled submit) for parity, and ensure the CLI surfaces the 409 cleanly.
Scope
- Out of scope for PR #1241 (per-project data organization). This is a follow-up.
- Deliverables: decision on the standard, per-entity reconciliation (API + portal + CLI), tests, and docs.
Acceptance criteria
- A documented, agreed convention for create-vs-update across catalog entities.
- Each entity's
POSTconforms (or its deviation is explicitly justified and documented). - Portal and CLI behavior matches the API for every entity (no silent-overwrite where the API 409s; no 409-only-after-submit where a pre-check is feasible).
- Tests cover the duplicate-create path per entity.
- Dominant language
- TypeScript
- Stars
- 5
- Forks
- 5
- Avg merge
- 3d 5h
- Merged PRs (30d)
- 26
Getting set up
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from microsoft/scope
-
type: worker-update
Difficulty 1/5 1-3 hours Newbie friendliness 85/100
Maintainers usually reply within 1 day
-
type: worker-update
Difficulty 1/5 Under an hour Newbie friendliness 88/100
Maintainers usually reply within 1 day
-
type: worker-update
Difficulty 1/5 1-3 hours Newbie friendliness 78/100
Maintainers usually reply within 1 day
-
author: JaGord documentation good first issue UI
Difficulty 2/5 1-3 hours Newbie friendliness 72/100
Maintainers usually reply within 1 day
-
author: cedricvidal bug portal
Difficulty 2/5 1-3 hours Newbie friendliness 85/100
Maintainers usually reply within 1 day
Similar issues
-
Difficulty 2/5 1-3 hours Newbie friendliness 84/100
Maintainers usually reply within 1 day
-
📕documentation
Difficulty 2/5 1-3 hours Newbie friendliness 72/100
db-ux-design-system/core-web#8343 ·
Maintainers usually reply within 1 day
-
enhancement triage/needs-triage
Difficulty 2/5 1-3 hours Newbie friendliness 88/100
heygen-com/hyperframes#4944 ·
Maintainers usually reply within 1 day
-
ai-driven-qa bug claude
Difficulty 2/5 1-3 hours Newbie friendliness 82/100
linagora/twake-calendar-frontend#1493 · 1 comment ·
Maintainers usually reply within 1 day
-
Difficulty 2/5 1-3 hours Newbie friendliness 72/100
material-extensions/vscode-material-icon-theme#3610 ·
Maintainers usually reply within 2 days