Skip to content

Add branding assets and PR lifecycle agent prompt#2

Merged
cmeans merged 2 commits into
mainfrom
chore/add-branding-and-prompts
Apr 13, 2026
Merged

Add branding assets and PR lifecycle agent prompt#2
cmeans merged 2 commits into
mainfrom
chore/add-branding-and-prompts

Conversation

@cmeans

@cmeans cmeans commented Apr 13, 2026

Copy link
Copy Markdown
Owner

Summary

  • Add Dev role branding logos in three sizes (40px, 128px, 256px) under branding/
  • Add prompts/pr-lifecycle-agent.md -- a dispatch template for managing the full PR lifecycle (CI polling, Codecov detail checks, label transitions, sequential queue rebasing)

Test plan

  • Verify logo images render correctly on GitHub
  • Review PR lifecycle agent template for accuracy

🤖 Generated with Claude Code

Add Dev role branding logos (40px, 128px, 256px) and the PR lifecycle
agent template used to manage CI transitions, Codecov checks, label
automation, and sequential PR queue rebasing.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

@cmeans cmeans left a comment

Copy link
Copy Markdown
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

QA Review — PR #2 (cmeans/claude-dev)

Informal review — this repo doesn't have the QA workflow, so no labels.

Branding (3 logos)

All three PNGs render correctly on GitHub. Code brackets on a shield, dark background with cyan accent. Clean design.

  • 256px — crisp, all details sharp ✓
  • 128px — clean at display size ✓
  • 40px — legible, brackets still recognizable at favicon/badge size ✓

PR Lifecycle Agent Prompt

Well-structured 4-phase template. A few observations:

Strengths:

  • Phase 1 CI polling correctly excludes QA Gate from the "pending" check — smart, since QA Gate stays pending until QA Approved
  • "Do NOT use gh pr checks --watch" — good warning, that would block forever
  • Phase 2 Codecov comment check (not just status) — catches the common trap of "codecov passed but patch coverage has gaps"
  • Phase 4 rebase uses --force-with-lease — safe force push ✓
  • "Important" rules are exactly right: never merge, never fix failures, never skip codecov detail, report-and-stop on unexpected

