@benjaminthomas/spec-driven-dev 0.0.0-stage → 1.4.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +557 -2
- package/bin/cli.mjs +415 -0
- package/package.json +12 -4
- package/skills/generative-seo/SKILL.md +255 -0
- package/skills/generative-seo/assets/citation-log-template.md +17 -0
- package/skills/generative-seo/assets/competitor-analysis-template.md +20 -0
- package/skills/generative-seo/assets/content-plan-template.md +15 -0
- package/skills/generative-seo/assets/geo-config-template.md +33 -0
- package/skills/generative-seo/assets/geo-playbook-template.md +22 -0
- package/skills/generative-seo/assets/social-queue-template.md +8 -0
- package/skills/generative-seo/references/geo-methodology.md +143 -0
- package/skills/spec-checkpoint/SKILL.md +106 -0
- package/skills/spec-create/SKILL.md +149 -0
- package/skills/spec-create/references/action-required-template.md +53 -0
- package/skills/spec-create/references/readme-template.md +53 -0
- package/skills/spec-create/references/requirements-template.md +54 -0
- package/skills/spec-create/references/task-template.md +86 -0
- package/skills/spec-implement/SKILL.md +236 -0
- package/skills/spec-implement/references/coder-prompt-template.md +48 -0
- package/skills/spec-implement/references/fix-prompt-template.md +38 -0
- package/skills/spec-implement/references/review-prompt-template.md +50 -0
- package/skills/spec-investigate/SKILL.md +323 -0
- package/skills/spec-investigate/references/report-template.md +53 -0
- package/skills/spec-setup/SKILL.md +105 -0
- package/skills/spec-setup/references/config-template.yml +45 -0
- package/skills/spec-ship/SKILL.md +218 -0
- package/skills/spec-verify/SKILL.md +153 -0
- package/skills/spec-verify/references/report-template.md +57 -0
|
@@ -0,0 +1,255 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: generative-seo
|
|
3
|
+
description: Run an evidence-based SEO + GEO (Generative Engine Optimization) program for ANY website or product codebase — auditing technical SEO, writing or retrofitting content so it gets cited by ChatGPT/Perplexity/AI Overviews, tracking AI-citation visibility, refreshing competitor research, and drafting distribution posts. Use whenever the user asks to audit SEO, improve AI-search/AI-citation visibility, write or optimize marketing/blog content for search or GEO, check whether a product shows up in ChatGPT/Perplexity answers, do competitor/keyword research, or wants a monthly SEO performance report — regardless of framework (Next.js, Astro, Remix, plain HTML, WordPress, etc.) or what the product is. Works on any repo; it interviews you once to learn the project's specifics (brand, domain, framework, docs location) and remembers the answers.
|
|
4
|
+
license: MIT
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Generative SEO (GEO) Operations
|
|
8
|
+
|
|
9
|
+
Runs an SEO + GEO program the same way a sharp in-house SEO operator would: technical
|
|
10
|
+
audits, answer-first content built to be quoted by AI engines, an AI-citation tracker,
|
|
11
|
+
competitor watch, and (draft-only) distribution. It is deliberately generic — first use
|
|
12
|
+
in a repo spends a few minutes learning that project's facts, then behaves like a
|
|
13
|
+
project-specific skill from then on.
|
|
14
|
+
|
|
15
|
+
**Mode selection:** the argument names the mode (`content`, `audit`, `optimize`,
|
|
16
|
+
`competitors`, `citations`, `report`, `social`). No argument → read the project's docs
|
|
17
|
+
(below), summarize current state, and recommend the highest-impact next action.
|
|
18
|
+
|
|
19
|
+
For the full evidence behind every rule below (which studies, what they found, why
|
|
20
|
+
each technique works) and the complete technical checklist, see
|
|
21
|
+
`references/geo-methodology.md`. Read it before an `audit` or before writing a
|
|
22
|
+
first piece of `content` in a new project; skip re-reading it on later runs in the
|
|
23
|
+
same project.
|
|
24
|
+
|
|
25
|
+
---
|
|
26
|
+
|
|
27
|
+
## First run in a project: learn the project
|
|
28
|
+
|
|
29
|
+
Look for a config file at `docs/seo/geo-config.md` (or wherever the user says their
|
|
30
|
+
SEO docs live — some repos keep them in `content/`, `marketing/`, or a wiki instead).
|
|
31
|
+
If it exists, read it and skip to **Read these first**.
|
|
32
|
+
|
|
33
|
+
If it does not exist, this is the first run — ask the user (batch these, don't
|
|
34
|
+
interview one question at a time):
|
|
35
|
+
|
|
36
|
+
1. **Product/brand name(s)** — and critically, if the product is a sub-brand of a
|
|
37
|
+
parent company or a different name than the company that builds it, get that
|
|
38
|
+
distinction explicit now (e.g. "Acme Corp is the company; Acme Flow is the
|
|
39
|
+
product we're marketing" or "same name, no distinction needed"). Getting this
|
|
40
|
+
wrong (writing "is Acme Corp free?" when the product is Acme Flow) is a
|
|
41
|
+
real, recurring mistake — nail it once here instead of guessing per-page later.
|
|
42
|
+
2. **Primary domain** the content lives on (affects sitemap/robots checks and
|
|
43
|
+
internal-link audits).
|
|
44
|
+
3. **Framework** — Next.js, Astro, Remix, SvelteKit, plain static HTML, a CMS
|
|
45
|
+
(WordPress/Webflow/etc.), or something else. This determines where
|
|
46
|
+
sitemap/robots/metadata/JSON-LD live (see `references/geo-methodology.md` for
|
|
47
|
+
the per-framework map) — if unsure, look at the repo yourself first
|
|
48
|
+
(`package.json`, top-level config files) before asking.
|
|
49
|
+
4. **Where marketing/content pages live** in the repo (a directory, a headless
|
|
50
|
+
CMS, or "not in this repo" if content is managed elsewhere).
|
|
51
|
+
5. **Existing design system doc**, if any (a `DESIGN.md`, a Storybook, a Figma
|
|
52
|
+
library) — new/edited pages should match it rather than invent a new look.
|
|
53
|
+
6. **How to source real statistics** for content — product analytics the user can
|
|
54
|
+
query, a public dataset, or "external sources only." Never invent numbers
|
|
55
|
+
regardless of the answer.
|
|
56
|
+
7. **Docs folder** for this skill's own working files (default: `docs/seo/` at
|
|
57
|
+
repo root — offer this default rather than making the user think of one).
|
|
58
|
+
|
|
59
|
+
Write the answers to `<docs_dir>/geo-config.md` using
|
|
60
|
+
`assets/geo-config-template.md` as the shape. Then create the four working docs
|
|
61
|
+
from their templates in `assets/` (only the ones missing — never overwrite an
|
|
62
|
+
existing one):
|
|
63
|
+
|
|
64
|
+
| File | Template | Purpose |
|
|
65
|
+
|---|---|---|
|
|
66
|
+
| `<docs_dir>/geo-playbook.md` | `assets/geo-playbook-template.md` | This project's evidence-based rules + house style, filled in from the config answers |
|
|
67
|
+
| `<docs_dir>/content-plan.md` | `assets/content-plan-template.md` | The execution backlog with statuses |
|
|
68
|
+
| `<docs_dir>/competitor-analysis.md` | `assets/competitor-analysis-template.md` | Competitor landscape + keyword gaps |
|
|
69
|
+
| `<docs_dir>/citation-log.md` | `assets/citation-log-template.md` | Dated AI-citation audit history |
|
|
70
|
+
|
|
71
|
+
For `citations` mode specifically, also derive a **fixed prompt set**: 10–15
|
|
72
|
+
realistic queries someone would type into ChatGPT/Perplexity/Google when looking
|
|
73
|
+
for a product like this one (category term, "best X for Y" roundups, problem-first
|
|
74
|
+
questions, a couple of named-competitor-alternative queries). Save them into
|
|
75
|
+
`<docs_dir>/citation-log.md`'s header. Keep this list stable run-over-run — append
|
|
76
|
+
new queries, don't rewrite the set, or trend comparison breaks.
|
|
77
|
+
|
|
78
|
+
## Read these first (source of truth — keep them updated every run)
|
|
79
|
+
|
|
80
|
+
- `<docs_dir>/geo-config.md` — project facts (brand, domain, framework, paths)
|
|
81
|
+
- `<docs_dir>/geo-playbook.md` — this project's rules, filled in from the methodology reference
|
|
82
|
+
- `<docs_dir>/content-plan.md` — phased content queue with statuses
|
|
83
|
+
- `<docs_dir>/competitor-analysis.md` — competitor landscape + keyword gap map
|
|
84
|
+
- `<docs_dir>/citation-log.md` — AI-citation audit history + the fixed prompt set
|
|
85
|
+
|
|
86
|
+
---
|
|
87
|
+
|
|
88
|
+
## Non-negotiable content rules (every page you write or edit)
|
|
89
|
+
|
|
90
|
+
Full evidence (Princeton GEO paper, Ahrefs citation studies) in
|
|
91
|
+
`references/geo-methodology.md`. Summary:
|
|
92
|
+
|
|
93
|
+
1. **Answer-first**: the complete, direct answer to the target query lands in the
|
|
94
|
+
first ~200 words. Most AI citations pull from early-page content.
|
|
95
|
+
2. **≥3 statistics, ≥1 quotable expert-voice line, cited sources** per substantive
|
|
96
|
+
page — measurably lifts AI-citation odds. Stats must be real and sourced (see
|
|
97
|
+
the project's config for where "real" comes from) — never invented.
|
|
98
|
+
3. **Extractable structure**: H2/H3s phrased as the questions people actually ask;
|
|
99
|
+
Q&A blocks; comparison tables; a TL;DR/summary box; definition-style openings
|
|
100
|
+
("X is …").
|
|
101
|
+
4. **Self-contained sections**: every H2 section should make sense quoted in
|
|
102
|
+
isolation — AI retrieval is passage-level, not whole-page.
|
|
103
|
+
5. **Author + published date + last-updated date** visible on-page. Refresh
|
|
104
|
+
anything older than ~6 months.
|
|
105
|
+
6. **FAQ block + `FAQPage` JSON-LD** on pricing, feature, and comparison pages.
|
|
106
|
+
7. Tone: practitioner-credible, specific, first-hand. No filler, never keyword-stuff.
|
|
107
|
+
8. Word count follows the query's actual answer depth — never pad, never ship a
|
|
108
|
+
page so thin it can't stand on its own (a rough floor: ~300 words).
|
|
109
|
+
9. Follow the naming/brand distinction captured in `geo-config.md` on every page —
|
|
110
|
+
re-check it before publishing if the page discusses "who makes this."
|
|
111
|
+
10. Match whatever design system this repo already has (`geo-config.md` points at
|
|
112
|
+
it) — a GEO-optimized page that looks out of place hurts more than it helps.
|
|
113
|
+
|
|
114
|
+
---
|
|
115
|
+
|
|
116
|
+
## Mode: `audit` — technical SEO + GEO audit (add `--fix` to also apply fixes)
|
|
117
|
+
|
|
118
|
+
Audit BOTH the codebase and the live site (fetch the live URLs — deployed state
|
|
119
|
+
drifts from the repo). Report every failure with file:line. With `--fix`, apply
|
|
120
|
+
code-level fixes and run the project's own check commands (lint/typecheck —
|
|
121
|
+
inspect `package.json` scripts or the repo's build tooling; skip anything that
|
|
122
|
+
doesn't exist rather than assuming `npm run check`).
|
|
123
|
+
|
|
124
|
+
Full checklist (sitemap/robots by framework, JSON-LD schema types, AI-crawler
|
|
125
|
+
allowlist, `llms.txt`, heading hygiene, internal linking, Core Web Vitals sanity)
|
|
126
|
+
is in `references/geo-methodology.md` — pull it up for this mode.
|
|
127
|
+
|
|
128
|
+
**Output:** severity-ordered findings table (blocker / high / med / low), each
|
|
129
|
+
with file:line and the fix. With `--fix`: apply, verify with the project's checks,
|
|
130
|
+
summarize the diff.
|
|
131
|
+
|
|
132
|
+
## Mode: `content` — write the next content piece
|
|
133
|
+
|
|
134
|
+
1. Read `<docs_dir>/content-plan.md`; pick the first `todo` item in the current
|
|
135
|
+
phase (or the item the user names). Flag any unresolved blockers first.
|
|
136
|
+
2. Check the target query's live SERP (web search) — confirm intent, note what
|
|
137
|
+
ranks, find a differentiating angle grounded in what this specific product
|
|
138
|
+
actually does differently (pull that from `geo-config.md` / the codebase, not
|
|
139
|
+
assumption).
|
|
140
|
+
3. Write the piece following the non-negotiable rules above. Comparison pages
|
|
141
|
+
must be honest about competitors — credibility is the citation currency.
|
|
142
|
+
4. Implement it wherever this repo's content actually lives (per `geo-config.md`
|
|
143
|
+
— a route file, a CMS entry, a markdown collection) with full metadata,
|
|
144
|
+
JSON-LD, and design-system compliance.
|
|
145
|
+
5. Add the URL to the project's sitemap mechanism. Update the item's status in
|
|
146
|
+
`content-plan.md` to `shipped (YYYY-MM-DD)`.
|
|
147
|
+
6. Run the project's lint/typecheck/build if it has them. Present the draft for
|
|
148
|
+
review — content is outward-facing; the user approves before it goes live.
|
|
149
|
+
7. AFTER the page is deployed and live, if the project has an IndexNow/Bing-ping
|
|
150
|
+
mechanism, use it (shortens AI-engine discovery from days to hours). If it
|
|
151
|
+
doesn't, mention manual IndexNow submission (bing.com/indexnow) as an option
|
|
152
|
+
rather than inventing tooling. Never ping before deploy.
|
|
153
|
+
|
|
154
|
+
## Mode: `optimize` — GEO-retrofit an existing page
|
|
155
|
+
|
|
156
|
+
Given a URL/path: score it against the non-negotiable rules (answer-first? stats?
|
|
157
|
+
extractable structure? dates? FAQ? schema?), report a before/after checklist, then
|
|
158
|
+
apply improvements preserving the page's voice and design.
|
|
159
|
+
|
|
160
|
+
## Mode: `competitors` — refresh competitor & keyword research
|
|
161
|
+
|
|
162
|
+
1. Re-run research (web search) covering the players already in
|
|
163
|
+
`competitor-analysis.md`, plus new AI-native entrants in the same category.
|
|
164
|
+
2. Check whether the product's category term has a new canonical answer in
|
|
165
|
+
search; check who's cited in relevant "best X" roundups.
|
|
166
|
+
3. Diff against the existing doc: new entrants, keyword-gap changes, threats.
|
|
167
|
+
Append a dated changelog entry — don't remove existing queue items. Suggest
|
|
168
|
+
content-plan additions.
|
|
169
|
+
Cadence: quarterly, or whenever the user senses a new competitor.
|
|
170
|
+
|
|
171
|
+
## Mode: `citations` — AI-visibility audit
|
|
172
|
+
|
|
173
|
+
1. Run the fixed prompt set from `citation-log.md` through web search (captures
|
|
174
|
+
Google/AI-Overview signals) and check Bing presence for the same queries.
|
|
175
|
+
Direct ChatGPT/Perplexity querying usually isn't possible from here — log
|
|
176
|
+
what's checkable and list the 5-minute manual checks for the user with exact
|
|
177
|
+
prompts to paste.
|
|
178
|
+
2. For each query: record who ranks / is cited, whether this product appears
|
|
179
|
+
(distinguish **mention** vs **citation**), and which of the project's own
|
|
180
|
+
pages should be winning it.
|
|
181
|
+
3. Append a dated entry to `citation-log.md`. Report the trend vs. the previous
|
|
182
|
+
entry.
|
|
183
|
+
|
|
184
|
+
## Mode: `report` — periodic performance summary
|
|
185
|
+
|
|
186
|
+
Compile from: citation-log trend, content-plan ship rate, live-site spot checks,
|
|
187
|
+
and (if the user provides Search Console/Bing/GA exports — ask, don't assume
|
|
188
|
+
access) impressions/clicks on target queries. Output: what shipped, what moved,
|
|
189
|
+
top 3 recommended actions for next period. Set realistic expectations: Google
|
|
190
|
+
traction is typically months out from a content ship; Bing/Perplexity move faster
|
|
191
|
+
(weeks).
|
|
192
|
+
|
|
193
|
+
## Mode: `social` — draft distribution posts for shipped content (drafts ONLY)
|
|
194
|
+
|
|
195
|
+
This mode never posts anywhere — automated posting risks ToS violations on
|
|
196
|
+
LinkedIn/Reddit/etc. and the account behind it. Output goes to
|
|
197
|
+
`<docs_dir>/social-queue.md` (create from `assets/social-queue-template.md` on
|
|
198
|
+
first run); the user reviews, pastes, and marks items posted.
|
|
199
|
+
|
|
200
|
+
1. Read `social-queue.md` and `content-plan.md`. Pick shipped pages with no queue
|
|
201
|
+
entry yet — or the page the user names. Newest first, max 3 pages per run.
|
|
202
|
+
2. For each page draft, in the founder/team's actual voice (first person,
|
|
203
|
+
practitioner tone, one concrete stat or claim pulled from the page, minimal
|
|
204
|
+
hashtags, ends with a question or the link — never reads like a press
|
|
205
|
+
release):
|
|
206
|
+
- A personal-profile post for whatever the primary channel is (ask if
|
|
207
|
+
unclear — LinkedIn and X are common defaults).
|
|
208
|
+
- A shorter, product-forward version for a company/brand page, if one exists.
|
|
209
|
+
- If the piece is worth republishing elsewhere (e.g. Medium), a checklist
|
|
210
|
+
entry noting the platform's canonical-URL mechanism must be used — never
|
|
211
|
+
copy-paste in a way that loses canonical attribution.
|
|
212
|
+
- Community threads (Reddit-style forums, Hacker News, niche Slack/Discord
|
|
213
|
+
communities): only where the skill has search budget to find 1–3 live
|
|
214
|
+
threads the page genuinely answers; draft a value-first reply that stands
|
|
215
|
+
on its own without the link, flagged for the user to post manually, in
|
|
216
|
+
their own voice. Never suggest posting the identical comment in 2 places.
|
|
217
|
+
3. Append drafts under a dated heading, one entry per page, with a status marker
|
|
218
|
+
the user flips (`[ ] queued` → `[x] posted YYYY-MM-DD <URL>` or `[-]
|
|
219
|
+
skipped`). Never overwrite prior entries.
|
|
220
|
+
4. Report what was drafted and what's still unposted from previous runs — an
|
|
221
|
+
aging queue means distribution, not content, is the bottleneck.
|
|
222
|
+
|
|
223
|
+
---
|
|
224
|
+
|
|
225
|
+
## Automation (scheduled agents)
|
|
226
|
+
|
|
227
|
+
If the harness supports scheduled/cron-style agent runs, these are reasonable
|
|
228
|
+
cadences — set them up only if the user asks, never silently:
|
|
229
|
+
|
|
230
|
+
| Routine | Cadence | Action |
|
|
231
|
+
|---|---|---|
|
|
232
|
+
| Content | Weekly | Pick the next queue item, open a PR (never push straight to main) |
|
|
233
|
+
| Citation audit | Monthly | Update the citation log on a branch |
|
|
234
|
+
| Technical audit | Monthly | File findings as a report; PR fixes only for blockers |
|
|
235
|
+
| Competitor refresh | Quarterly | Refresh competitor-analysis.md |
|
|
236
|
+
| Social drafts | Weekly | Draft posts for newly-shipped pages |
|
|
237
|
+
|
|
238
|
+
Scheduled runs always work on a branch + PR — content is outward-facing and needs
|
|
239
|
+
human review before going live. If a run hits an unresolved blocker, report
|
|
240
|
+
rather than plow ahead. Never invent statistics, in scheduled or interactive runs.
|
|
241
|
+
|
|
242
|
+
## Standing cautions
|
|
243
|
+
|
|
244
|
+
- A subdomain is a separate site for authority purposes — don't split content
|
|
245
|
+
onto a subdomain without a deliberate reason; it usually just dilutes signal.
|
|
246
|
+
- Programmatic/templated pages need real data depth per page — thin
|
|
247
|
+
variable-injection pages risk scaled-content-abuse penalties for the whole
|
|
248
|
+
domain.
|
|
249
|
+
- `llms.txt` and schema markup are hygiene, not strategy — don't over-invest
|
|
250
|
+
expecting them alone to move AI-citation odds. The actual lever is answer-first
|
|
251
|
+
content + real stats + third-party mentions (roundups, directories, forums,
|
|
252
|
+
YouTube) + fast indexing (Bing/IndexNow).
|
|
253
|
+
- Anything gated behind a login the skill can't access (Search Console, Bing
|
|
254
|
+
Webmaster Tools, review-site dashboards, social platforms) → give the user a
|
|
255
|
+
precise action list; don't fake having checked it.
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
# AI Citation Log
|
|
2
|
+
|
|
3
|
+
## Fixed prompt set
|
|
4
|
+
|
|
5
|
+
<!--
|
|
6
|
+
10-15 queries a real prospect would type into ChatGPT / Perplexity / Google
|
|
7
|
+
when looking for a product like this one. Derived once on first `citations`
|
|
8
|
+
run, kept stable so trend comparisons mean something — append, don't rewrite.
|
|
9
|
+
-->
|
|
10
|
+
|
|
11
|
+
-
|
|
12
|
+
|
|
13
|
+
## Audit history
|
|
14
|
+
|
|
15
|
+
| Date | Prompt | Engine | Our status (mention/citation/absent) | Who wins | Note |
|
|
16
|
+
|---|---|---|---|---|---|
|
|
17
|
+
| | | | | | |
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
# Competitor & Keyword Analysis
|
|
2
|
+
|
|
3
|
+
## Competitor landscape
|
|
4
|
+
|
|
5
|
+
| Competitor | Category term(s) they own | Notes |
|
|
6
|
+
|---|---|---|
|
|
7
|
+
| | | |
|
|
8
|
+
|
|
9
|
+
## Keyword gap map
|
|
10
|
+
|
|
11
|
+
| Query | Who ranks/is cited today | Should we contest it? |
|
|
12
|
+
|---|---|---|
|
|
13
|
+
| | | |
|
|
14
|
+
|
|
15
|
+
## Changelog
|
|
16
|
+
|
|
17
|
+
<!-- Append a dated entry each `competitors` run. Never delete prior entries. -->
|
|
18
|
+
|
|
19
|
+
### YYYY-MM-DD
|
|
20
|
+
-
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# Content Plan
|
|
2
|
+
|
|
3
|
+
Status values: `todo`, `in-progress`, `blocked (reason)`, `shipped (YYYY-MM-DD)`.
|
|
4
|
+
|
|
5
|
+
## Phase 0 — foundation (blockers)
|
|
6
|
+
|
|
7
|
+
| Item | Target query | Status | Notes |
|
|
8
|
+
|---|---|---|---|
|
|
9
|
+
| | | todo | |
|
|
10
|
+
|
|
11
|
+
## Phase 1
|
|
12
|
+
|
|
13
|
+
| Item | Target query | Status | Notes |
|
|
14
|
+
|---|---|---|---|
|
|
15
|
+
| | | todo | |
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
---
|
|
2
|
+
product_name:
|
|
3
|
+
brand_name:
|
|
4
|
+
domain:
|
|
5
|
+
framework:
|
|
6
|
+
marketing_pages_dir:
|
|
7
|
+
sitemap_mechanism:
|
|
8
|
+
robots_mechanism:
|
|
9
|
+
design_system_doc:
|
|
10
|
+
stats_source:
|
|
11
|
+
docs_dir: docs/seo
|
|
12
|
+
---
|
|
13
|
+
|
|
14
|
+
# Brand & naming notes
|
|
15
|
+
|
|
16
|
+
<!--
|
|
17
|
+
Free text. If the product is a sub-brand of a parent company, or the software
|
|
18
|
+
name differs from the company name, state the rule here explicitly, e.g.:
|
|
19
|
+
|
|
20
|
+
"Acme Corp is the parent company (a services agency). Acme Flow is the
|
|
21
|
+
product. Never write 'is Acme Corp free' or 'who is Acme Corp for' — the
|
|
22
|
+
software is Acme Flow; Acme Corp builds it. Correct brand uses: legal
|
|
23
|
+
operator, IP ownership, author/publisher credit."
|
|
24
|
+
|
|
25
|
+
If there's no distinction (company name == product name), just say so.
|
|
26
|
+
-->
|
|
27
|
+
|
|
28
|
+
# House style notes
|
|
29
|
+
|
|
30
|
+
<!--
|
|
31
|
+
Anything specific to how this project writes: tone, banned phrases, a
|
|
32
|
+
tagline that must appear consistently, units/currency conventions, etc.
|
|
33
|
+
-->
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# GEO Playbook — {{product_name}}
|
|
2
|
+
|
|
3
|
+
Filled in from `geo-config.md` and `references/geo-methodology.md` in the
|
|
4
|
+
generative-seo skill. This file is the project-specific source of truth — the
|
|
5
|
+
skill's reference file has the general evidence; this one has what this project
|
|
6
|
+
has decided to do about it.
|
|
7
|
+
|
|
8
|
+
## Category / positioning
|
|
9
|
+
|
|
10
|
+
<!-- What category term is this project trying to own? What's the one-line
|
|
11
|
+
differentiator vs the obvious alternatives? -->
|
|
12
|
+
|
|
13
|
+
## Content rules specific to this project
|
|
14
|
+
|
|
15
|
+
<!-- Start from SKILL.md's non-negotiable rules; add anything specific here
|
|
16
|
+
(e.g. "always include a pricing comparison table", "never use the word X"). -->
|
|
17
|
+
|
|
18
|
+
## What's proven vs still a hypothesis
|
|
19
|
+
|
|
20
|
+
<!-- Track which tactics this project has actually validated (ranked, got
|
|
21
|
+
cited, drove signups) vs ones still being tried. Update after each `report`
|
|
22
|
+
or `citations` run. -->
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
# Social Distribution Queue
|
|
2
|
+
|
|
3
|
+
Drafts only — nothing here gets posted automatically. Review, edit into your own
|
|
4
|
+
voice, paste, then flip the status marker.
|
|
5
|
+
|
|
6
|
+
Status markers: `[ ] queued` → `[x] posted YYYY-MM-DD <URL>` or `[-] skipped`.
|
|
7
|
+
|
|
8
|
+
<!-- Append a new dated H2 per `social` run. Never overwrite prior entries. -->
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
# GEO Methodology Reference
|
|
2
|
+
|
|
3
|
+
The evidence behind the rules in SKILL.md, and the full technical checklist for
|
|
4
|
+
`audit` mode. Read this once per project before the first `audit` or `content`
|
|
5
|
+
run; the summary in SKILL.md is enough for later runs.
|
|
6
|
+
|
|
7
|
+
## Table of contents
|
|
8
|
+
|
|
9
|
+
1. [The evidence](#the-evidence)
|
|
10
|
+
2. [Technical checklist](#technical-checklist)
|
|
11
|
+
3. [Sitemap / robots by framework](#sitemap--robots-by-framework)
|
|
12
|
+
4. [JSON-LD schema types](#json-ld-schema-types)
|
|
13
|
+
5. [AI-crawler allowlist](#ai-crawler-allowlist)
|
|
14
|
+
|
|
15
|
+
---
|
|
16
|
+
|
|
17
|
+
## The evidence
|
|
18
|
+
|
|
19
|
+
**Answer-first placement.** Research on what generative engines (AI Overviews,
|
|
20
|
+
ChatGPT search, Perplexity) actually quote found citations skew heavily toward
|
|
21
|
+
early-page content — a large share of cited passages come from roughly the first
|
|
22
|
+
third of the page. Practical takeaway: don't bury the direct answer under a long
|
|
23
|
+
intro, definitions section, or history lesson. State it, then elaborate.
|
|
24
|
+
|
|
25
|
+
**Statistics and quotable lines.** Studies analyzing what content gets cited by
|
|
26
|
+
AI answer engines (Princeton's GEO paper; independent studies from SEO tooling
|
|
27
|
+
vendors) found that adding concrete statistics, direct quotes, and citations to
|
|
28
|
+
sources measurably increases the odds a passage gets pulled into an AI-generated
|
|
29
|
+
answer — reported lifts in the 30–40%+ range for visibility, depending on the
|
|
30
|
+
study and baseline. This is the single highest-leverage on-page lever available.
|
|
31
|
+
|
|
32
|
+
**Extractable structure.** AI engines assemble answers from passages, not whole
|
|
33
|
+
pages. Content that mirrors how people actually ask ("How do I…", "What is…",
|
|
34
|
+
"X vs Y") in H2/H3 headings, uses genuine Q&A blocks, comparison tables, and a
|
|
35
|
+
TL;DR/summary block gets extracted more cleanly than prose that requires reading
|
|
36
|
+
top-to-bottom to make sense.
|
|
37
|
+
|
|
38
|
+
**Self-contained passages.** Because retrieval is passage-level, a section that
|
|
39
|
+
depends on context from three paragraphs earlier ("as mentioned above...") reads
|
|
40
|
+
as incomplete when lifted alone — which is exactly how it will be consumed.
|
|
41
|
+
|
|
42
|
+
**Freshness signals.** Visible author, published date, and last-updated date are
|
|
43
|
+
both a trust signal to AI crawlers and a genuine correctness signal — stale
|
|
44
|
+
numbers get corrected by AI engines using other sources instead. Re-verify and
|
|
45
|
+
refresh anything older than about 6 months, especially anything with a number
|
|
46
|
+
in it.
|
|
47
|
+
|
|
48
|
+
**Structured Q&A + schema.** `FAQPage` JSON-LD gives engines an unambiguous,
|
|
49
|
+
pre-parsed question/answer pair to lift verbatim — lower effort for the engine
|
|
50
|
+
than extracting an answer from prose, which matters when the engine is choosing
|
|
51
|
+
between two similarly good sources.
|
|
52
|
+
|
|
53
|
+
**What has weak or no proven effect (don't over-invest):** `llms.txt` files and
|
|
54
|
+
generic schema markup are commonly recommended but have thin independent
|
|
55
|
+
evidence of directly causing AI-citation lift — treat them as cheap hygiene
|
|
56
|
+
(an hour of work, do it once) rather than a strategy. The actual strategy is the
|
|
57
|
+
content quality levers above, plus off-site signals (third-party mentions in
|
|
58
|
+
roundups/directories/forums/video) and fast technical indexing.
|
|
59
|
+
|
|
60
|
+
---
|
|
61
|
+
|
|
62
|
+
## Technical checklist
|
|
63
|
+
|
|
64
|
+
Run through all of these for `audit` mode; report failures with file:line.
|
|
65
|
+
|
|
66
|
+
1. **Sitemap** includes every indexable page with an honest `lastModified`;
|
|
67
|
+
excludes anything robots disallows; no auth-gated URLs. See framework map below.
|
|
68
|
+
2. **Robots** disallows app/API/auth routes; explicitly allows AI-answer-engine
|
|
69
|
+
bots (see allowlist below) unless the user has a specific reason to block
|
|
70
|
+
AI training/retrieval (rare — confirm before ever adding a disallow for these).
|
|
71
|
+
3. Every marketing/content page has: unique `title` (not duplicating a sitewide
|
|
72
|
+
template), unique `description` (~140–160 chars), a canonical URL, and
|
|
73
|
+
OG + Twitter/X card metadata.
|
|
74
|
+
4. JSON-LD present and valid — see schema-type table below.
|
|
75
|
+
5. `llms.txt` in the site root — a markdown index of key pages with one-line
|
|
76
|
+
descriptions. Low proven impact; still a cheap one-time hedge (see evidence
|
|
77
|
+
section — don't over-invest beyond the first pass).
|
|
78
|
+
6. All public content is server-rendered or otherwise present in the initial
|
|
79
|
+
HTML response — many AI crawlers don't execute JavaScript, so client-only
|
|
80
|
+
marketing copy is invisible to them.
|
|
81
|
+
7. **Live checks**: fetch `/robots.txt`, `/sitemap.xml` (or the framework's
|
|
82
|
+
equivalent), `/llms.txt`, and the homepage on the live domain — confirm they
|
|
83
|
+
match the repo and return 200; spot-check that sitemap URLs resolve.
|
|
84
|
+
8. Heading hygiene: exactly one H1 per page; H2s phrased as the questions the
|
|
85
|
+
page targets, where the page targets a specific query.
|
|
86
|
+
9. Internal linking: every content page links to its category/pillar page and
|
|
87
|
+
vice versa; pillar pages link out to their spokes.
|
|
88
|
+
10. Core Web Vitals sanity: no oversized unoptimized images (use the framework's
|
|
89
|
+
image component if it has one), no obvious layout shift from late-loading
|
|
90
|
+
content, no render-blocking resources that are trivially deferrable.
|
|
91
|
+
|
|
92
|
+
---
|
|
93
|
+
|
|
94
|
+
## Sitemap / robots by framework
|
|
95
|
+
|
|
96
|
+
Confirm the actual files in the repo before assuming — frameworks change these
|
|
97
|
+
mechanisms across versions.
|
|
98
|
+
|
|
99
|
+
| Framework | Sitemap | Robots | Metadata |
|
|
100
|
+
|---|---|---|---|
|
|
101
|
+
| Next.js (App Router) | `app/sitemap.ts` (dynamic) or `public/sitemap.xml` | `app/robots.ts` or `public/robots.txt` | `generateMetadata` / static `metadata` export per route; root `metadataBase` in root layout |
|
|
102
|
+
| Astro | `@astrojs/sitemap` integration (generates at build) or manual `public/sitemap.xml` | `public/robots.txt` | Per-page `<head>` in `.astro` files, or a shared `<SEO>` component |
|
|
103
|
+
| Remix / React Router | A resource route returning XML (e.g. `app/routes/sitemap[.]xml.tsx`) | A resource route or `public/robots.txt` | `meta` export per route |
|
|
104
|
+
| SvelteKit | `src/routes/sitemap.xml/+server.ts` | `static/robots.txt` | `<svelte:head>` per page |
|
|
105
|
+
| Plain static site | Hand-maintained or generated `sitemap.xml` at the root | `robots.txt` at the root | Per-HTML-file `<head>` tags |
|
|
106
|
+
| WordPress / Webflow / other CMS | Usually auto-generated by an SEO plugin (Yoast, RankMath) or the platform itself | Same — check the plugin/platform settings, don't hand-edit generated files | Plugin-managed fields per page/post |
|
|
107
|
+
|
|
108
|
+
If none of these match, ask the user rather than guessing — inventing a
|
|
109
|
+
mechanism that doesn't fit the framework produces code that won't build.
|
|
110
|
+
|
|
111
|
+
## JSON-LD schema types
|
|
112
|
+
|
|
113
|
+
| Page type | Schema | Notes |
|
|
114
|
+
|---|---|---|
|
|
115
|
+
| Every page (sitewide, once) | `Organization` | Name, logo, sameAs (social profiles) |
|
|
116
|
+
| Homepage / pricing (for a product) | `SoftwareApplication` + `Offer` | Only if the product genuinely is software with a price; don't force this onto a services business |
|
|
117
|
+
| Any page with a real FAQ | `FAQPage` | Must match the visible on-page Q&A exactly — don't add schema for content that isn't rendered |
|
|
118
|
+
| Blog / article content | `Article` + `author` + `datePublished` + `dateModified` | Keep `dateModified` in sync with the visible "last updated" date |
|
|
119
|
+
| Blog / article content | `BreadcrumbList` | Only where there's a real breadcrumb trail |
|
|
120
|
+
| Ranked list/roundup content | `ItemList` | For "best X" style pages |
|
|
121
|
+
|
|
122
|
+
Sanitize any inline JSON-LD script against injection if the data includes
|
|
123
|
+
user-controlled or dynamic strings (e.g. `JSON.stringify(data).replace(/</g,
|
|
124
|
+
"\\u003c")` in a Node/JS context) — this is standard defensive practice for
|
|
125
|
+
inlining JSON into HTML, not framework-specific.
|
|
126
|
+
|
|
127
|
+
## AI-crawler allowlist
|
|
128
|
+
|
|
129
|
+
Bot user-agents to explicitly allow in `robots.txt` (or the framework's robots
|
|
130
|
+
mechanism) so AI answer engines can retrieve and potentially cite the content —
|
|
131
|
+
disallowing these is usually the opposite of what a project pursuing AI-search
|
|
132
|
+
visibility wants:
|
|
133
|
+
|
|
134
|
+
- `OAI-SearchBot`, `ChatGPT-User`, `GPTBot` (OpenAI)
|
|
135
|
+
- `ClaudeBot`, `Claude-SearchBot`, `Claude-User` (Anthropic)
|
|
136
|
+
- `PerplexityBot`, `Perplexity-User` (Perplexity)
|
|
137
|
+
- `Bingbot`, `Google-Extended` (Microsoft/Google AI training + retrieval)
|
|
138
|
+
- `CCBot` (Common Crawl — feeds many downstream AI training sets)
|
|
139
|
+
|
|
140
|
+
If the user has an explicit reason to keep content out of AI training data
|
|
141
|
+
(e.g. a paywalled or licensed-content business model), confirm before adding
|
|
142
|
+
these — the default recommendation is "allow all" for anyone wanting AI-search
|
|
143
|
+
visibility, but that's not universal.
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: spec-checkpoint
|
|
3
|
+
description: >
|
|
4
|
+
Create a comprehensive checkpoint commit with detailed analysis of all changes. Use this skill
|
|
5
|
+
when the user says "checkpoint", "commit everything", "save my progress", "create a commit",
|
|
6
|
+
or wants to stage and commit all current changes with a well-crafted message. Also use when
|
|
7
|
+
the user says "/spec-checkpoint" (or their host's equivalent invocation syntax) or asks to
|
|
8
|
+
snapshot current work. This skill stages all changes and creates a descriptive commit — it
|
|
9
|
+
does not push.
|
|
10
|
+
license: MIT
|
|
11
|
+
---
|
|
12
|
+
|
|
13
|
+
# Checkpoint Commit
|
|
14
|
+
|
|
15
|
+
Create a checkpoint commit that captures all current changes — but only after the code passes lint, type check, and build.
|
|
16
|
+
|
|
17
|
+
## Project config (read first)
|
|
18
|
+
|
|
19
|
+
Load `.spec-driven.yml`: walk up from the current directory to the home folder, and the first one
|
|
20
|
+
found wins (a `multi-repo` config only applies inside the repos it lists). Its values beat anything
|
|
21
|
+
you would detect or assume. This skill uses `commands` (lint/typecheck/test/build), `git.commit_style`, and `layout`/`repos`.
|
|
22
|
+
|
|
23
|
+
**Multi-repo:** run this in every listed repo that has changes, making one commit per repo with the same subject. **Monorepo:** run the checks for the packages that changed, or the root commands if that's how the repo works.
|
|
24
|
+
|
|
25
|
+
**No config?** If the `spec-setup` skill is available, run it first, then continue here. If it
|
|
26
|
+
isn't, detect what this skill needs from the repo, ask about anything ambiguous, and offer to save
|
|
27
|
+
the answers to `.spec-driven.yml` (keys: `layout`, `repos`, `tracker`, `git`, `commands`,
|
|
28
|
+
`specs_dir`).
|
|
29
|
+
|
|
30
|
+
## Instructions
|
|
31
|
+
|
|
32
|
+
### Step 1: Analyze Changes
|
|
33
|
+
|
|
34
|
+
Run these commands to understand the full picture:
|
|
35
|
+
|
|
36
|
+
1. `git status` — see all tracked and untracked files
|
|
37
|
+
2. `git diff` — see detailed changes in tracked files
|
|
38
|
+
3. `git diff --cached` — see already-staged changes
|
|
39
|
+
4. `git log -5 --oneline` — understand this repo's commit message style
|
|
40
|
+
|
|
41
|
+
### Step 2: Quality Checks
|
|
42
|
+
|
|
43
|
+
Use `commands` from `.spec-driven.yml`. For any that are missing, find the repo's own lint, typecheck, test, and build commands — `package.json` scripts (with the
|
|
44
|
+
repo's package manager), `Makefile`, `pyproject.toml`, `Cargo.toml`, CI config, or `CLAUDE.md`/
|
|
45
|
+
`AGENTS.md`. Run each one the repo has; skip (and say so) any it doesn't. If any fail, fix the
|
|
46
|
+
issues before proceeding — do not skip or ignore failures.
|
|
47
|
+
|
|
48
|
+
Iterate until every check passes cleanly. Only then move to the next step.
|
|
49
|
+
|
|
50
|
+
### Step 3: Stage Everything
|
|
51
|
+
|
|
52
|
+
Stage all changes — tracked modifications, deletions, and new untracked files:
|
|
53
|
+
|
|
54
|
+
```bash
|
|
55
|
+
git add -A
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
Then review `git status` again. If anything staged looks like it could hold secrets —
|
|
59
|
+
`.env*`, `*.pem`, `*_rsa`, `credentials.json`, `secrets.*`, or an unfamiliar filename that might
|
|
60
|
+
contain an API key — unstage it (`git restore --staged <file>`) and tell the user what was
|
|
61
|
+
excluded and why, rather than committing it silently. Don't rely on the filename alone for
|
|
62
|
+
anything you don't recognize; skim its diff if you're unsure.
|
|
63
|
+
|
|
64
|
+
### Step 4: Craft the Commit Message
|
|
65
|
+
|
|
66
|
+
Write a commit message in the config's `git.commit_style` (`conventional` → `feat: …`, `ticket` → `STP-123: …` using the ticket ID from the branch name, `freeform`). Without config, follow the project's existing conventions (observed from `git log`). Structure:
|
|
67
|
+
|
|
68
|
+
- **First line**: clear, concise summary in imperative mood (50-72 chars)
|
|
69
|
+
- Use conventional commit prefixes where the project uses them: `feat:`, `fix:`, `refactor:`, `docs:`, `chore:`, etc.
|
|
70
|
+
- **Body** (separated by blank line): a short TL;DR of the changes — 1-3 sentences max. No bullet lists, no file-by-file breakdowns, no lengthy explanations.
|
|
71
|
+
- **Footer**: co-author attribution, naming whichever agent/model is actually running this
|
|
72
|
+
skill — never hardcode a specific vendor or model name, since this skill runs under many
|
|
73
|
+
different hosts
|
|
74
|
+
|
|
75
|
+
### Step 5: Commit
|
|
76
|
+
|
|
77
|
+
Create the commit using a heredoc for proper formatting:
|
|
78
|
+
|
|
79
|
+
```bash
|
|
80
|
+
git commit -m "$(cat <<'EOF'
|
|
81
|
+
{first line}
|
|
82
|
+
|
|
83
|
+
{tldr}
|
|
84
|
+
|
|
85
|
+
Co-Authored-By: {agent name} <noreply@example.com>
|
|
86
|
+
EOF
|
|
87
|
+
)"
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
Fill in `{agent name}` with whatever the current agent/model actually identifies as (e.g. "Claude", "Codex", "Cursor Agent") — if your host has no clean way to identify itself, omit the footer entirely rather than guessing.
|
|
91
|
+
|
|
92
|
+
### Step 6: Report
|
|
93
|
+
|
|
94
|
+
Display:
|
|
95
|
+
- The commit hash and message summary
|
|
96
|
+
- Files changed count
|
|
97
|
+
- Insertions/deletions summary
|
|
98
|
+
|
|
99
|
+
## Important
|
|
100
|
+
|
|
101
|
+
- Stage and commit everything except files that look like secrets or credentials (see Step 3) — check contents, not just filenames, before assuming something is safe to commit
|
|
102
|
+
- If the repo has no git history, run `git init` first
|
|
103
|
+
- All quality checks (lint, type-check, build) MUST pass before committing — fix issues, don't skip them
|
|
104
|
+
- Keep the commit body short — a TL;DR, not an essay
|
|
105
|
+
- Follow the project's existing commit conventions (check the log first)
|
|
106
|
+
- Do not push — only commit locally
|