Skip to content

fix(api): Scope item and user lists and issue linking to an organization - #77

Draft
sentry-junior[bot] wants to merge 1 commit into
mainfrom
mattduncan/ie-93-scope-items-to-org
Draft

sentry-junior[bot] wants to merge 1 commit into
mainfrom
mattduncan/ie-93-scope-items-to-org

Conversation

@sentry-junior

@sentry-junior sentry-junior Bot commented Oct 28, 2026 •

Copy link
Copy Markdown
Contributor

Fixes three places where one organization's data could be read or modified through another organization's request. Same change in both the Python and TypeScript backends.

Refs IE-93.

Changes

GET /api/items/ and GET /api/users/

Before: if ?organization= was missing, or didn't match an organization, the endpoint returned rows from every organization.

After:

  • missing organization → 400
  • unknown organization → 404
  • otherwise only that organization's rows are returned

The frontend (KanbanPage.tsx) is the only caller, and it always passes ?organization=<slug>.

Python only: on /api/items/, the user filter used to be skipped when the request went through the Sentry-enrichment path. It's now applied in both paths.

POST /api/sentry/issue-link/link/

Before: the selected item was looked up by itemId alone, so an installation could link a Sentry issue to another organization's item.

After: the lookup also matches the installation's organization, and returns 404 if the item isn't found. Previously a missing item crashed with a 500.

Files:

  • backend-py/src/api/endpoints/items.py, users.py, sentry/issue_link.py
  • backend-ts/src/api/items.ts, users.ts, sentry/issueLink.ts

Tests

Removed the two tests per backend that asserted the unscoped behavior (GET with no organization returns everything). Added:

  • GET items / users with no organization → 400
  • GET items / users with an unknown organization → 404
  • linking an item from another organization → 404, and the item is left unchanged
  • Python: user filter combined with organization, including a user from another organization → empty list

All the new tests fail against main (7 Python, 5 TypeScript) and pass on this branch.

Verification

  • backend-py: pytest 60 passed (Python 3.13); black 22.6.0 and flake8 4.0.1 clean on changed files
  • backend-ts: jest 44 passed; tsc --noEmit clean; eslint clean on changed files except a Prettier error in src/api/items.ts line 18, which is also on main
  • Both containers against the seeded DB: no organization → 400, unknown → 404, acme → 200 for /api/users/ (both) and /api/items/ (TS)

/api/items/?organization=acme on the Python container returns 500 on both main and this branch. It's unrelated to this change: Item.sentry_id is not None in items.py always evaluates to True, so every request goes down the Sentry-enrichment path and fails when the org has no Sentry installation.

via matt.duncan.

--

View Junior Session [Sentry]

GET /api/items/ and GET /api/users/ returned rows from every
organization when the organization query parameter was missing or did
not match an organization. Both backends now return 400 when it is
missing and 404 when it is unknown, and only ever return the requested
organization's rows. In the Python backend the user filter on
/api/items/ is now also applied when items are enriched with Sentry
data.

The issue-link 'link' endpoint looked up the selected item by ID alone,
so an installation could link a Sentry issue to another organization's
item. It now only matches items in the installation's organization and
returns 404 otherwise.

Refs IE-93

Co-Authored-By: Matt Duncan <[email protected]>
@linear-code

linear-code Bot commented Oct 28, 2026

Copy link
Copy Markdown

IE-93

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

0 participants