# Behavior traces — Graphify-Labs/graphify

> Canonical page: https://codevetter.com/unpack/graphify/behavior-traces

# Behavior traces — Graphify-Labs/graphify

Scanned commit 20a20d30d8e7eef77675651f0199d87f913bd3e7 (2026-09-20). Generated by codevetter codevetter 1.12.0 on 2026-09-22.

Three traced flows: (1) `graphify install` copies the platform's generated skill bundle and registers hooks/always-on instruction blocks; (2) `graphify extract .` runs the full headless pipeline detect->extract->resolve->build->cluster->export with shrink guards; (3) `graphify query`/`graphify update` read and incrementally maintain graph.json. A fourth trace covers the git post-commit auto-rebuild. All flows converge on the same modules: detect/extract/build/cluster/report/export under graphify/.
- Startup trace (`graphify <cmd>`): __main__.main() -> _run_cli() reconfigures stdout/stderr to utf-8, checks every platform skill destination's .graphify_version stamp for staleness (skipped for install/uninstall/hook-check/hook-guard), prints usage if no args, then routes install commands to install.dispatch_install_cli and everything else to cli.dispatch_command. — [graphify/__main__.py#L486-536](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/__main__.py#L486-L536) [graphify/__main__.py#L163-233](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/__main__.py#L163-L233)
- Install trace: dispatch_install_cli -> _canonical_platform/_PLATFORM_CONFIG lookup -> _platform_skill_destination -> _copy_skill_file copies graphify/skill-<host>.md (plus skills/<host>/references/ sidecar via _install_skill_references) into e.g. ~/.claude/skills/graphify/SKILL.md, then _write_version_stamp; hook platforms additionally write PreToolUse hook config (e.g. `graphify hook-guard` for Claude, `graphify hook-check` for Codex). — [graphify/install.py#L120-260](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/install.py#L120-L260) [graphify/__main__.py#L29-119](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/__main__.py#L29-L119) [graphify/__main__.py#L396-414](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/__main__.py#L396-L414)
- Extract trace (headless): cli 'extract' parses flags -> persists corpus-shaping options (_write_build_cfg for excludes/gitignore) -> detect or detect_incremental -> collect_files -> extract() [cache check -> _extract_parallel/_extract_sequential -> run_language_resolvers] -> llm.extract_corpus_parallel for doc/image/paper chunks (unless --code-only) -> merge -> deduplicate_entities -> build_from_json -> cluster + score_all -> to_json (shrink-guarded) -> report.generate -> save_manifest. — [graphify/cli.py#L3218-3467](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/cli.py#L3218-L3467) [graphify/extract.py#L6787-6918](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/extract.py#L6787-L6918) [graphify/resolver_registry.py#L59-85](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/resolver_registry.py#L59-L85)
- Skill-driven trace (`/graphify .`): skill.md instructs the host agent to resolve a Python interpreter into graphify-out/.graphify_python, run detect() writing .graphify_detect.json, run AST extraction to .graphify_ast.json, dispatch parallel general-purpose subagents writing .graphify_chunk_NN.json files (or call llm.extract_corpus_parallel when GEMINI_API_KEY/GOOGLE_API_KEY is set), merge to .graphify_semantic.json then .graphify_extract.json, then build_from_json -> cluster -> to_json -> GRAPH_REPORT.md, label communities, export html, save manifest, and clean temp files. — [graphify/skill.md#L65-194](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/skill.md#L65-L194) [graphify/skill.md#L196-356](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/skill.md#L196-L356) [graphify/skill.md#L393-449](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/skill.md#L393-L449) [graphify/skill.md#L482-624](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/skill.md#L482-L624)
- Query trace: cli 'query' resolves --graph (default graphify-out/graph.json), enforces .json suffix + size cap, json.loads -> node_link_graph (undirected with per-edge _src/_tgt direction preserved) -> serve._query_graph_text(question, mode=bfs|dfs, depth, token_budget, context_filters) -> querylog.log_query -> _touch_query_stamp -> print. — [graphify/cli.py#L1202-1322](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/cli.py#L1202-L1322) [graphify/serve.py#L1349-1400](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/serve.py#L1349-L1400)
- Update trace: cli 'update' reads GRAPHIFY_FORCE/--force, recovers the scan root from graphify-out/.graphify_root (utf-8-sig read), then watch._rebuild_code(watch_path, block_on_lock=True) -> _rebuild_lock flock -> detect() with persisted excludes -> re-extract changed code files only -> build_merge into existing graph -> to_json -> manifest update; doc/image changes still require the skill's --update path with an LLM. — [graphify/cli.py#L2403-2461](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/cli.py#L2403-L2461) [graphify/watch.py#L1355-1474](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/watch.py#L1355-L1474)
- Post-commit hook trace: git hook -> _WORKTREE_GUARD skips linked worktrees -> _PYTHON_DETECT resolves interpreter (pinned exe -> .graphify_python -> launcher shebang -> uv tool dirs -> python3) -> _detached_launch spawns detached python -c rebuild -> _REBUILD_BODY_COMMIT sets SIGALRM/threading timeout (GRAPHIFY_REBUILD_TIMEOUT, kills multiprocessing children), validates .graphify_root stays in-repo, calls _rebuild_code(changed_paths), then best-effort reflect() to refresh LESSONS.md. — [graphify/hooks.py#L19-138](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/hooks.py#L19-L138) [graphify/hooks.py#L144-223](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/hooks.py#L144-L223) [graphify/hooks.py#L318-371](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/hooks.py#L318-L371)
- MCP request trace: serve()/serve_http -> _build_server(graph_path) -> _GraphContextCache (pinned default + LRU of project graphs, GRAPHIFY_MAX_CONTEXTS default 8) -> tool call _select_graph(project_path) -> _load_ctx -> _load_graph (size cap + node_link_graph) -> handler (e.g. _tool_query_graph -> _query_graph_text) with ToolError mapped to isError results. — [graphify/serve.py#L121-180](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/serve.py#L121-L180) [graphify/serve.py#L1795-1860](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/serve.py#L1795-L1860) [graphify/serve.py#L2021-2049](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/serve.py#L2021-L2049)
- Skill version-check trace: on any non-silent invocation, _run_cli iterates {_platform_skill_destination(name) for name in _PLATFORM_CONFIG} and calls _check_skill_version, which warns when the on-disk skill is older (suggests targeted `graphify install --platform X`) or NEWER than the package (warns that install would downgrade). — [graphify/__main__.py#L163-233](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/__main__.py#L163-L233) [graphify/__main__.py#L516-527](https://github.com/Graphify-Labs/graphify/blob/20a20d30d8e7eef77675651f0199d87f913bd3e7/graphify/__main__.py#L516-L527)

Every claim links to its cited files at the pinned commit. Citations identify source evidence; they do not establish runtime correctness. Independent CodeVetter scan — not reviewed by upstream maintainers.

## Public product links

- [CodeVetter](https://codevetter.com/)
- [Download](https://codevetter.com/download)
- [Documentation](https://codevetter.com/docs/)
- [Source](https://github.com/Codevetter/codevetter)