Observations (not blockers — this is a personal tools repo):

  1. Phase 4 assumes a local clone exists. git checkout {{NEXT_BRANCH}} won't work if the agent was dispatched in a clean environment. Could add a git fetch origin {{NEXT_BRANCH}} before checkout, or note "assumes worktree context" in the docs.

  2. {{#if NEXT_PR}} / {{/if}} Handlebars syntax won't be evaluated — the user manually pastes the template. Consider a note like "Remove Phase 4 if no NEXT_PR" or split into two templates (single PR vs queued).

  3. notify-send + paplay are Linux-specific. Fine for your setup, but if you ever share this prompt, a note about platform would help.

  4. Phase 1 step 2 edge case: If checks haven't started yet (e.g., GitHub is slow), the grep returns empty — same as "all passed." Could add a "checks found" guard: if gh pr checks returns no lines at all, wait before declaring success.

None of these are blockers — the template is practical and well-thought-out. It automates exactly the tedious parts of the PR lifecycle while keeping the human/QA in the loop for decisions.

Verdict

Looks good. Ship it.

- Add checks-exist guard before declaring CI passed (prevents false
  positive when checks haven't started yet)
- Remove Handlebars {{#if}} syntax; note to remove Phase 4 manually
  when no NEXT_PR is provided
- Add git fetch for NEXT_BRANCH and note that Phase 4 assumes a local
  clone with the branch available
- Add platform notes section for notify-send/paplay alternatives

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@cmeans cmeans merged commit 4190b7b into main Apr 13, 2026
@cmeans cmeans deleted the chore/add-branding-and-prompts branch April 13, 2026 00:18
cmeans-claude-dev Bot added a commit that referenced this pull request Apr 25, 2026
## Summary

Replaces the v1 bot-push design (env-var GIT_CONFIG_* matrix + \`git\`
shell-function wrapper + manual \`bot-git-push.sh\` invocation) with a
curated bot git config loaded via \`GIT_CONFIG_GLOBAL\`. After this
lands, plain \`git push\` from any subprocess in an activated bot
session attributes the PushEvent to \`cmeans-claude-dev[bot]\` — no
wrapper to remember.

Surfaced by mcp-awareness PR #396 on 2026-04-24, where the v1 design's
env-var fight against \`~/.gitconfig\` lost in a Bash subprocess and the
push attributed to \`cmeans\`, blocking merge under
\`require_last_push_approval\`.

## Why GIT_CONFIG_GLOBAL swap

Three options were considered (full analysis in awareness
\`bot-push-attribution-options-2026-04-24\`):

1. **Per-clone HTTPS \`origin\` URL.** Doesn't actually work in this
repo's setup — Chris's global \`~/.gitconfig\` has
\`url.git@github.com:.insteadOf=https://github.com/\` which rewrites
every HTTPS URL back to SSH for *every* git invocation, regardless of
who's running it. Per-clone change can't override a global insteadOf.
2. **Debug v1's env-var \`pushInsteadOf\`.** Empirically loses to global
insteadOf in subprocesses despite documented precedence. Unknown
debugging depth.
3. **\`git\` binary shim in \`~/.local/bin\`.** Universal but invasive —
intercepts every git command, surprising failure modes, hard to reason
about.

The chosen mechanism is more durable than any of those: don't fight the
global config — replace it for the duration of the bot session via
\`GIT_CONFIG_GLOBAL\`. Subprocess-safe (env vars inherit). Per-role
isolated (a non-activated shell doesn't see it, so QA / human sessions
in the same clone push as the human normally).

## What's in the new bot config

Built from scratch (not filtered from \`~/.gitconfig\`) so the diff
against intent is readable and immune to drift:

- \`[user]\` — \`BOT_USER_ID\`-prefixed bot email
(\`272174644+cmeans-claude-dev[bot]@users.noreply.github.com\`)
- \`[commit/tag/push] gpgSign = false\` — insulates against future
user-side gpgSign defaults
- \`[init] defaultBranch = main\`
- \`[url \"https://github.com/\"] pushInsteadOf = git@github.com:\` —
forces SSH→HTTPS for push regardless of \`origin\` URL
- \`[credential \"https://github.com\"]\` — list reset (no \`store\`
inheritance) + \`git-credential-bot-token.sh\`

## Why a template + render rather than a static file

Git's \`credential.helper\` does NOT expand \`~\` in path values — the
helper script must be referenced by absolute path. To stay portable
across clone locations without hardcoding \`/home/cmeans/...\`,
\`activate.sh\` substitutes \`__SCRIPT_DIR__\` at activation time and
writes the rendered config to \`github-app/.git-global.config\`
(gitignored). Source of truth is the \`.template\` file.

## Inventory of \`~/.gitconfig\` (decisions reviewable)

Ran before drafting to confirm what gets left behind by going
from-scratch:

\`\`\`
file:/home/cmeans/.gitconfig  user.name=Chris Means
file:/home/cmeans/.gitconfig  user.email=chris.a.means@gmail.com
file:/home/cmeans/.gitconfig  credential.helper=store
file:/home/cmeans/.gitconfig  init.defaultbranch=main
file:/home/cmeans/.gitconfig
url.git@github.com:.insteadof=https://github.com/
\`\`\`

No \`~/.config/git/config\`. No \`/etc/gitconfig\`. No \`[include]\` /
\`[includeIf]\`. No signing config. No \`core.sshCommand\` /
\`core.hooksPath\` / \`init.templatedir\`. No other URL rewrites.

What's left behind by going from-scratch (deliberate):
- \`user.name=Chris Means\` / \`user.email=chris.a.means@gmail.com\` —
replaced with bot identity (the whole point).
- \`credential.helper=store\` — replaced with bot helper. Inheriting it
would silently auth as Chris via \`~/.git-credentials\` (CD's #2).
- \`url.git@github.com:.insteadof=https://github.com/\` — deliberately
omitted (the rule we're fighting).
- \`init.defaultBranch=main\` — kept (re-set in the bot config
explicitly).

## Belt-and-suspenders fallback

\`bot-git-push.sh\` is kept in this PR as a fallback for v1. The new
\`activate.sh\` does NOT define a \`git push\` wrapper, so the script is
only used if invoked manually (\`bash bot-git-push.sh push origin
<branch>\`). After this design carries real PR traffic for a few cycles
and we're confident, a follow-up cleanup PR removes it.

The corresponding awareness entry (\`bot-push-via-helper\`) and feedback
memory will be tightened to: **\"Use ONLY if a push is attributing to
\`cmeans\` from an activated session — that indicates a bug in
activate.sh, file an issue, then use this script as a one-shot to
unblock. Do not use this script as a default workflow.\"** That signal
is what keeps the new design from eroding through soft fallback.

## Hygiene cleanup

This PR also brings two scripts into source control that have been
driving real bot pushes from the working tree since 2026-04-22 but were
never PR'd to this repo:

- \`bot-git-push.sh\` (now belt-and-suspenders fallback)
- \`git-credential-bot-token.sh\` (referenced from the new bot config)

Closes the \"main is ~2 weeks stale relative to disk\" gap.

## Verification

Three checks ran during development; all pass:

**(a) Format test — \`[bot]\` brackets render correctly.** This commit's
identity:
\`\`\`
author: cmeans-claude-dev[bot]
<272174644+cmeans-claude-dev[bot]@users.noreply.github.com>
committer: cmeans-claude-dev[bot]
<272174644+cmeans-claude-dev[bot]@users.noreply.github.com>
\`\`\`
GitHub UI rendering visible on the commit page after merge.

**(b) Sequential test — push attribution differs per role.**
- Activated session: this branch's \`CreateEvent\` reports
\`actor.login: cmeans-claude-dev[bot]\` (verified via \`gh api
repos/cmeans/claude-dev/events\` immediately after push).
- Non-activated session in the same clone: \`git config user.email\`
returns \`chris.a.means@gmail.com\`, \`git config --get
url.git@github.com:.insteadOf\` returns Chris's rule. Same
\`.git/config\`, two identities.

**(c) Concurrent test — proven by construction.** \`GIT_CONFIG_GLOBAL\`
is an environment variable; environment is per-process. Two terminals on
the same machine, one activated and one not, cannot interfere with each
other. Manual verification (two-terminal simultaneous push) recommended
once before relying on this for production traffic; happy to run it
post-merge.

## Test plan

- [ ] Merge, then start a fresh Dev session and confirm \`source
github-app/activate.sh\` reports the rendered config path
- [ ] Confirm \`git config --list --show-origin\` in an activated
session shows the rendered \`.git-global.config\` only (no
\`~/.gitconfig\` entries, no \`command line:\` matrix entries)
- [ ] Confirm a real bot push to a test branch in this repo (or the next
mcp-awareness feature PR) shows up over HTTPS in the \`git push\` output
and \`actor.login: cmeans-claude-dev[bot]\` in events
- [ ] Confirm a non-activated terminal in the same clone still pushes as
\`cmeans\` over SSH (one-time sanity check; per-process env isolation
should make this trivially correct)
- [ ] One concurrent-session test: two terminals (one activated, one
not), simultaneous pushes to different branches, confirm \`actor.login\`
differs correctly per push

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: cmeans-claude-dev[bot] <272174644+cmeans-claude-dev[bot]@users.noreply.github.com>
Co-authored-by: Chris Means <chris.a.means@gmail.com>
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.

1 participant