Zsh — 18 Operations for AI Agents
Zsh scripts and dotfiles shape every developer's daily environment — `.zshrc`, functions, completion logic. act101 reads functions and aliases as structure, so agents modify shell environments without breaking the setup someone tuned for years.
This page is the canonical reference an AI coding agent uses to refactor, query, and analyze Zsh code through the act MCP server. 18 operations available: 0 refactor, 18 query, 0 analysis. Each operation is callable from Claude Code, Cursor, Codex, OpenCode, or any MCP-compatible agent host. Click any operation for a stable anchor link suitable for citation.
Worked Zsh examples
act101 reads a Zsh script's function definitions as function declarations, and reads every local-declared variable inside a function, plus a top-level typeset array, as variable declarations named for the variable. symbols covers the identical set and adds one more construct the skeleton does not read: the loop variable bound by a for x in ... clause, reported as kind: unknown since the grammar states no kind for it. The unit of structure in this grammar is the declaration statement itself: neither query descends into a function's own command pipeline, so a variable set by plain assignment without local or typeset never appears. Each example below is the verbatim output of the command shown, run against the file shown. Query outputs are pretty-printed with the timing block omitted.
Read the script's functions and declared variables as a skeleton
checksum-sweep.zsh verifies release artifacts against known SHA-256 sums: checksum_of hashes one file, and verify_release walks the expected_sums array checking each release variant.
$ act query skeleton checksum-sweep.zsh
Before
#!/usr/bin/env zsh
set -euo pipefail
typeset -A expected_sums
expected_sums=(
linux-amd64 "9f2c1a0e8b7d6c5a4f3e2d1c0b9a8f7e"
darwin-arm64 "2b1a0f9e8d7c6b5a4f3e2d1c0b9a8f7d"
)
function checksum_of() {
local artifact_path=$1
shasum -a 256 "$artifact_path" | awk '{print $1}'
}
function verify_release() {
local release_dir=$1
local failures=0
for variant in "${(@k)expected_sums}"; do
local artifact="$release_dir/act-$variant.tar.gz"
local actual=$(checksum_of "$artifact")
if [[ ! -f "$artifact" ]]; then
(( failures++ ))
elif [[ "$actual" != "${expected_sums[$variant]}" ]]; then
(( failures++ ))
fi
done
return $failures
}
verify_release "$1"
Output
{
"type": "Skeleton",
"declarations": [
{
"kind": "variable",
"name": "expected_sums",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 5,
"column": 1,
"byte_offset": 63
},
"end": {
"file": "checksum-sweep.zsh",
"line": 8,
"column": 2,
"byte_offset": 186
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 5,
"column": 1,
"byte_offset": 63
},
"end": {
"file": "checksum-sweep.zsh",
"line": 5,
"column": 14,
"byte_offset": 76
}
}
},
{
"kind": "function",
"name": "checksum_of",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 10,
"column": 1,
"byte_offset": 188
},
"end": {
"file": "checksum-sweep.zsh",
"line": 13,
"column": 2,
"byte_offset": 295
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 10,
"column": 10,
"byte_offset": 197
},
"end": {
"file": "checksum-sweep.zsh",
"line": 10,
"column": 21,
"byte_offset": 208
}
}
},
{
"kind": "variable",
"name": "artifact_path",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 11,
"column": 11,
"byte_offset": 223
},
"end": {
"file": "checksum-sweep.zsh",
"line": 11,
"column": 27,
"byte_offset": 239
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 11,
"column": 11,
"byte_offset": 223
},
"end": {
"file": "checksum-sweep.zsh",
"line": 11,
"column": 24,
"byte_offset": 236
}
}
},
{
"kind": "function",
"name": "verify_release",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 15,
"column": 1,
"byte_offset": 297
},
"end": {
"file": "checksum-sweep.zsh",
"line": 28,
"column": 2,
"byte_offset": 730
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 15,
"column": 10,
"byte_offset": 306
},
"end": {
"file": "checksum-sweep.zsh",
"line": 15,
"column": 24,
"byte_offset": 320
}
}
},
{
"kind": "variable",
"name": "release_dir",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 16,
"column": 11,
"byte_offset": 335
},
"end": {
"file": "checksum-sweep.zsh",
"line": 16,
"column": 25,
"byte_offset": 349
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 16,
"column": 11,
"byte_offset": 335
},
"end": {
"file": "checksum-sweep.zsh",
"line": 16,
"column": 22,
"byte_offset": 346
}
}
},
{
"kind": "variable",
"name": "failures",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 17,
"column": 11,
"byte_offset": 360
},
"end": {
"file": "checksum-sweep.zsh",
"line": 17,
"column": 21,
"byte_offset": 370
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 17,
"column": 11,
"byte_offset": 360
},
"end": {
"file": "checksum-sweep.zsh",
"line": 17,
"column": 19,
"byte_offset": 368
}
}
},
{
"kind": "variable",
"name": "artifact",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 19,
"column": 15,
"byte_offset": 431
},
"end": {
"file": "checksum-sweep.zsh",
"line": 19,
"column": 58,
"byte_offset": 474
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 19,
"column": 15,
"byte_offset": 431
},
"end": {
"file": "checksum-sweep.zsh",
"line": 19,
"column": 23,
"byte_offset": 439
}
}
},
{
"kind": "variable",
"name": "actual",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 20,
"column": 15,
"byte_offset": 489
},
"end": {
"file": "checksum-sweep.zsh",
"line": 20,
"column": 48,
"byte_offset": 522
}
},
"name_range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 20,
"column": 15,
"byte_offset": 489
},
"end": {
"file": "checksum-sweep.zsh",
"line": 20,
"column": 21,
"byte_offset": 495
}
}
}
]
}
The skeleton reports eight declarations: expected_sums as variable from its typeset -A array; checksum_of and verify_release as function; and five local-declared variables — artifact_path, release_dir, failures, artifact, actual — each as variable.
List the same declarations plus the loop variable as symbols
verify_release iterates the array's keys with for variant in "${(@k)expected_sums}".
$ act query symbols checksum-sweep.zsh
Before
#!/usr/bin/env zsh
set -euo pipefail
typeset -A expected_sums
expected_sums=(
linux-amd64 "9f2c1a0e8b7d6c5a4f3e2d1c0b9a8f7e"
darwin-arm64 "2b1a0f9e8d7c6b5a4f3e2d1c0b9a8f7d"
)
function checksum_of() {
local artifact_path=$1
shasum -a 256 "$artifact_path" | awk '{print $1}'
}
function verify_release() {
local release_dir=$1
local failures=0
for variant in "${(@k)expected_sums}"; do
local artifact="$release_dir/act-$variant.tar.gz"
local actual=$(checksum_of "$artifact")
if [[ ! -f "$artifact" ]]; then
(( failures++ ))
elif [[ "$actual" != "${expected_sums[$variant]}" ]]; then
(( failures++ ))
fi
done
return $failures
}
verify_release "$1"
Output
{
"type": "Symbols",
"symbols": [
{
"name": "expected_sums",
"kind": "variable",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 5,
"column": 1,
"byte_offset": 63
},
"end": {
"file": "checksum-sweep.zsh",
"line": 5,
"column": 14,
"byte_offset": 76
}
},
"visibility": "unknown"
},
{
"name": "checksum_of",
"kind": "function",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 10,
"column": 10,
"byte_offset": 197
},
"end": {
"file": "checksum-sweep.zsh",
"line": 10,
"column": 21,
"byte_offset": 208
}
},
"visibility": "unknown"
},
{
"name": "artifact_path",
"kind": "variable",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 11,
"column": 11,
"byte_offset": 223
},
"end": {
"file": "checksum-sweep.zsh",
"line": 11,
"column": 24,
"byte_offset": 236
}
},
"visibility": "unknown"
},
{
"name": "verify_release",
"kind": "function",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 15,
"column": 10,
"byte_offset": 306
},
"end": {
"file": "checksum-sweep.zsh",
"line": 15,
"column": 24,
"byte_offset": 320
}
},
"visibility": "unknown"
},
{
"name": "release_dir",
"kind": "variable",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 16,
"column": 11,
"byte_offset": 335
},
"end": {
"file": "checksum-sweep.zsh",
"line": 16,
"column": 22,
"byte_offset": 346
}
},
"visibility": "unknown"
},
{
"name": "failures",
"kind": "variable",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 17,
"column": 11,
"byte_offset": 360
},
"end": {
"file": "checksum-sweep.zsh",
"line": 17,
"column": 19,
"byte_offset": 368
}
},
"visibility": "unknown"
},
{
"name": "variant",
"kind": "unknown",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 18,
"column": 9,
"byte_offset": 379
},
"end": {
"file": "checksum-sweep.zsh",
"line": 18,
"column": 16,
"byte_offset": 386
}
},
"visibility": "unknown"
},
{
"name": "artifact",
"kind": "variable",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 19,
"column": 15,
"byte_offset": 431
},
"end": {
"file": "checksum-sweep.zsh",
"line": 19,
"column": 23,
"byte_offset": 439
}
},
"visibility": "unknown"
},
{
"name": "actual",
"kind": "variable",
"range": {
"start": {
"file": "checksum-sweep.zsh",
"line": 20,
"column": 15,
"byte_offset": 489
},
"end": {
"file": "checksum-sweep.zsh",
"line": 20,
"column": 21,
"byte_offset": 495
}
},
"visibility": "unknown"
}
]
}
symbols reports the same eight declarations plus one more: variant, the for loop's bound variable, reported as kind: unknown since the grammar's rule for a loop variable states no kind.
Score the release-verification branching
verify_release loops once over the expected variants and branches once with an if/elif pair checking whether the artifact is missing or its checksum doesn't match.
$ act query complexity checksum-sweep.zsh
Before
#!/usr/bin/env zsh
set -euo pipefail
typeset -A expected_sums
expected_sums=(
linux-amd64 "9f2c1a0e8b7d6c5a4f3e2d1c0b9a8f7e"
darwin-arm64 "2b1a0f9e8d7c6b5a4f3e2d1c0b9a8f7d"
)
function checksum_of() {
local artifact_path=$1
shasum -a 256 "$artifact_path" | awk '{print $1}'
}
function verify_release() {
local release_dir=$1
local failures=0
for variant in "${(@k)expected_sums}"; do
local artifact="$release_dir/act-$variant.tar.gz"
local actual=$(checksum_of "$artifact")
if [[ ! -f "$artifact" ]]; then
(( failures++ ))
elif [[ "$actual" != "${expected_sums[$variant]}" ]]; then
(( failures++ ))
fi
done
return $failures
}
verify_release "$1"
Output
{
"type": "Complexity",
"score": 3,
"details": "Base complexity: 1, +1 for_statement, +1 if_statement"
}
Complexity starts at a base of 1 and adds one point for the for_statement and one for the if_statement, for a total score of 3; the elif clause chained onto the same if adds nothing further, unlike a separate if_statement.
Query
18 query tools, the same on every supported language. Descriptions live in the shared reference: /docs/query-tools.
callers control_flow data_flow definition diagnostics effect_closure effect_summary fix_auto get_type graph import_organize interface mutations references repo_outline skeleton symbols symbols_batch