Token导航 LogoToken导航

Agent Skill · 开发

but(但是)

but 用于处理 GitHub 仓库、Issue、Pull Request 和代码协作信息,适合在 Codex、Claude、Cursor、Gemini CLI 中需要围绕仓库状态、代码变更或协作事项进行整理时使用。可结合来源仓库、安装命令和原始 README 继续核验具体用法。安装前建议确认权限范围、维护状态,以及是否会触发联网、命令执行或文件读写。

but 是开发类 Agent Skill,可用宿主为 Codex、Claude、Cursor、Gemini CLI,通过GitHub 仓库获取,权限为需要联网;许可证信息还不明确,第三方扫描有未通过项,按安装量在开发类的 21,746 个 Skill 里排第 12,141。

总安装 1,420周安装 61GitHub Stars 2下载 498核验 2026-05-01

安装说明

本站只整理中文说明,不托管安装包,也不代用户安装。
GitHub
许可证
unknown

安装方式

通过对话安装

复制提示词发给支持本地命令或 Skills 的 AI 助手,先确认命令和权限,再让它执行。

请帮我安装这个 Agent Skill:but(但是)
来源仓库:https://github.com/gaboe/opencode-gitbutler
仓库路径:skills/but
安装命令:
npx skills add https://github.com/gaboe/opencode-gitbutler --skill but
安装前请先检查当前环境是否支持对应 CLI,并向我确认将要执行的命令、安装目录、联网范围和文件读写权限;确认后再执行。

命令行安装

复制命令到本机终端执行。该命令会通过 npx skills 从第三方来源获取 Skill;本站只展示命令,不托管安装包,也不自动执行。

skills.shnpx skills
npx skills add https://github.com/gaboe/opencode-gitbutler --skill but

这个 Skill 是做什么的

开发类 Skill 面向写代码、改代码和排查问题,一般会读写仓库文件,部分还会执行构建或测试命令。

but 用于处理 GitHub 仓库、Issue、Pull Request 和代码协作信息。适合在 Codex、Claude、Cursor、Gemini CLI 中围绕仓库状态、代码变更或协作事项进行整理。通过 npx skills add 命令从指定仓库安装,需结合原始 README 核验具体用法。

安装前建议确认权限范围、维护状态,以及是否会触发联网、命令执行或文件读写。注意该技能属于开发类,实际功能以来源仓库文档为准。

来源仓库内路径:skills/but

上手步骤

4 步
  1. 1

    确认自己的宿主工具

    公开资料标注支持 Codex、Claude、Cursor、Gemini CLI;先确认自己用的是其中之一,再按对应工具的 Skills 目录放置。

  2. 2

    拿到安装命令

    可以直接复制的命令是 npx skills add https://github.com/gaboe/opencode-gitbutler --skill but;命令里的占位符换成自己的路径或密钥再执行。

  3. 3

    安装后重启宿主

    命令执行完要完全退出宿主工具再打开,让新装的 Skill 被重新扫描到,否则列表里可能看不到。

  4. 4

    按最小权限试用

    它需要需要联网,先在测试目录或测试账号里跑,确认没问题再放到正式项目。

常见问题

6 条

but 怎么安装?

在终端执行 npx skills add https://github.com/gaboe/opencode-gitbutler --skill but。装完完全退出宿主工具再打开,让它重新扫描本地 Skill。

but 支持哪些 AI 工具?

公开资料标注支持 Codex、Claude、Cursor、Gemini CLI。其他工具只要能读取本地 Skill 目录,一般也能手动放进去,但要自己确认触发方式是否一致。

but 需要什么权限?

权限级别是需要联网。该 Skill 可能需要联网访问来源站点、仓库或外部 API;具体网络访问范围需要结合源码和 README 复核。

but 是免费的吗?

公开资料没有标注明确许可证,收费和商用限制都无法确认。正式使用前请到来源仓库核对授权说明。

but 用的人多吗?

公开数据是累计安装 1,420 次,近一周安装 61 次,下载 498 次,GitHub 2 星。这些数字来自第三方目录统计,只能当作热度参考,不代表质量或安全性。

but 安全吗?

