analyze-project
Analyze Project
Scan a project and produce or update docs/TechStack.md and docs/ProjectStructure.md — living documentation that any AI agent session can read to instantly understand the project without re-scanning from scratch.
When to Use
- Starting work on a project for the first time
- Before any feature work when project docs don't exist yet
- Periodically to keep docs current after codebase changes
- After major refactors, dependency upgrades, or service additions
When NOT to use: docs/TechStack.md and docs/ProjectStructure.md exist and no significant structural changes (config files, directories, container configs) have occurred since the last scan.
Input
- A project or workspace root (provided by user or detected from workspace)
Output
docs/TechStack.md— concise tech stack reference carddocs/ProjectStructure.md— operational project map- In monorepos: per-service copies under
[service-path]/docs/
The Process
Step 1: Check Existing Docs
Check if docs/TechStack.md and docs/ProjectStructure.md exist at the project root.
If they exist, read them and extract the YAML frontmatter:
---
generated-by: analyze-project
date: 2024-03-14T12:00:00Z
commit: abc1234
---
If the files exist, hold their contents — you'll compare against fresh scan results later.
Step 2: Staleness Gate
Run git rev-parse --short HEAD to get the current commit hash.
If the commit field in frontmatter differs from HEAD (it usually will — it records the commit at last scan, not the latest), check what actually changed:
Run git diff --name-only <frontmatter-commit>..HEAD to get committed changes, and git status --short to get uncommitted changes (staged, unstaged, and untracked files). Combine both lists.
Evaluate whether the changes are significant for project docs:
- Significant changes (trigger re-scan): new/removed/renamed config files (
package.json,composer.json,docker-compose.yml,Dockerfile,Makefile,*.config.*, etc.), new/removed top-level directories, changes to.devcontainer/, CI config changes, README/INSTALL/SETUP changes - Insignificant changes (skip re-scan): source code changes within existing directories, test changes, asset changes, documentation changes in subdirectories
Decision:
- Files don't exist → Proceed to scan.
- Files exist, commits match HEAD → Report "Project docs are up to date." and stop.
- Files exist, commits differ, only insignificant changes → Report "Project docs are up to date (no structural changes since last scan)." and stop.
- Files exist, commits differ, significant changes detected → Report which files changed and proceed to scan.
- No commit field in frontmatter → Proceed to scan.
If git is not available, skip this check and always proceed to scan.
Step 3: Ownership Check
For each existing file, check the generated-by field in YAML frontmatter:
generated-by: analyze-projectpresent → Skill owns this file. Will update without asking.- File exists but no
generated-by: analyze-project→ Manually authored. Ask the user before overwriting:
"
docs/TechStack.mdexists but wasn't generated by this skill. Overwrite it? (yes/no)"
If user declines, skip that file and report findings in chat instead.
Step 4: Scan Root
List the project root directory. Read relevant files found:
Config files (reveal tech stack):
package.json,composer.json,Cargo.toml,go.mod,pyproject.toml,Gemfile,build.gradle,pom.xml, etc.tsconfig.json,vite.config.*,webpack.config.*,nuxt.config.*, etc.
Container and dev environment:
docker-compose.yml/docker-compose.yamlDockerfile.devcontainer/devcontainer.json
CI/CD:
.github/workflows/*.yml.gitlab-ci.ymlJenkinsfile
Documentation:
README.mdINSTALL.md,SETUP.md
Quality tooling:
Makefile.eslintrc.*,eslint.config.*.prettierrcphpunit.xml,vitest.config.*,jest.config.*,pytest.ini
Start from the root listing. If root has enough config files, that's all you need. If root contains only a single folder (e.g., the repo wraps one project in a subdirectory), treat that folder as the effective root and list it instead. If root is unclear, run a quick glob for config files (**/{*.yml,*.yaml,*.json,*.toml,*.ini,*.md}) limited to a small number of results — the paths reveal where projects and services live (e.g., services/api/package.json). Then read those directories. Avoid full recursive filesystem scans.
Step 5: Detect Monorepo
Check for monorepo signals from what was found in Step 4:
- Directories named
apps/,services/,packages/at root docker-compose.ymldefining multiple services with build contexts- Workspace config in
package.json(workspacesfield) orpnpm-workspace.yaml - Multiple
Dockerfilereferences in different subdirectories
If monorepo detected, identify service directories and their names.
Step 6: Scan Services (monorepo only)
For each service directory identified in Step 5, apply the same root-reading approach:
- List the service directory
- Read its config files (package.json, composer.json, Dockerfile, etc.)
- Read its README.md if present
- Note its doc location, dev/lint/test commands
Step 7: Write Docs
Use the templates from references/formats.md.
Single project:
- Write
docs/TechStack.mdwith tech stack reference card - Write
docs/ProjectStructure.mdwith operational project map ProjectStructure.mdends with a "See Also" link toDatabaseStructure.md
Monorepo:
- Write root
docs/TechStack.mdwith shared stack + per-service summary - Write root
docs/ProjectStructure.mdwith service table and monorepo-level overview - For each service, write
[service-path]/docs/TechStack.mdand[service-path]/docs/ProjectStructure.md - Create
docs/directories if they don't exist
All files get YAML frontmatter with:
generated-by: analyze-projectdate:current ISO 8601 datetimecommit:current short git commit hash
Announce the saved paths:
"Project docs updated:
docs/TechStack.mddocs/ProjectStructure.md[per-service paths if monorepo] Commit: [hash]"
Common Rationalizations
| Rationalization | Reality |
|---|---|
| "The README has all this info" | READMEs describe intent and setup steps. TechStack and ProjectStructure describe current reality in a structured, machine-readable format. |
| "I can just read package.json" | One config file gives you one piece. These docs synthesize all signals into two quick-read files. |
| "The project is small, I don't need docs" | Small projects still have a stack, structure, and tooling. Two short files save every future session from re-discovering them. |
| "Docs will get outdated" | The staleness gate and commit tracking exist specifically to prevent this. Run the skill again. |
Red Flags
- Skipping the staleness check and always rewriting (wastes time, loses manual edits)
- Deep-scanning the filesystem instead of reading root
- Not including YAML frontmatter in output files
- Overwriting manually-authored files without asking
- Missing the monorepo detection step on a multi-service project
- Writing rationale or opinions instead of facts in TechStack.md
- Not creating
docs/directory before writing
Verification
Before finishing, confirm:
- Staleness check performed (or git unavailable noted)
- Ownership check performed for existing files
- Root directory listing read (not deep-scanned)
- Relevant config files read
-
docs/TechStack.mdwritten with frontmatter and concise stack listing -
docs/ProjectStructure.mdwritten with frontmatter and operational map -
ProjectStructure.mdends with reference toDatabaseStructure.md - If monorepo: services detected and per-service docs written
- All generated files have
generated-by,date, andcommitin frontmatter - Saved paths announced to user