Skip to content

Allow integration installs to complete from a CLI #127853

Open

Description

@sentry-junior

The API-mode integration pipeline (POST /api/0/organizations/{org}/pipeline/integration_pipeline/) already models most providers as API steps, but a client authenticated with a bearer token (e.g. the Sentry CLI, getsentry/toolkit#1519, getsentry/toolkit#1520) can't finish an install.

Blockers

  • State is session-bound. RedisSessionStore keys pipeline state via request.session (src/sentry/utils/session_store.py), and Pipeline.get_for_request / unpack_state read it from there (src/sentry/pipeline/base.py). Token requests have no session, so nothing persists between initialize and later steps.
  • OAuth callbacks only reach a browser. PipelineAdvancerView (src/sentry/web/frontend/pipeline_advancer.py, extensions/<provider>/setup/) looks up the pipeline from the browser's session and, in API mode, relays params to window.opener via postMessage. A pipeline started by a CLI is never found ("Invalid request").
  • OAuth state is not per-pipeline. pipeline.signature is an md5 of the step class names (pipeline/base.py), identical for every install of a provider. It's used as OAuth state (identity/oauth2.py, integrations/github/integration.py, jira, msteams), so it can't identify a pipeline and adds no CSRF protection beyond the session cookie.
  • Loopback redirects mostly don't apply. Sentry-owned apps (GitHub, Slack, Azure DevOps, Discord, PagerDuty) have a fixed redirect URI and exchange the code server-side with the client secret.
  • Publish status. OrganizationPipelineEndpoint is EXPERIMENTAL and POST sentry-app-installations is PRIVATE, so neither is in the public schema / @sentry/api.

Per-provider edge cases

  • Fully JSON once state is fixed: Opsgenie.
  • Mostly JSON: GitHub when the app is already installed (chosen_installation_id), GitHub Enterprise (accepts a raw installation_id), GitLab (config step; needs a customer OAuth app), Azure DevOps (account selection).
  • Provider consent always in a browser: Slack, Discord, GitHub when the app isn't installed. Unverified whether GitHub passes state through the app-install Setup URL redirect.
  • Vendor-initiated: Jira Cloud and MS Teams need signed params from the vendor side.
  • Bitbucket Cloud (Atlassian Connect) returns no state, so the callback can't be tied to a pipeline. Bitbucket Server's OAuth1 callback has the same problem.
  • Unverified whether PagerDuty accepts an arbitrary redirect_url.
  • Linear is a Sentry App: install via POST /organizations/{org}/sentry-app-installations/, then the user finishes on linear.app. The grant code is only returned with org:integrations.

Proposals (raised by Burak Yigit Kaya)

  • Use provider device-authorization grants where available (e.g. GitHub) instead of browser redirects.
  • With user consent, drive more of the flow through existing provider CLIs such as gh.
  • For providers that require a redirect, open a temporary tunnel from Sentry's servers to finalize the flow.

Open questions

  • Can a cookie-jar stopgap (CLI keeps sentrysid from initialize) work through the API gateway and customer domains? Untested; it wouldn't cover OAuth callbacks.
  • Should the pipeline endpoint and Sentry App install POST become PUBLIC? Needs sign-off from the owning teams (FOUNDATIONS / INTEGRATION_PLATFORM).

via byk.

--

View Junior Session [Sentry]

Activity

  1. linear-code commented on Oct 16, 2026

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

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions