Skip to content

Review guide refuses Forgejo PRs when the project's SSH remote host differs from the web host #29753

Closed

Description

@olschulz

What happened

In a Forgejo project whose origin is an SSH remote on a different hostname from the web UI, "Write review guide" on a linked PR fails with:

Guides are written from this project's checkout, and this pull request is in another repository. Write it from a project that is a checkout of that repository.

The PR is in the project's own repository. It was linked to the thread automatically and shows as open.

This setup is common for self-hosted Forgejo. The web UI sits behind a reverse proxy or tunnel (Caddy, Traefik, nginx, Cloudflare Tunnel) under a public name like git.example.com, and those usually forward only HTTP(S). Git over SSH can't go through them, so it connects straight to the machine running Forgejo by its LAN, VPN or Tailscale name (e.g. git-ssh.internal), often on a non-default port such as 222 because the host's own sshd already uses 22. Some users also use an alias from ~/.ssh/config as the remote host (e.g. forgejo:owner/repo.git). Either way, the remote URL's host never matches the web host, though both point at the same repository.

Diagnosis

The project's identity comes from its SSH remote, for example ssh://[email protected]:222/owner/repo.git. That gives canonicalKey = git-ssh.internal/owner/repo, while webUrl = https://git.example.com/owner/repo. The PR is stored under the web host, git.example.com.

  • PR linking works because isChangeRequestOnProjectHost / isChangeRequestInProjectRepository also accept the project's web URL.
  • requireOwnRepository in apps/server/src/pullRequest/PullRequestReviewGuideService.ts builds the project's own key with pullRequestSyncKey. That calls sourceControlDefinitions.changeRequestHost. For a non-HTTP remote, Forgejo's changeRequestHost (packages/source-control-forgejo/src/shared/definition.ts) falls back to projectChangeRequestHost, which is the first part of canonicalKey (git-ssh.internal).
  • So own.host !== key.host (git-ssh.internal vs git.example.com), and the guide is rejected.

The same check is unchanged on main. A likely fix: when the identity has a webUrl, Forgejo's changeRequestHost should use that URL's host. Alternatively, requireOwnRepository could match the same way PR linking does. Other code that uses pullRequestSyncKey for SSH-remote Forgejo projects may have the same mismatch.

Steps to reproduce

  1. Self-hosted Forgejo whose SSH hostname differs from its web hostname (e.g. SSH git-ssh.internal:222, web git.example.com).
  2. Add a project whose origin is ssh://[email protected]:222/owner/repo.git. T3 resolves webUrl to https://git.example.com/owner/repo.
  3. In a thread on that project, open a PR on that repo. It gets linked to the thread as git.example.com/owner/repo#N.
  4. Click "Write review guide" on that PR.
  5. The error above appears.

Version

0.1.7-nightly.20261102.4066 (desktop app and its local server). The check is identical on main as of 2026-11-03.

Environment

Linux x64 (CachyOS, kernel 7.3), Node v26.12.1, T3 Code Desktop with a local server. Self-hosted Forgejo reached over SSH through a different hostname than its web UI.

Evidence

- Project `repositoryIdentity`: `canonicalKey: "<ssh-host>/owner/repo"`, `locator.remoteUrl: "ssh://git@<ssh-host>:222/owner/repo.git"`, `webUrl: "https://<web-host>/owner/repo"`, `provider: "forgejo"`
- Thread PR link: `host: "<web-host>"`, `repository: "owner/repo"`, `state: "open"`
- Error toast: "Could not start a review guide — Guides are written from this project's checkout, and this pull request is in another repository. Write it from a project that is a checkout of that repository."

Related issues

None found.

Fix applied or workaround

None applied. A possible workaround, not tested: set origin's fetch URL to the HTTPS web URL and keep SSH as the push URL (git remote set-url --push). This needs HTTPS credentials for fetching when the repo is private.

Filed by

Claude Code (Opus 5.5, claude-opus-5-5) via T3 Code triage

Activity

  1. added a commit that references this issue on Nov 10, 2026
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

    via-triageFiled through npx t3 triage

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions