open-swe/tests/test_app_bot_identity.py
Adam Moussa 8a9974c3c4
Some checks failed
CI / Lint (push) Waiting to run
CI / Format check (push) Waiting to run
CI / Unit tests (push) Waiting to run
CI / Playwright E2E (push) Waiting to run
Build & publish app artifacts / Publish + deploy (dev) (push) Has been cancelled
Build & publish app artifacts / Publish + deploy (prod) (push) Has been cancelled
Infra CD / Infra CI (pre-deploy) (push) Has been cancelled
Infra CD / Deploy open-swe-dev (push) Has been cancelled
Infra CD / Deploy open-swe-prod (push) Has been cancelled
feat: author Slack/dashboard/schedule commits + PRs as the app by default (#57) (#60)
* feat: default Slack/dashboard/schedule PRs + commits to the app identity (#57)

Slack/dashboard/schedule runs now author PRs and run git/gh operations as the
GitHub App seahaven-openswe[bot] by default (matching GitHub-issue runs), so the
self-review 422 is impossible by construction rather than guarded in the prompt.
A profile flag author_prs_as_user restores per-user attribution.

- open_pull_request._resolve_pr_author_token + auth.resolve_github_token: default
  to the installation token for these sources; per-user only when opted in.
- authorship: commit identity -> seahaven-openswe[bot] (numeric noreply;
  accepted Vercel-resolution risk, documented inline).
- self-trigger safety: INTERNAL_BOT_LOGINS + webapp/reviewer_reconcile/reply
  markers recognize seahaven-openswe[bot] (bot-authored events are now ours).

Supersedes the prompt-only guard in #58.

* fix: author commits as the app bot in the default path (SH-IDSPLIT-01)

Security review found the commit identity was NOT actually unified to the bot:
resolve_triggering_user_identity got a 403 from the installation token and fell
back to configurable['github_login'], so commits were still authored as the
triggering user (commit=user, push+PR=bot — a three-way split that missed the
stated goal). Now gate the triggering-user identity resolution on the same
default-bot decision as the token: slack/dashboard/schedule default to the app
bot identity unless author_prs_as_user is set.

* docs(security): record AUTHZ-SLACK-BOT-DEFAULT-001 as an accepted residual (#59)

Single-user deployment; bounded by App-on-pilot + ALLOWED_GITHUB_REPOS lock.
Revisit (add a per-user gate) before expanding users or the App installation.
2026-06-29 14:22:33 -04:00

34 lines
1.5 KiB
Python

from __future__ import annotations
from agent.dashboard.agent_overrides import profile_author_prs_as_user
from agent.utils.authorship import OPEN_SWE_BOT_EMAIL, OPEN_SWE_BOT_NAME
from agent.utils.github_org_membership import INTERNAL_BOT_LOGINS
def test_author_prs_as_user_defaults_off() -> None:
# Default is the app bot; the per-user opt-in must be explicit.
assert profile_author_prs_as_user(None) is False
assert profile_author_prs_as_user({}) is False
assert profile_author_prs_as_user({"author_prs_as_user": "true"}) is False
assert profile_author_prs_as_user({"author_prs_as_user": True}) is True
def test_commit_identity_is_the_app_bot() -> None:
assert OPEN_SWE_BOT_NAME == "seahaven-openswe[bot]"
assert OPEN_SWE_BOT_EMAIL == "296972425+seahaven-openswe[bot]@users.noreply.github.com"
def test_self_trigger_guard_recognizes_our_app_bot() -> None:
# Bot-authored PRs/actions must be recognized as our own to avoid self-trigger loops.
assert "seahaven-openswe[bot]" in INTERNAL_BOT_LOGINS
def test_default_commit_identity_in_prompt_is_the_app_bot() -> None:
# SH-IDSPLIT-01: with no triggering-user identity (the default-bot path), the
# constructed prompt must set the git commit identity to the app bot — so
# commits, push, and PR all come in as the app (not the triggering user).
from agent.prompt import construct_system_prompt
prompt = construct_system_prompt(working_dir="/workspace", triggering_user_identity=None)
assert OPEN_SWE_BOT_NAME in prompt
assert OPEN_SWE_BOT_EMAIL in prompt