ast-grep について
ast-grep は、25 言語に対応する AST ベースの検索・書き換えツールを使うためのスキルです。構文構造に沿ってコードを検索・変換するコーディングエージェント向けで、パターン検証や変更プレビューを行う Python ヘルパーを備えています。
主な機能
- 01AST ベースの検索と書き換え
- 02Python ヘルパーによる検索と置換
- 03オフラインでのパターン検証
- 04適用前の変更プレビュー
- 05YAML ルールのスキャンと自動修正
- 06言語一覧とバイナリ診断
活用シーン
- 01呼び出し、関数、インポートの構造検索
- 02リポジトリ内ファイルへのコード移行
- 03YAML lint ルールによるコード検査
- 04検索前のパターン検証
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ code-yeongyu/ ast-grep-skill --skill ast-grepインストール後、Claude Code で/ast-grepを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
.gitignoreLICENSEinstall.ps1README.mdinstall.sh.github/workflows/ci.ymlreferences/patterns.mdinstall.mdcli.mdpitfalls.mdrecipes.mdsgconfig.mdyaml-rules.mdscripts/ast_grep_helper.pytests/smoke.shsmoke.ps1詳細
ast-grep
sg(ast-grep としてもインストールされます)は、25 言語に対応した AST 対応の検索・書き換えツールです。パターンをコードとして扱い、プロジェクトの解析と同じ方法で解析して、構造に基づいてマッチします。質問の答えがテキストのバイト列ではなく、コードの構造によって決まる場合に最適なツールです。
このスキルには、Python ラッパー scripts/ast_grep_helper.py と、プラットフォーム別のインストールスクリプト install.sh(POSIX)および install.ps1(Windows)が含まれています。ヘルパーは、オフラインでのパターン検証、2 パスで書き込む方法、バイナリの自動解決機能を追加します。デフォルトのエントリーポイントとして使用してください。
このスキルを使用する場面
ユーザーの質問がバイト列ではなく、コード構造に関するものであれば、いつでも使用してください。
- 「
Requestパラメーターを取る関数をすべて見つけてください。」 - 「すべての
console.log(x)をlogger.info(x)に書き換えてください。」 - 「すべての
as anyキャストを削除してください。」 - 「リポジトリ全体で
require(...)をimportに置き換えてください。」 - 「空の catch ブロックを見つけてください。」
- 「
Optional[X]をX | Noneに移行してください。」 - 「この codemod をこれら 200 個のファイルに適用してください。」
- 「YAML の lint ルールを実行して、違反を報告してください。」
質問がテキストに関するもの(文字列リテラルの内容、コメント、ライセンスヘッダー、ファイル名、言語をまたぐ正規表現など)の場合は、通常の grep/rg に切り替えてください。迷った場合は、「答えは言語の構文木に依存するのか、それともファイルのバイト列だけに依存するのか」と考えてください。前者なら ast-grep、後者なら grep を使います。
エージェントが理解しておくべき 3 つのこと
1. ast-grep は正規表現ではありません
ワイルドカードは $VAR(AST ノード 1 つ)と $$$(ノード 0 個以上)です。正規表現の構文を使っても、エラーにならずに動作しないことがあります。
| 入力したもの | ast-grep が認識したもの | 本来意図していたもの |
|---|---|---|
foo|bar | foo と bar のビット単位 OR | 検索を 2 回に分ける |
.*foo | 解析できない | $$$ がノードのリストの場合は $$$ foo、または rg を使う |
\w+ | 解析できない | 任意の識別子をキャプチャするには $VAR を使う |
[a-z] | 文字クラスだが、解析できない | rg に切り替える |
すべてのアンチパターンは references/pitfalls.md §1 に記載されています。ヘルパーの validate サブコマンドはこれらを機械的に検出します。「マッチしない」原因を手作業で調査する前に実行してください。
2. パターンは有効なコードでなければなりません
パターン自体を解析できる必要があります。末尾の : によってコードが不完全になるため、def $FN($$$): は失敗します。代わりに def $FN($$$) を使用してください。パラメーターや本体のない function $NAME は失敗します。代わりに function $NAME($$$) { $$$ } を使用してください。言語ごとの完全な一覧は references/pitfalls.md §2 にあります。
3. --update-all と --json は同時に指定できません(エラーは通知されません)
スクリプトを作成する際に最も注意が必要な点です。sg run -p P -r R --json --update-all は JSON を返しますが、ファイルは変更しません。プレビューと適用の両方を行うには、2 回に分けて実行してください。
sg run -p P -r R --json=compact . # pass 1: see what would change
sg run -p P -r R --update-all . # pass 2: actually apply
ヘルパーで replace --apply を呼び出すと、この処理が自動的に行われます。references/pitfalls.md §9 を参照してください。
ヘルパースクリプト — scripts/ast_grep_helper.py
Python 3 標準ライブラリのみを使った単一ファイルのラッパーです。すべての OS で同じように動作します。エージェントのデフォルトのエントリーポイントです。
search — パターンに一致するものをすべて検索
python3 scripts/ast_grep_helper.py search 'console.log($MSG)' --lang ts src/
最初にパターンをオフラインで検証します。パターンが正規表現のように見える(\w、.*、| など)場合、ヒントを表示してヘルパーを終了し、sg を呼び出しません。これにより、実行の往復を省けます。検証をスキップするには --force を渡してください。
フラグ:
--lang ts(または 25 言語のいずれか。js、py、rs、ktなどのエイリアスも使用できます)--globs '!**/*.test.ts'(複数回指定可能。除外するには先頭に!を付けます)-C 3(前後に表示する行数)--json-out(人が読みやすい形式ではなく、生の JSON を出力)
replace — パターンで書き換え(デフォルトではドライラン)
# Dry-run preview (default — no files mutated)
python3 scripts/ast_grep_helper.py replace 'console.log($MSG)' 'logger.info($MSG)' --lang ts src/
# Actually apply
python3 scripts/ast_grep_helper.py replace 'console.log($MSG)' 'logger.info($MSG)' --lang ts src/ --apply
ヘルパーは次の処理を行います。
patternとrewriteの両方を検証し、ヒントで検出できる間違いを確認します。--json=compactを使ってパス 1 を実行し、一致を収集してプレビューを表示します。--applyが設定されている場合は、--update-allを使ってパス 2 を実行し、ファイルを変更します。
scan — YAML ルールを実行
# Discover sgconfig.yml from cwd and run all rules
python3 scripts/ast_grep_helper.py scan src/
# Run a single rule file
python3 scripts/ast_grep_helper.py scan -r rules/no-console.yml src/
# Apply auto-fixes
python3 scripts/ast_grep_helper.py scan -U src/
# CI-friendly GitHub annotations
python3 scripts/ast_grep_helper.py scan --report-style short src/
validate — オフラインでのパターン検証(sg の呼び出しなし)
CI の lint、pre-commit フック、簡単な妥当性確認に便利です。
python3 scripts/ast_grep_helper.py validate '\w+' --lang ts
# → exit 2: regex \w not supported. Use $VAR for identifiers.
python3 scripts/ast_grep_helper.py validate 'console.log($MSG)' --lang ts
# → exit 0: pattern looks plausible for ast-grep.
langs/doctor/install
python3 scripts/ast_grep_helper.py langs # list 25 supported languages and aliases
python3 scripts/ast_grep_helper.py doctor # check ast-grep binary availability
python3 scripts/ast_grep_helper.py install # delegate to install.sh / install.ps1
new および test サブコマンドは、それぞれ sg new および sg test に直接処理を委譲します。
sg を直接使用する(ヘルパーでは不十分な場合)
ヘルパーには独自の方針があります。完全に制御したい場合は、sg を直接使用します。このスキルには、CLI のチートシートが references/cli.md に含まれています。最小限の使用例は次のとおりです。
# Search
sg run -p 'console.log($MSG)' --lang ts src/
# Search with JSON for scripting
sg run -p 'console.log($MSG)' --lang ts --json=compact src/ | jq '.[] | .file'
# Rewrite, dry-run
sg run -p 'console.log($MSG)' -r 'logger.info($MSG)' --lang ts --json=compact src/
# Rewrite, apply
sg run -p 'console.log($MSG)' -r 'logger.info($MSG)' --lang ts --update-all src/
# Pattern from stdin (great for ad-hoc experiments)
echo 'console.log("hi")' | sg run -p 'console.log($MSG)' --lang js --stdin
# Debug a pattern that returns 0 matches
sg run -p '<your pattern>' --lang <lang> --debug-query=ast --stdin <<< '<sample-code>'
# Run YAML rules
sg scan src/
# Inline YAML rule (one-off)
sg scan --inline-rules '
id: no-todo
language: TypeScript
severity: warning
rule: { pattern: TODO }' src/
シェルで sg を直接使用するときは、シェルによって $VAR が展開されないように、パターンは必ずシングルクォートで囲んでください。
判断基準 — いつ何を使うか
USER asks for "find/rewrite/codemod"
│
├─ structural pattern (function shape, call, class, import, control flow)
│ └→ ast-grep (this skill)
│
├─ text pattern (regex, alternation, character classes, file names)
│ └→ rg / grep
│
├─ semantic question (what variable does this refer to? does this throw?)
│ └→ LSP tools, TypeScript compiler, Pyright, Semgrep with type inference
│
└─ multiple repos / federated search
└→ a search engine + then ast-grep / rg / LSP per-repo
ユーザーが「すべて検索」や「すべて」と言った場合、対象が構造的なもの(関数、クラス、呼び出し、インポート、ステートメント)であれば、デフォルトでは ast-grep を使います。対象がテキスト(文字列の内容、コメント、ライセンスヘッダー、ファイル名、識別子の部分文字列)であれば、デフォルトでは rg を使います。
書き換えの前に必ずドライランを実行する
パターンが不適切だと、誤った箇所が気づかないうちに書き換えられてしまいます。このため、ヘルパーの replace はデフォルトでドライランを実行します。手順は次のとおりです。
- 検索して一致を確認します:
helper search '<pattern>' --lang X . - 書き換えをドライランします:
helper replace '<pattern>' '<rewrite>' --lang X .(--applyは指定しません) - ドライランの概要を確認します:一致数、影響を受けるファイル、各箇所のプレビュー。
- 誤っている場合:パターンを修正し、手順 1 に戻ります。
- 正しい場合:
helper replace '<pattern>' '<rewrite>' --lang X . --applyを実行します。
ドライランを実行していない書き換えを適用してはいけません。
コードがあると分かっているのに sg が一致を 0 件返す場合
優先順に確認します。
helper validate '<pattern>' --lang <lang>を実行します — 正規表現の誤用、関数本体の欠落、Python の末尾のコロンを検出します。--langを確認します —sgは拡張子から言語を推測します。.tsxファイルに--lang ts(tsxではなく)を指定すると、JSX は解析されません。- 解析されたパターンを確認します:
sg run -p '<pattern>' --lang <lang> --debug-query=ast --stdin <<< '<sample>'。ERRORノードが表示された場合、パターンの形式が正しくありません。 - 対象ファイルの AST を確認します:
sg run -p '$_' --lang <lang> --debug-query=cst path/to/file | head -40— 一致させようとしているkindを探します。 - プレイグラウンドを試します:https://ast-grep.github.io/playground.html — コードとパターンを貼り付けて、何が起きているか確認します。
変化を加えながら、やみくもに再試行しないでください。失敗にはそれぞれ理由があります。その理由を明らかにしてください。
YAML ルールとインライン -p パターンの使い分け
インライン -p を使う場合:
- 一度限りのアドホックなクエリ。
- パターンが単純(制約や修正テンプレートがない)。
- 探索的に使う場合。
YAML ルールを使う場合(rules/ 内のファイルを sg scan で実行):
- パターンを再利用する場合(CI で実行する lint ルールや codemod)。
constraints、transform、複雑なinside/has、または複合ロジックが必要な場合。- 自動修正(
fix:フィールド)を使いたい場合。 - ルールをテストしたい場合(
sg testによるスナップショットテスト)。
YAML ルールのスキーマ全体は references/yaml-rules.md にあります。プロジェクトの設定(sgconfig.yml、ruleDirs、utilDirs)については references/sgconfig.md を参照してください。
出力に関する注意事項
sg run --json=compactは、一致オブジェクトの配列を生成します:{ file, range: {start, end}, text, replacement?, lines, language, ... }。後続処理にはjqを通してください。--jsonを指定しない場合、sgはターミナル向けの色付きで読みやすい出力を生成します。- ヘルパーのデフォルト出力は、人間が読みやすい形式(file:line:column + 一致箇所のプレビュー)です。生の JSON を出力するには
--json-outを指定します。 - ヘルパーの
replaceは常に、一致数、ファイル数、各箇所のプレビューを要約します。
ユーザー向けに要約する際は、一致数だけでなく、影響を受けるファイル数を必ず含めてください。ユーザーが気にするのは、影響の範囲です。
必読ドキュメント(優先順位順)
references/patterns.md— メタ変数、命名規則、厳密度レベルについて説明しています。パターンが一致しない理由がわからないときに読んでください。references/pitfalls.md— 失敗モードのガイドです。一致件数が0件で驚いたときに読んでください。references/recipes.md— 言語別のコピー&ペースト用パターンです。新しいタスクを始めるときに最初に読んでください。references/cli.md—sg run、sg scan、sg test、sg new、sg lspについて説明しています。ヘルパーでは不十分なときに読んでください。references/yaml-rules.md— YAMLルールのスキーマです。インラインパターンでは足りなくなったときに読んでください。references/sgconfig.md— プロジェクトレベルの設定です。実際のプロジェクトでsg scanを設定するときに読んでください。references/install.md— OSごとのインストール方法です。install.sh/install.ps1が失敗した場合にのみ読んでください。
不変条件(必ず守ってください)
- 検索する前に検証してください。 プログラムでパターンを出力するときは、まず
helper validateを呼び出してください。これは、「一致件数が0件」のデバッグセッションの約70%を占める、正規表現の誤用による問題を検出します。 - 適用する前にドライランしてください。 一致箇所を確認せずに
sg run -r ... --update-allを実行してはいけません。ヘルパーのreplaceはデフォルトでこれを強制します。 - 書き込みは2回に分けてください。
sgを直接使ってプレビューと適用の両方を行う場合は、2回実行してください。--jsonでは--update-allは無視されます。 - シェルではパターンをシングルクォートで囲んでください。
"$VAR"ではなく'$VAR'を使ってください。ダブルクォート内ではシェルが$VARを空文字列に展開するため、パターンが壊れます。 - パターンはコードであり、正規表現ではありません。 パターンに
|、.*、\w、[a-z]が必要になる場合は、代わりにrgを使ってください。ast-grepを無理に正規表現の形式にしないでください。 - 標準入力には
--langが必要です。--stdinでパイプ入力するときは、--langを明示的に指定してください。sgは拡張子から言語を推測できません。 - Linuxでは、
sgはsetgroupsと衝突するため、ast-grepを優先してください。 ヘルパーがこの処理を行います。sgを直接呼び出す場合は、alias sg=ast-grepを設定してください。