第三方扫描有未通过项,风险较高。除非你确认过源码,否则不建议直接安装到常用环境。

值得选的地方和要先想清楚的地方

值得选的地方

  • 同时适配 4 种工具,换客户端不用重新找替代品。

先想清楚的地方

  • 许可证没有明确标注,能不能商用、能不能再分发都不确定。
  • 第三方扫描存在提醒项或未通过项,需要人工逐条确认。
  • 第三方目录整理,版本更新和行为细节以来源仓库为准。

适不适合你

更适合

  • 已经在用 Codex,想直接扩展它能力的人。
  • 需要处理开发类任务、又不想每次都手写提示词的人。

不太适合

  • 需要明确授权才能用到公司项目里的场景。
  • 需要厂商级技术支持和 SLA 的生产系统。

开发类 Skill 对比

6 个同类
Skill总安装GitHub 星权限许可证扫描
skill-vetter

技能审查员 · OpenClaw

8,779,018986操作浏览器MIT-0通过
ontology

本体论 · OpenClaw

6,636,960576只读MIT-0通过
entra-app-registration

内部应用程序注册 · Codex、Claude

6,631,872764接触敏感数据未明确通过
entra-app-registration

内部应用程序注册 · Codex、Claude

3,757,680201接触敏感数据未明确通过
nano-banana-pro

纳米香蕉专业版 · OpenClaw

3,526,898364接触敏感数据MIT-0有提醒
but

但是 · 本页

1,4202需要联网未明确未通过

按安装量取同分类前几名;数字来自第三方目录统计,只作热度参考,不代表质量结论。

SKILL.md 原文

GitButler CLI Skill

Help users work with GitButler CLI (but command) in workspace mode.

New Session Workflow

EVERY new agent session that involves code changes MUST follow this flow:

  1. Sync first → but pull to get latest upstream changes (prevents conflicts and stale base)
  2. Check state → but status to see existing branches and unstaged changes
  3. Decide branch →

