F
Flowman docsWorkflow SDK
Back to app
Connectors

GitHub connector

The GitHub connector links a project to a GitHub App installation so a run can read live pull request status from GitHub. Unlike the IMAP connector, it is not a polling worker in connector-runtime — it is an on-demand integration. When you select Refresh PR status from Run actionson a run, Flowman queries GitHub for the run's pull requests, updates their stored state, and marks the workflow done once every PR is merged or closed. The same installation also lets the automatic Cursor Cloud ready-for-review Sub-agent convert linked draft PRs to ready.

Create the GitHub App

One GitHub App serves the whole Flowman instance. In GitHub, go to Settings → Developer settings → GitHub Apps → New GitHub App and configure:

  • Repository permissions: Contents: Read and write, Pull requests: Read and write, and Metadata: Read-only. Contents and pull-request write access are required for Codex Cloud to push its working branch and create or update the run's pull request. Pull-request write access is also required for Cursor Cloud's deterministic ready-for-review child.
  • Setup URL: <APP_URL>/api/connectors/github/setup, with "Redirect on update" enabled so reinstalls return to Flowman.
  • Subscribe to the Pull request webhook event pointed at <APP_URL>/api/webhooks/github/pull-request. When a Flowman-linked PR is merged or closed, Flowman records the terminal state and marks the run done automatically — the same outcome as selecting Refresh PR status. For local coding sessions started from Jira Intake, completion first queues the installed completion skill so it can verify the base branch, transition the linked Jira issue to Done, and then finish the Flowman run. Other local sessions queue a runtime base-branch sync so the workspace checks out and fast-forward pulls the PR target when the worktree is clean.
  • Generate a private key (PEM), and note the App ID, client id/secret, and the app slug.

Environment variables

Set these on the Flowman web/Convex deployment (instance-wide):

  • GITHUB_APP_ID — the numeric App ID.
  • GITHUB_APP_PRIVATE_KEY — the PEM private key (literal \n escapes are accepted).
  • GITHUB_APP_SLUG — the app slug used to build the install URL.
  • GITHUB_APP_CLIENT_ID / GITHUB_APP_CLIENT_SECRET— the app's OAuth client credentials.
  • Reuse FLOWMAN_PR_COMPLETION_TOKEN on both the Next.js app and Convex deployment. For the pull request webhook, also set GITHUB_WEBHOOK_SECRET to the secret configured on the GitHub App webhook.

Connect a project

On /p/<slug>/connectors an admin presses Connect GitHub. Flowman redirects to GitHub's installation page; after you choose the repositories, GitHub returns to the setup URL and Flowman stores the installation id for the project (scoped per project, like other credentials). Each project keeps only the installation id — the App private key never leaves the server environment.

Refresh PR status and finalize

When Cursor Cloud finishes its initial implementation and Flowman has linked at least one PR, a Flowman-managed Sub-agent mints a short-lived installation token, reads every PR's live draft state, and uses GitHub's ready-for-review mutation for drafts. One child covers all polyrepo PRs. It is idempotent and independently retryable, so an already-ready PR succeeds without another mutation and a child failure does not change the completed implementation result.

When a run has an open pull request, Run actions includes Refresh PR status. With GitHub connected, selecting it mints a short-lived installation token, reads each pull request via the GitHub REST API, and maps the result to Flowman's open / closed / merged state. When all linked pull requests are merged or closed, the coding session and workflow run are marked done. Jira-linked local sessions first queue the installed completion skill and require its verified Jira Done result. Other local sessions also queue a runtime base-branch sync (checkout + ff-only pull of the PR target when the worktree is clean). If the GitHub App webhook is configured, the same finalize happens automatically when GitHub delivers a pull_request closed event. If GitHub is not connected, the button falls back to asking the coding agent to reconcile completion.