code-structural-search

v2026.09.24

Use ast-grep for AST-based code pattern matching.

GitHub
Install command
npx skhub add oimiragieo/code-structural-search
Markdown
SKILL.md

Code Structural Search

Use ast-grep for AST-based code pattern matching.

When to Use

  • Find code by structure, not keywords
  • "Find all functions with 3 arguments"
  • "Find all classes that extend X"
  • "Find all database queries"
  • "Find all error handling patterns"
  • Precise code refactoring (change exact patterns)

Interface

Skill({ skill: 'code-structural-search', args: 'pattern-here --lang ts' });

Language Support

ast-grep supports 20+ languages via tree-sitter:

LanguageFlagFile Extensions
JavaScript--lang js.js, .jsx
TypeScript--lang ts.ts, .tsx
Python--lang py.py, .pyi
Go--lang go.go
Rust--lang rs.rs
Java--lang java.java
C--lang c.c, .h
C++--lang cpp.cpp, .cc, .hpp, .hh
C#--lang cs.cs
Kotlin--lang kt.kt, .kts
Swift--lang swift.swift
PHP--lang php.php
Ruby--lang rb.rb
Lua--lang lua.lua
Elixir--lang ex.ex, .exs
HTML--lang html.html, .htm
CSS--lang css.css
JSON--lang json.json
Bash--lang bash.sh, .bash
Thrift--lang thrift.thrift

Pattern Examples

JavaScript/TypeScript

Find all functions:

function $NAME($ARGS) { $$ }

Find functions with exactly 2 arguments:

function $NAME($A, $B) { $$ }

Find async functions:

async function $NAME($ARGS) { $$ }

Find class methods:

class $NAME {
  $METHOD($ARGS) { $$ }
}

Find arrow functions:

const $NAME = ($ARGS) => { $$ }

Find console.log statements:

console.log($$$)

Find try-catch blocks:

try { $$ } catch ($ERR) { $$ }

Python

Find all functions:

def $NAME($ARGS): $$$

Find class definitions:

class $NAME: $$$

Find async functions:

async def $NAME($ARGS): $$$

Find imports:

import $MODULE

Find from imports:

from $MODULE import $$$

Go

Find all functions:

func $NAME($ARGS) $RETURN { $$ }

Find struct definitions:

type $NAME struct { $$$ }

Find interface definitions:

type $NAME interface { $$$ }

Rust

Find all functions:

fn $NAME($ARGS) -> $RETURN { $$ }

Find impl blocks:

impl $NAME { $$$ }

Find pub functions:

pub fn $NAME($ARGS) -> $RETURN { $$ }

Java

Find all methods:

public $RETURN $NAME($ARGS) { $$ }

Find class definitions:

public class $NAME { $$$ }

Find interface definitions:

public interface $NAME { $$$ }

Pattern Syntax

SymbolMeaningExample
$NAMESingle node/identifierfunction $NAME() {}
$$$Zero or more statements/nodesclass $NAME { $$$ }
$$Zero or more statements (block)if ($COND) { $$ }
$_Anonymous wildcard (discard)console.log($_)

Performance

  • Speed: <50ms per search (typical)
  • Best combined with semantic search (Phase 1)
  • Use ripgrep first for initial file discovery

vs Other Tools

vs Ripgrep (grep):

  • Ripgrep: Fast text search, finds keywords
  • ast-grep: Structural search, finds exact code patterns
  • Use ripgrep first → then ast-grep to refine

vs Semantic Search (Phase 1):

  • Semantic: Understands code meaning
  • ast-grep: Understands code structure
  • Combined: Best results (Phase 2)

Usage Workflow

  1. Broad search with ripgrep:

    Skill({ skill: 'ripgrep', args: 'authenticate --type ts' })
    
  2. Structural refinement with ast-grep:

    Skill({ skill: 'code-structural-search', args: 'function authenticate($$$) { $$ } --lang ts' })
    
  3. Semantic understanding with Phase 1:

    Skill({ skill: 'code-semantic-search', args: 'authentication logic' })
    

Common Use Cases

Security Patterns

Find unvalidated inputs:

router.post($PATH, ($REQ, $RES) => { $$ })

Find SQL queries (potential injection):

db.query(`SELECT * FROM ${$VAR}`)

Find eval usage:

eval($$$)

Code Quality Patterns

Find deeply nested functions:

function $NAME($ARGS) {
  if ($COND) {
    if ($COND2) {
      if ($COND3) { $$ }
    }
  }
}

Find long parameter lists (>5 params):

function $NAME($A, $B, $C, $D, $E, $F, $$$) { $$ }

Find unused variables:

const $NAME = $VALUE;

Refactoring Patterns

Find old API usage:

oldAPI.deprecatedMethod($$$)

Find callback patterns (convert to async/await):

$FUNC($ARGS, ($ERR, $DATA) => { $$ })

Find React class components (convert to hooks):

class $NAME extends React.Component { $$$ }

Iron Laws

  1. ALWAYS specify the language with --lang flag — without a language flag, ast-grep applies heuristics that produce false positives; specify --lang ts, --lang py, etc. for accurate AST parsing.
  2. ALWAYS use ripgrep/keyword search first to narrow the target set — structural search over the whole codebase is slow; use ripgrep to find candidate files first, then apply ast-grep for precise matching.
  3. NEVER use regex for structural code patterns — regex breaks on formatting differences, nested structures, and multi-line code; AST patterns are format-independent and semantically precise.
  4. ALWAYS test patterns on a known match before running project-wide — patterns with incorrect syntax silently match nothing; verify the pattern finds at least one known example before broad application.
  5. ALWAYS use $$$ for variable argument lists, not * or . — ast-grep uses metavariable syntax ($NAME, $$$, $$); regex or glob syntax in patterns produces silent failures.

Anti-Patterns

Anti-PatternWhy It FailsCorrect Approach
No --lang flagWrong parser applied; produces false positives and missesAlways specify --lang ts, --lang py, etc.
Running project-wide without ripgrep pre-filterSlow on large codebases; many irrelevant resultsUse ripgrep to identify candidate files first
Regex for structural matchingBreaks on multi-line, whitespace variations, nestingUse ast-grep AST patterns ($NAME, $$$, etc.)
Untested pattern on full codebaseIncorrect patterns silently return nothingTest on one known match first
Using * or . for wildcardsNot valid ast-grep syntax; ignored or errorsUse $NAME for single node, $$$ for sequences

Memory Protocol (MANDATORY)

Before starting: Read .claude/context/memory/learnings.md

After completing:

  • New pattern → .claude/context/memory/learnings.md
  • Issue found → .claude/context/memory/issues.md
  • Decision made → .claude/context/memory/decisions.md

ASSUME INTERRUPTION: If it's not in memory, it didn't happen.

Discovery
Tags

No tags published for this skill.

Version
Latest version metadata

Version

v2026.09.24

Published

Sep 24, 2026

Category

Uncategorized

License

Not specified

Source path

.claude/skills/code-structural-search

Default branch

main

Latest commit

64b580e

Tree SHA

42a1df4