- If an existing branch matches the task → reuse it (it's already applied) - If this is new work → but branch new <task-name> (e.g. feat/add-auth, fix/login-bug) - If you need to resume unapplied work → but apply <branch>

  1. Make changes → Edit files as needed
  2. Stage & commit → but commit <branch> -m "message" --changes <id>,<id>
  3. Refine → Use but absorb or but squash to clean up history
  4. Push when ready → but push <branch>
  5. Create PR → but pr new <branch> -t (uses default target branch)

Branch naming: Use conventional prefixes: feat/, fix/, chore/, refactor/

Commit early, commit often. Don't hesitate to create commits - GitButler makes editing history trivial. You can always squash, reword, or absorb changes into existing commits later. Small atomic commits are better than large uncommitted changes.

After Using Write/Edit Tools

When ready to commit:

  1. Run but status --json to see uncommitted changes and get their CLI IDs
  2. Commit the relevant files directly: but commit <branch> -m "message" --changes <id>,<id>

You can batch multiple file edits before committing - no need to commit after every single change.

Critical Concept: Workspace Model

GitButler ≠ Traditional Git

  • Traditional Git: One branch at a time, switch with git checkout
  • GitButler: Multiple stacks simultaneously in one workspace, changes assigned to stacks

This means:

  • ❌ Don't use git status, git commit, git checkout
  • ✅ Use but status, but commit, but commands
  • ✅ Read-only git commands are fine (git log, git diff)

Hard Safety Rules (Non-Negotiable)

  1. Never discard changes you did not create.

- zz (unassigned) often contains work from other sessions/agents/users. - If unrelated changes exist, leave them untouched and ask before any discard action.

  1. Never leave your own changes in zz at the end of work.

- After edits, run but status --json and move your file/hunk IDs to the correct branch via but stage or but commit --changes.

  1. Validate branch ownership before commit.

- Confirm each changed file/hunk belongs to the intended branch/task, then commit only those IDs.

  1. Respect branch ownership across sessions.

- In multi-agent environments, branches may belong to other agent sessions. Never reword, rename, or push branches you didn't create in this session. - If you need to modify another session's branch, ask the user first.

Quick Start

Installation:

curl -sSL https://gitbutler.com/install.sh | sh
but setup                          # Initialize in your repo
but skill install --path <path>    # Install/update skill (agents use --path with known location)

Note for AI agents:

  • When installing or updating this skill programmatically, always use --path to specify the exact installation directory. The --detect flag requires user interaction if multiple installations exist.
  • Use --json flag for all commands to get structured, parseable output. This is especially important for but status --json to reliably parse workspace state.

Core workflow:

but status --json       # Always start here - shows workspace state (JSON for agents)
but branch new feature  # Create new stack for work
# Make changes...
but commit <branch> -m "…" --changes <id>,<id>  # Commit specific files by CLI ID
but push <branch>       # Push to remote

Essential Commands

For detailed command syntax and all available options, see references/reference.md. For a hands-on learning guide, see references/tutorial.md. For a one-page quick lookup, see references/cheatsheet.md.

IMPORTANT for AI agents: Add --json flag to all commands for structured, parseable output.

Understanding state:

  • but status --json - Overview (START HERE, always use --json for agents)
  • but status --json -f - Overview with full file lists (use when you need to see all changed files)
  • but show <id> --json - Details about commit/branch
  • but diff <id> - Show diff

Flags explanation:

  • --json - Output structured JSON instead of human-readable text (always use for agents)
  • -f - Include detailed file lists in status output (combines with --json: but status --json -f)

Organizing work:

  • but branch new <name> - Independent branch
  • but branch new <name> -a <anchor> - Stacked branch (dependent)
  • but stage <file> <branch> - Pre-assign file to branch (optional, for organizing before commit)

Making changes:

  • but commit <branch> -m "msg" --changes <id>,<id> - Commit specific files or hunks (recommended)
  • but commit <branch> -m "msg" -p <id>,<id> - Same as above, using short flag
  • but commit <branch> -m "msg" - Commit ALL uncommitted changes to branch
  • but commit <branch> --only -m "msg" - Commit only pre-staged changes (cannot combine with --changes)
  • but amend <file-id> <commit-id> - Amend file into specific commit (explicit control)
  • but absorb <file-id> - Absorb file into auto-detected commit (smart matching)
  • but absorb <branch-id> - Absorb all changes staged to a branch
  • but absorb - Absorb ALL uncommitted changes (use with caution)

Getting IDs for --changes:

  • File IDs: but status --json - commit entire files
  • Hunk IDs: but diff --json - commit individual hunks (for fine-grained control when a file has multiple changes)

Editing history:

  • but rub <source> <dest> - Universal edit (stage/amend/squash/move)
  • but squash <commits> - Combine commits
  • but reword <id> - Change commit message/branch name

Remote operations:

  • but pull - Update with upstream
  • but push [branch] - Push to remote
  • but pr new <branch> - Push and create pull request (auto-pushes, no need to push first)
  • but pr new <branch> -m "Title..." - Inline PR message (first line is title, rest is description)
  • but pr new <branch> -F pr_message.txt - PR message from file (first line is title, rest is description)
  • For stacked branches, the custom message (-m or -F) only applies to the selected branch; dependent branches use defaults

Key Concepts

For deeper understanding of the workspace model, dependency tracking, and philosophy, see references/concepts.md.

CLI IDs: Every object gets a short ID (e.g., c5 for commit, bu for branch). Use these as arguments.

Parallel vs Stacked branches:

  • Parallel: Independent work that doesn't depend on each other
  • Stacked: Dependent work where one feature builds on another

The but rub primitive: Core operation that does different things based on what you combine:

  • File + Branch → Stage
  • File + Commit → Amend
  • Commit + Commit → Squash
  • Commit + Branch → Move

Workflow Examples

For complete step-by-step workflows and real-world scenarios, see references/examples.md.

Starting independent work:

but status --json
but branch new api-endpoint
but branch new ui-update
# Make changes, then commit specific files to appropriate branches
but status --json  # Get file CLI IDs
but commit api-endpoint -m "Add endpoint" --changes <api-file-id>
but commit ui-update -m "Update UI" --changes <ui-file-id>

Committing specific hunks (fine-grained control):

but diff --json             # See hunk IDs when a file has multiple changes
but commit <branch> -m "Fix first issue" --changes <hunk-id-1>
but commit <branch> -m "Fix second issue" --changes <hunk-id-2>

Cleaning up commits:

but absorb              # Auto-amend changes
but status --json       # Verify absorb result
but squash <branch>     # Squash all commits in branch

Resolving conflicts:

but resolve <commit>    # Enter resolution mode
# Fix conflicts in editor
but resolve finish      # Complete resolution

Managing workspace:

but config target origin/test   # Set default PR target (requires unapply all branches first)
but unapply <branch>            # Remove branch from workspace (keeps commits)
but apply <branch>              # Bring branch back into workspace
but teardown                    # Exit GitButler mode → normal git
but setup                       # Re-enter GitButler mode
but discard <ids>               # Discard unstaged changes

Post-Merge PR Flow

After a PR is squash-merged on GitHub, follow this exact sequence:

but unapply <merged-branch>    # MUST do BEFORE pull - prevents orphan branch errors
but pull                        # Pull merged changes from remote

Critical: If you but pull before unapplying the merged branch, GitButler will error with orphan branch conflicts. Always unapply first.

If but unapply fails (branch already gone from workspace after remote deletion with --delete-branch), but pull may also fail with "resolution mismatch" errors because the ghost stack still exists internally. In this case, the GitButler desktop app can handle it — tell the user to run but pull from the GUI. Alternatively, use but teardown → but setup → but config target origin/<branch> to reset.

After but teardown → but setup: Target config resets. Run but config target origin/<branch> again.

Using --no-hooks Safely

When pre-commit hooks fail on pre-existing errors unrelated to your changes, use --no-hooks. But this skips the formatter too:

bun run format                                    # Format FIRST
but commit <branch> -m "msg" --changes <ids> --no-hooks  # Then commit without hooks

Alternatively, commit normally and absorb formatter fixes:

but commit <branch> -m "msg" --changes <ids>      # Commit (hooks may fix formatting)
but absorb                                         # Absorb any auto-formatted changes

Known Issues & Workarounds

IssueWhat happensWorkaround
but resolve loses target configAfter entering resolve mode, but config target resets to "not set"Run but config target origin/<branch> again after but resolve finish. If finish fails, do git checkout gitbutler/workspace → but teardown → but setup
but absorb hunk lockAbsorb assigns hunk to wrong commit when it's locked by another commit on a different branchUse but amend <file> <commit> for explicit control instead of absorb
but pr new has no --base flagAlways creates PR against default targetSet target first: but config target origin/<branch>
but config target requires unapplyCannot change target with applied branchesbut unapply all → change target → but apply
but config forge auth is interactiveCannot run in non-interactive agent modeUser must run in terminal + grant org access on GitHub
but commit pre-commit hook failsHook fails on pre-existing errors unrelated to your changesbut commit --no-hooks if errors are not from your changes. Always bun run format first since --no-hooks skips the formatter
but branch delete last segmentCannot delete if it would leave anonymous segmentUse but unapply instead of delete
but stage prefix matchingBranch name can be abbreviatedbut stage <id> ch works for chore/gitbutler-setup
but discard hunk range errorDiscarding file-level changes sometimes fails with hunk range errorsUse git checkout -- <file> instead of but discard for file-level discards
but teardown + but setup resets targetAfter teardown/setup cycle, target config is lostRun but config target origin/<branch> again after setup
Lefthook pre-commit.old accumulatesLefthook creates pre-commit.old backup that conflicts on next installAdd rm -f.git/hooks/pre-commit.old to prepare script in package.json
but pull before unapplyPulling with merged branches still applied causes orphan errorsAlways but unapply <merged-branch> before but pull
but unapply after remote branch deletionbut unapply fails with "branch not found" when remote deleted the branch (e.g. --delete-branch on merge), and subsequent but pull fails with "resolution mismatch"Use GitButler desktop app to pull, or but teardown → but setup → but config target origin/<branch>
Split-hunk files stuck in zzFile has hunks locked to commits on different branches — GitButler sets stack_id=None, plugin considers file "handled" via lock referenceManually commit each hunk: but diff --json to get hunk IDs, then but commit <branch> -m "msg" --changes <hunk-id> for each
Plugin auto-cleanup misses empty branchesge-branch-* cleanup has ~12% failure rate; user-named empty branches are never auto-cleanedRun /b-branch-gc command or manually but unapply <branch-id>
Notifications not reaching agentPlugin notification delivery is ~55% (259 queued vs 142 delivered in observed sessions)Always verify state with but status --json — don't rely on <system-reminder> notifications alone

| Workspace projection mismatch | but status shows a branch/stack, but but unapply <branch> or GUI stack_details says the stack is not found in the workspace | Treat as GitButler metadata corruption, not a git-history problem. Stop mutating in place, capture logs/project/commit graph for support, then use but teardown → back up .git/gitbutler → but setup. If it persists, use a fresh clone/worktree. | | Many (no changes) commits after repeated resolve/rebase | A stack accumulates synthetic commits that are patch-equivalent to upstream or replayed duplicates | Do not keep resolving in place. Freeze refs, identify patch-equivalent commits with git cherry -v and rebuild clean branches from the logical base instead of preserving the broken history. | | Applying one stack auto-unapplies another | GitButler says it had to unapply another stack to apply the requested one | The stacks overlap in content or ancestry. Unapply the currently active conflicting stack first, or rebuild the intended stack boundaries so only one logical chain remains applied at a time. | | but push blocked by projection errors | Workspace/stack metadata is broken but the raw git refs are healthy | If the goal is to repair remote ancestry, verify branch refs with raw git and use git push --force-with-lease as a last resort. Afterwards return to gitbutler/workspace and reinitialize metadata with but setup. |

Diagnosing zz Stuck Files

When files are stuck in zz (unassigned) and don't auto-recover:

  1. Identify the cause: but status --json -f # Look for files in zz with [LOCKED] markers but diff --json # Get hunk-level IDs and see lock targets
  2. If hunks are locked to different branches (split-hunk scenario):

- Each hunk must be committed to its locked branch individually - but commit <branch> -m "msg" --changes <hunk-id> for each hunk - Or but rub <hunk-id> <commit-id> to amend into the locked commit

  1. If files have no locks but are still in zz:

- Plugin's after-edit may have failed silently — stage manually - but stage <file-id> <branch> or commit with --changes

  1. If many files are stuck after but cursor stop:

- Run but rub <file-id> <branch-id> for each file to force assignment - This is the most reliable recovery method

Key insight: Auto-recovery won't fix multi-branch locked files. If you see [LOCKED] in zz, manual intervention is required.

Surgical Repair for Broken Stacks

When a stack is too damaged for normal but resolve to converge quickly — for example:

  • repeated conflicted commits keep reappearing,
  • git cherry -v shows lots of patch-equivalent duplicates,
  • GitButler shows many commits marked (no changes),
  • or a single commit drags .auto-resolution/** or other obvious snapshot junk,

use surgical repair instead of trying to preserve the broken history.

When surgical repair is the right move
  • The raw git graph is understandable, but GitButler metadata/history replay is not.
  • You can clearly identify the intended logical layers of the work, even if the current branch history no longer reflects them cleanly.
  • A mixed commit contains the real feature files plus obvious accidental junk.
Surgical repair workflow
  1. Freeze everything first

- Create backup refs for the current broken branches. - Stash any workspace dirt/hook refresh noise.

  1. Find the clean logical base

- Use git cherry -v <base> <branch> to separate patch-equivalent duplicates from truly unique commits. - Use git log --reverse <base>..<branch> to see the branch's commit layers in order.

  1. Rebuild from clean bases, not from broken branch history

- Create scratch branches from the intended base. - Cherry-pick only clean commits. - If a commit is contaminated (for example adds .auto-resolution/**), do file-level checkout of only the intended paths from that commit or from the existing branch tip, then create a new clean commit.

  1. Validate each rebuilt layer independently

- Compare file deltas between layers with git diff --name-only <base>..<layer>. - Run the project verification (bun run check, build/tests/analyzers, etc.) on the rebuilt stack before replacing refs.

  1. Replace refs only after the clean stack is proven

- Move the real branch refs to the rebuilt scratch refs. - Force-push with --force-with-lease only after ancestry and checks are confirmed.

Why this is fast in practice

Surgical repair sounds heavier than repeated conflict resolution, but once the stack crosses into duplicated replay / (no changes) / metadata-corruption territory, rebuilding the logical deltas is usually faster and safer than preserving every historical artifact.

Critical Safety Rules

  1. NEVER discard changes you didn't create. Unassigned changes in zz may belong to other agents, sessions, or the user. Always ask the user before running but discard or git checkout -- on any change you don't recognize. In GitButler workspace, multiple actors work in parallel — discarding "stale" or "already merged" changes is a destructive assumption.
  2. Always assign your changes to a branch immediately. Don't leave edits sitting in zz (unassigned). After editing files, stage them to your working branch with but stage <file-id> <branch> or commit directly with --changes.

Guidelines

  1. Always start with but status --json to understand current state (agents should always use --json)
  2. Create a new stack for each independent work theme
  3. Use --changes to commit specific files directly - no need to stage first
  4. Commit early and often - don't wait for perfection. Unlike traditional git, GitButler makes editing history trivial with absorb, squash, and reword. It's better to have small, atomic commits that you refine later than to accumulate large uncommitted changes.
  5. Use --json flag for ALL commands when running as an agent - this provides structured, parseable output instead of human-readable text
  6. Use --dry-run flags (push, absorb) when unsure
  7. Run but pull frequently — at session start, before creating branches, and before pushing. Stale workspace = merge conflicts
  8. When updating this skill, use but skill install --path <known-path> to avoid prompts
  9. Check for zz files with locks before finishing work. Run but status --json -f and look for files in zz with [LOCKED] markers. These won't auto-recover — you must manually commit each hunk to its correct branch using --changes <hunk-id>. See references/concepts.md — Hunk Locking for details.
  10. Don't trust notifications alone — plugin notification delivery is ~55%. Always verify workspace state with but status --json before making assumptions about branch assignments or commit status.

Plugin Auto-Behaviors (What Happens Behind the Scenes)

The GitButler plugin performs several actions automatically. You do NOT need to do these yourself — but you should know they happen so you don't duplicate work or get confused by unexpected state changes.

BehaviorTriggerWhat It Does
File auto-assignAfter each file editFinds which branch owns the file and runs but cursor after-edit or but rub to assign it
Auto-commitSession idle (agent stops editing)Runs but cursor stop which commits all uncommitted changes to their assigned branches
LLM commit rewordAfter auto-commitRewrites generic commit messages using Claude Haiku based on the actual diff
Branch renameAfter auto-commitRenames ge-branch-* branches to descriptive names based on user's prompt
Empty branch cleanupAfter auto-commitRemoves ge-branch-* branches with 0 commits (~88% success rate)
Session title syncAfter auto-commitUpdates session title from branch name
Context injectionBefore each agent messageInjects <system-reminder> with workspace notifications (branch created, commits made, etc.)

What This Means for You

  1. **Don't manually rename ge-branch-* branches** — the plugin will do it after idle
  2. Don't reword auto-generated commit messages — the plugin rewrites them with LLM
  3. If you see unexpected commits — check if the plugin auto-committed during an idle event
  4. Notification delivery is ~55% — not all injected notifications reach you. Always verify state with but status --json rather than relying on notifications
  5. Empty branch cleanup can fail — if you see stale ge-branch-* branches, run /b-branch-gc

平台分布

Codex

35.93%
按下载量换算179

Claude

28.3%
按下载量换算141

Cursor

18.47%
按下载量换算92

Gemini CLI

9.46%
按下载量换算47

安全审计

Gen Agent Trust Hub

未通过

Socket

通过

Snyk

未通过

权限和风险

需要联网

该 Skill 可能需要联网访问来源站点、仓库或外部 API;具体网络访问范围需要结合源码和 README 复核。

安装前确认

本站仅展示第三方公开信息,不托管安装包,不提供自动安装或运行环境。安装前应自行审查源码、依赖和命令行为。来源安全扫描存在提醒或未通过项,安装前请自行复核。目前只有一个公开来源,建议同时核对源仓库。

继续浏览同类 Skills