@ahmed-g-gad/apothem 0.1.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.
Files changed (674) hide show
  1. package/CHANGELOG.md +60 -0
  2. package/LICENSE +21 -0
  3. package/LICENSES/MIT.txt +18 -0
  4. package/LICENSES/PSF-2.0.txt +47 -0
  5. package/README.md +549 -0
  6. package/bin/README.md +37 -0
  7. package/bin/apothem.mjs +78 -0
  8. package/package.json +75 -0
  9. package/pyproject.toml +347 -0
  10. package/src/apothem/README.md +52 -0
  11. package/src/apothem/__init__.py +66 -0
  12. package/src/apothem/__main__.py +28 -0
  13. package/src/apothem/_vendor/.keep +0 -0
  14. package/src/apothem/_vendor/__init__.py +25 -0
  15. package/src/apothem/_vendor/attr/__init__.py +104 -0
  16. package/src/apothem/_vendor/attr/__init__.pyi +389 -0
  17. package/src/apothem/_vendor/attr/_cmp.py +160 -0
  18. package/src/apothem/_vendor/attr/_cmp.pyi +13 -0
  19. package/src/apothem/_vendor/attr/_compat.py +99 -0
  20. package/src/apothem/_vendor/attr/_config.py +31 -0
  21. package/src/apothem/_vendor/attr/_funcs.py +497 -0
  22. package/src/apothem/_vendor/attr/_make.py +3406 -0
  23. package/src/apothem/_vendor/attr/_next_gen.py +674 -0
  24. package/src/apothem/_vendor/attr/_typing_compat.pyi +15 -0
  25. package/src/apothem/_vendor/attr/_version_info.py +89 -0
  26. package/src/apothem/_vendor/attr/_version_info.pyi +9 -0
  27. package/src/apothem/_vendor/attr/converters.py +162 -0
  28. package/src/apothem/_vendor/attr/converters.pyi +19 -0
  29. package/src/apothem/_vendor/attr/exceptions.py +95 -0
  30. package/src/apothem/_vendor/attr/exceptions.pyi +17 -0
  31. package/src/apothem/_vendor/attr/filters.py +72 -0
  32. package/src/apothem/_vendor/attr/filters.pyi +6 -0
  33. package/src/apothem/_vendor/attr/py.typed +0 -0
  34. package/src/apothem/_vendor/attr/setters.py +79 -0
  35. package/src/apothem/_vendor/attr/setters.pyi +20 -0
  36. package/src/apothem/_vendor/attr/validators.py +750 -0
  37. package/src/apothem/_vendor/attr/validators.pyi +140 -0
  38. package/src/apothem/_vendor/attr.LICENSE +21 -0
  39. package/src/apothem/_vendor/attrs/__init__.py +72 -0
  40. package/src/apothem/_vendor/attrs/__init__.pyi +314 -0
  41. package/src/apothem/_vendor/attrs/converters.py +3 -0
  42. package/src/apothem/_vendor/attrs/exceptions.py +3 -0
  43. package/src/apothem/_vendor/attrs/filters.py +3 -0
  44. package/src/apothem/_vendor/attrs/py.typed +0 -0
  45. package/src/apothem/_vendor/attrs/setters.py +3 -0
  46. package/src/apothem/_vendor/attrs/validators.py +3 -0
  47. package/src/apothem/_vendor/attrs.LICENSE +21 -0
  48. package/src/apothem/_vendor/jsonschema/__init__.py +120 -0
  49. package/src/apothem/_vendor/jsonschema/__main__.py +6 -0
  50. package/src/apothem/_vendor/jsonschema/_format.py +546 -0
  51. package/src/apothem/_vendor/jsonschema/_keywords.py +449 -0
  52. package/src/apothem/_vendor/jsonschema/_legacy_keywords.py +449 -0
  53. package/src/apothem/_vendor/jsonschema/_types.py +204 -0
  54. package/src/apothem/_vendor/jsonschema/_typing.py +29 -0
  55. package/src/apothem/_vendor/jsonschema/_utils.py +355 -0
  56. package/src/apothem/_vendor/jsonschema/benchmarks/__init__.py +5 -0
  57. package/src/apothem/_vendor/jsonschema/benchmarks/const_vs_enum.py +30 -0
  58. package/src/apothem/_vendor/jsonschema/benchmarks/contains.py +28 -0
  59. package/src/apothem/_vendor/jsonschema/benchmarks/import_benchmark.py +31 -0
  60. package/src/apothem/_vendor/jsonschema/benchmarks/issue232/issue.json +2653 -0
  61. package/src/apothem/_vendor/jsonschema/benchmarks/issue232.py +25 -0
  62. package/src/apothem/_vendor/jsonschema/benchmarks/json_schema_test_suite.py +12 -0
  63. package/src/apothem/_vendor/jsonschema/benchmarks/nested_schemas.py +56 -0
  64. package/src/apothem/_vendor/jsonschema/benchmarks/subcomponents.py +42 -0
  65. package/src/apothem/_vendor/jsonschema/benchmarks/unused_registry.py +35 -0
  66. package/src/apothem/_vendor/jsonschema/benchmarks/useless_applicator_schemas.py +106 -0
  67. package/src/apothem/_vendor/jsonschema/benchmarks/useless_keywords.py +32 -0
  68. package/src/apothem/_vendor/jsonschema/benchmarks/validator_creation.py +14 -0
  69. package/src/apothem/_vendor/jsonschema/cli.py +292 -0
  70. package/src/apothem/_vendor/jsonschema/exceptions.py +490 -0
  71. package/src/apothem/_vendor/jsonschema/protocols.py +230 -0
  72. package/src/apothem/_vendor/jsonschema/validators.py +1410 -0
  73. package/src/apothem/_vendor/jsonschema.LICENSE +19 -0
  74. package/src/apothem/_vendor/jsonschema_specifications/__init__.py +12 -0
  75. package/src/apothem/_vendor/jsonschema_specifications/_core.py +38 -0
  76. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft201909/metaschema.json +42 -0
  77. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft201909/vocabularies/applicator +56 -0
  78. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft201909/vocabularies/content +17 -0
  79. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft201909/vocabularies/core +57 -0
  80. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft201909/vocabularies/format +14 -0
  81. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft201909/vocabularies/meta-data +37 -0
  82. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft201909/vocabularies/validation +98 -0
  83. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/metaschema.json +58 -0
  84. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/applicator +48 -0
  85. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/content +17 -0
  86. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/core +51 -0
  87. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/format-annotation +14 -0
  88. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/format-assertion +14 -0
  89. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/meta-data +37 -0
  90. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/unevaluated +15 -0
  91. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft202012/vocabularies/validation +98 -0
  92. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft3/metaschema.json +172 -0
  93. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft4/metaschema.json +149 -0
  94. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft6/metaschema.json +153 -0
  95. package/src/apothem/_vendor/jsonschema_specifications/schemas/draft7/metaschema.json +166 -0
  96. package/src/apothem/_vendor/jsonschema_specifications.LICENSE +19 -0
  97. package/src/apothem/_vendor/referencing/__init__.py +7 -0
  98. package/src/apothem/_vendor/referencing/_attrs.py +31 -0
  99. package/src/apothem/_vendor/referencing/_attrs.pyi +21 -0
  100. package/src/apothem/_vendor/referencing/_core.py +739 -0
  101. package/src/apothem/_vendor/referencing/exceptions.py +165 -0
  102. package/src/apothem/_vendor/referencing/jsonschema.py +642 -0
  103. package/src/apothem/_vendor/referencing/py.typed +0 -0
  104. package/src/apothem/_vendor/referencing/retrieval.py +94 -0
  105. package/src/apothem/_vendor/referencing/typing.py +61 -0
  106. package/src/apothem/_vendor/referencing.LICENSE +19 -0
  107. package/src/apothem/_vendor/rpds/__init__.py +251 -0
  108. package/src/apothem/_vendor/typing_extensions.LICENSE +279 -0
  109. package/src/apothem/_vendor/typing_extensions.py +4317 -0
  110. package/src/apothem/_vendor/vendor.txt +22 -0
  111. package/src/apothem/_vendor/yaml/__init__.py +389 -0
  112. package/src/apothem/_vendor/yaml/composer.py +138 -0
  113. package/src/apothem/_vendor/yaml/constructor.py +748 -0
  114. package/src/apothem/_vendor/yaml/cyaml.py +100 -0
  115. package/src/apothem/_vendor/yaml/dumper.py +61 -0
  116. package/src/apothem/_vendor/yaml/emitter.py +1137 -0
  117. package/src/apothem/_vendor/yaml/error.py +74 -0
  118. package/src/apothem/_vendor/yaml/events.py +85 -0
  119. package/src/apothem/_vendor/yaml/loader.py +63 -0
  120. package/src/apothem/_vendor/yaml/nodes.py +48 -0
  121. package/src/apothem/_vendor/yaml/parser.py +588 -0
  122. package/src/apothem/_vendor/yaml/reader.py +185 -0
  123. package/src/apothem/_vendor/yaml/representer.py +388 -0
  124. package/src/apothem/_vendor/yaml/resolver.py +226 -0
  125. package/src/apothem/_vendor/yaml/scanner.py +1435 -0
  126. package/src/apothem/_vendor/yaml/serializer.py +110 -0
  127. package/src/apothem/_vendor/yaml/tokens.py +103 -0
  128. package/src/apothem/_vendor/yaml.LICENSE +20 -0
  129. package/src/apothem/agents/README.md +60 -0
  130. package/src/apothem/agents/codebase-explorer.md +91 -0
  131. package/src/apothem/agents/convention-auditor.md +93 -0
  132. package/src/apothem/agents/dependency-auditor.md +97 -0
  133. package/src/apothem/agents/fact-checker.md +84 -0
  134. package/src/apothem/agents/mcp-builder.md +86 -0
  135. package/src/apothem/agents/memory-auditor.md +93 -0
  136. package/src/apothem/agents/prompt-evaluator.md +87 -0
  137. package/src/apothem/agents/quality-gate.md +103 -0
  138. package/src/apothem/agents/refactor-surgeon.md +74 -0
  139. package/src/apothem/agents/research-scout.md +73 -0
  140. package/src/apothem/agents/security-scanner.md +83 -0
  141. package/src/apothem/agents/test-runner.md +84 -0
  142. package/src/apothem/audit/README.md +73 -0
  143. package/src/apothem/audit/_scan_lib.py +182 -0
  144. package/src/apothem/audit/analyze_graph.py +260 -0
  145. package/src/apothem/audit/build_capability_graph.py +607 -0
  146. package/src/apothem/audit/build_inventory.py +657 -0
  147. package/src/apothem/audit/build_plans_provenance.py +997 -0
  148. package/src/apothem/audit/check_links.py +389 -0
  149. package/src/apothem/audit/classify_artifacts.py +381 -0
  150. package/src/apothem/audit/deprecated-tokens.txt +10 -0
  151. package/src/apothem/audit/execute_plans_migration.py +491 -0
  152. package/src/apothem/audit/known-projects.txt +15 -0
  153. package/src/apothem/audit/render_capability_index.py +467 -0
  154. package/src/apothem/audit/render_inventory.py +405 -0
  155. package/src/apothem/audit/scan_ai_surfaces.py +1125 -0
  156. package/src/apothem/audit/scan_ai_surfaces_coarse.py +261 -0
  157. package/src/apothem/audit/scan_drift_features.py +143 -0
  158. package/src/apothem/audit/scan_frontmatter.py +293 -0
  159. package/src/apothem/audit/scan_header_coverage.py +1134 -0
  160. package/src/apothem/audit/scan_plan_leakage.py +540 -0
  161. package/src/apothem/audit/scan_plans_discipline.py +188 -0
  162. package/src/apothem/audit/scan_secrets_pii.py +245 -0
  163. package/src/apothem/audit/scan_stale_tokens.py +296 -0
  164. package/src/apothem/audit/synthesize_drift.py +205 -0
  165. package/src/apothem/benchmarks/README.md +33 -0
  166. package/src/apothem/benchmarks/__init__.py +3 -0
  167. package/src/apothem/benchmarks/bench_agents.py +63 -0
  168. package/src/apothem/benchmarks/bench_hooks.py +93 -0
  169. package/src/apothem/benchmarks/bench_install.py +58 -0
  170. package/src/apothem/benchmarks/bench_tests.py +93 -0
  171. package/src/apothem/benchmarks/bench_validate_ecosystem.py +84 -0
  172. package/src/apothem/cli/README.md +33 -0
  173. package/src/apothem/cli/__init__.py +229 -0
  174. package/src/apothem/cli/_cmd_completion.py +88 -0
  175. package/src/apothem/cli/_cmd_diff.py +181 -0
  176. package/src/apothem/cli/_cmd_doctor.py +143 -0
  177. package/src/apothem/cli/_cmd_harnesses.py +167 -0
  178. package/src/apothem/cli/_cmd_install.py +327 -0
  179. package/src/apothem/cli/_cmd_migrate_workspace.py +143 -0
  180. package/src/apothem/cli/_cmd_profile.py +341 -0
  181. package/src/apothem/cli/_cmd_status.py +180 -0
  182. package/src/apothem/cli/_cmd_uninstall.py +215 -0
  183. package/src/apothem/cli/_cmd_update.py +397 -0
  184. package/src/apothem/cli/_cmd_verify.py +194 -0
  185. package/src/apothem/cli/_common_flags.py +90 -0
  186. package/src/apothem/cli/_epilogs.py +296 -0
  187. package/src/apothem/cli/_helpers.py +857 -0
  188. package/src/apothem/cli/_json_formatter.py +21 -0
  189. package/src/apothem/cli/_materialize.py +376 -0
  190. package/src/apothem/cli/completions/apothem.bash +30 -0
  191. package/src/apothem/cli/completions/apothem.fish +19 -0
  192. package/src/apothem/cli/completions/apothem.ps1 +27 -0
  193. package/src/apothem/cli/completions/apothem.zsh +42 -0
  194. package/src/apothem/cli/reference_export.py +126 -0
  195. package/src/apothem/commands/README.md +125 -0
  196. package/src/apothem/commands/a11y-audit.md +203 -0
  197. package/src/apothem/commands/architecture-review.md +194 -0
  198. package/src/apothem/commands/audit.md +165 -0
  199. package/src/apothem/commands/code-audit.md +218 -0
  200. package/src/apothem/commands/code-review.md +193 -0
  201. package/src/apothem/commands/dependency-audit.md +209 -0
  202. package/src/apothem/commands/docs-review.md +199 -0
  203. package/src/apothem/commands/elevate.md +285 -0
  204. package/src/apothem/commands/eval.md +149 -0
  205. package/src/apothem/commands/fortress.md +172 -0
  206. package/src/apothem/commands/freshify.md +168 -0
  207. package/src/apothem/commands/github-deploy-fresh.md +178 -0
  208. package/src/apothem/commands/github-deploy-next.md +167 -0
  209. package/src/apothem/commands/perf-audit.md +198 -0
  210. package/src/apothem/commands/plan-amend.md +104 -0
  211. package/src/apothem/commands/plan-audit.md +127 -0
  212. package/src/apothem/commands/plan-design.md +257 -0
  213. package/src/apothem/commands/plan-execute.md +495 -0
  214. package/src/apothem/commands/plan-generate.md +351 -0
  215. package/src/apothem/commands/plan-review.md +555 -0
  216. package/src/apothem/commands/plan-spec.md +359 -0
  217. package/src/apothem/commands/plan-status.md +222 -0
  218. package/src/apothem/commands/plan.md +173 -0
  219. package/src/apothem/commands/projectify.md +142 -0
  220. package/src/apothem/commands/release-readiness.md +142 -0
  221. package/src/apothem/commands/research-analysis.md +241 -0
  222. package/src/apothem/commands/research-design.md +231 -0
  223. package/src/apothem/commands/research-disseminate.md +225 -0
  224. package/src/apothem/commands/research-experiment.md +232 -0
  225. package/src/apothem/commands/research-ideate.md +213 -0
  226. package/src/apothem/commands/research-paper.md +252 -0
  227. package/src/apothem/commands/research-proposal.md +220 -0
  228. package/src/apothem/commands/research-publish.md +255 -0
  229. package/src/apothem/commands/research-review.md +251 -0
  230. package/src/apothem/commands/research-sources.md +266 -0
  231. package/src/apothem/commands/research-spec.md +255 -0
  232. package/src/apothem/commands/research-synthesis.md +233 -0
  233. package/src/apothem/commands/research-theory.md +218 -0
  234. package/src/apothem/commands/research.md +181 -0
  235. package/src/apothem/commands/security-audit.md +196 -0
  236. package/src/apothem/commands/supply-chain-audit.md +192 -0
  237. package/src/apothem/commands/test-suite.md +146 -0
  238. package/src/apothem/commands/threat-model-audit.md +199 -0
  239. package/src/apothem/commands/ux-review.md +202 -0
  240. package/src/apothem/commands/workflow.md +162 -0
  241. package/src/apothem/conformity/README.md +173 -0
  242. package/src/apothem/conformity/__init__.py +1 -0
  243. package/src/apothem/conformity/_grep_base.py +93 -0
  244. package/src/apothem/conformity/agent_capability_grep.py +306 -0
  245. package/src/apothem/conformity/agents_md_coverage_grep.py +382 -0
  246. package/src/apothem/conformity/agnosticism_grep.py +311 -0
  247. package/src/apothem/conformity/always_on_budget_grep.py +318 -0
  248. package/src/apothem/conformity/bare_except_grep.py +115 -0
  249. package/src/apothem/conformity/binding_reciprocity_grep.py +151 -0
  250. package/src/apothem/conformity/brand_mark_grep.py +272 -0
  251. package/src/apothem/conformity/commented_out_code_grep.py +176 -0
  252. package/src/apothem/conformity/completion_claim_grep.py +169 -0
  253. package/src/apothem/conformity/conventional_commit_grep.py +319 -0
  254. package/src/apothem/conformity/copilot_instructions_presence_grep.py +324 -0
  255. package/src/apothem/conformity/cross_platform_matrix_grep.py +297 -0
  256. package/src/apothem/conformity/determinism_grep.py +306 -0
  257. package/src/apothem/conformity/diagram_staleness_grep.py +154 -0
  258. package/src/apothem/conformity/dynamism_grep.py +284 -0
  259. package/src/apothem/conformity/editorconfig_presence_grep.py +281 -0
  260. package/src/apothem/conformity/file_header_grep.py +502 -0
  261. package/src/apothem/conformity/freshness_token_grep.py +233 -0
  262. package/src/apothem/conformity/frontmatter_grep.py +274 -0
  263. package/src/apothem/conformity/frontmatter_value_grep.py +386 -0
  264. package/src/apothem/conformity/gate.py +1386 -0
  265. package/src/apothem/conformity/gitattributes_presence_grep.py +238 -0
  266. package/src/apothem/conformity/harden_runner_grep.py +320 -0
  267. package/src/apothem/conformity/hedging_grep.py +129 -0
  268. package/src/apothem/conformity/license_author_consistency_grep.py +204 -0
  269. package/src/apothem/conformity/link_check.py +327 -0
  270. package/src/apothem/conformity/magic_number_grep.py +182 -0
  271. package/src/apothem/conformity/multi_surface_coherence_grep.py +620 -0
  272. package/src/apothem/conformity/naming_grep.py +224 -0
  273. package/src/apothem/conformity/no_global_plans_grep.py +339 -0
  274. package/src/apothem/conformity/no_toplevel_docs_grep.py +120 -0
  275. package/src/apothem/conformity/oidc_trusted_publishing_grep.py +291 -0
  276. package/src/apothem/conformity/option_annotation_grep.py +352 -0
  277. package/src/apothem/conformity/orphan_output_grep.py +206 -0
  278. package/src/apothem/conformity/permissions_minimum_scope_grep.py +299 -0
  279. package/src/apothem/conformity/plain_language_grep.py +559 -0
  280. package/src/apothem/conformity/plan_next_step_consistency_grep.py +450 -0
  281. package/src/apothem/conformity/plan_suite_structure_grep.py +534 -0
  282. package/src/apothem/conformity/plans_discipline_language_grep.py +245 -0
  283. package/src/apothem/conformity/production_ready_pr_grep.py +200 -0
  284. package/src/apothem/conformity/recommend_next_step_grep.py +250 -0
  285. package/src/apothem/conformity/redundancy_grep.py +401 -0
  286. package/src/apothem/conformity/reference_token_grep.py +230 -0
  287. package/src/apothem/conformity/registry_capability_consistency_grep.py +368 -0
  288. package/src/apothem/conformity/secret_leak_grep.py +193 -0
  289. package/src/apothem/conformity/semver_stability_grep.py +358 -0
  290. package/src/apothem/conformity/smoke_install_grep.py +194 -0
  291. package/src/apothem/conformity/static_version_grep.py +284 -0
  292. package/src/apothem/conformity/token_efficiency_grep.py +185 -0
  293. package/src/apothem/conformity/unpinned_action_grep.py +115 -0
  294. package/src/apothem/conformity/user_confirm_grep.py +74 -0
  295. package/src/apothem/conformity/workflow_concurrency_grep.py +283 -0
  296. package/src/apothem/harnesses/README.md +63 -0
  297. package/src/apothem/harnesses/__init__.py +16 -0
  298. package/src/apothem/harnesses/_shared/README.md +36 -0
  299. package/src/apothem/harnesses/_shared/__init__.py +12 -0
  300. package/src/apothem/harnesses/_shared/install_driver.py +281 -0
  301. package/src/apothem/harnesses/_shared/install_driver_apply.py +612 -0
  302. package/src/apothem/harnesses/_shared/install_driver_backup.py +535 -0
  303. package/src/apothem/harnesses/_shared/install_driver_converters.py +310 -0
  304. package/src/apothem/harnesses/_shared/install_driver_lifecycle.py +495 -0
  305. package/src/apothem/harnesses/_shared/install_driver_materialize.py +675 -0
  306. package/src/apothem/harnesses/_shared/install_driver_merge.py +656 -0
  307. package/src/apothem/harnesses/_shared/install_driver_pathsafety.py +137 -0
  308. package/src/apothem/harnesses/_shared/install_driver_planvalidation.py +240 -0
  309. package/src/apothem/harnesses/_shared/install_driver_removal.py +366 -0
  310. package/src/apothem/harnesses/_shared/install_driver_treeops.py +248 -0
  311. package/src/apothem/harnesses/_shared/install_driver_types.py +330 -0
  312. package/src/apothem/harnesses/_shared/wrapper_factories.py +448 -0
  313. package/src/apothem/harnesses/antigravity/STANDARD-CONVENTION-PIN.md +91 -0
  314. package/src/apothem/harnesses/antigravity/__init__.py +70 -0
  315. package/src/apothem/harnesses/antigravity/capabilities.yml +40 -0
  316. package/src/apothem/harnesses/antigravity/install.py +63 -0
  317. package/src/apothem/harnesses/antigravity/templates/GEMINI.md +40 -0
  318. package/src/apothem/harnesses/antigravity/templates/plugin.json +5 -0
  319. package/src/apothem/harnesses/antigravity/uninstall.py +22 -0
  320. package/src/apothem/harnesses/antigravity/update.py +10 -0
  321. package/src/apothem/harnesses/antigravity/verify.py +11 -0
  322. package/src/apothem/harnesses/claude_code/STANDARD-CONVENTION-PIN.md +65 -0
  323. package/src/apothem/harnesses/claude_code/__init__.py +107 -0
  324. package/src/apothem/harnesses/claude_code/capabilities.yml +42 -0
  325. package/src/apothem/harnesses/claude_code/install.py +147 -0
  326. package/src/apothem/harnesses/claude_code/templates/settings.json +351 -0
  327. package/src/apothem/harnesses/claude_code/uninstall.py +23 -0
  328. package/src/apothem/harnesses/claude_code/update.py +10 -0
  329. package/src/apothem/harnesses/claude_code/verify.py +11 -0
  330. package/src/apothem/harnesses/codebuddy/STANDARD-CONVENTION-PIN.md +74 -0
  331. package/src/apothem/harnesses/codebuddy/__init__.py +49 -0
  332. package/src/apothem/harnesses/codebuddy/capabilities.yml +34 -0
  333. package/src/apothem/harnesses/codebuddy/install.py +40 -0
  334. package/src/apothem/harnesses/codebuddy/templates/apothem-rules.md +37 -0
  335. package/src/apothem/harnesses/codebuddy/uninstall.py +25 -0
  336. package/src/apothem/harnesses/codebuddy/update.py +10 -0
  337. package/src/apothem/harnesses/codebuddy/verify.py +11 -0
  338. package/src/apothem/harnesses/codex/STANDARD-CONVENTION-PIN.md +79 -0
  339. package/src/apothem/harnesses/codex/__init__.py +72 -0
  340. package/src/apothem/harnesses/codex/capabilities.yml +40 -0
  341. package/src/apothem/harnesses/codex/install.py +69 -0
  342. package/src/apothem/harnesses/codex/templates/AGENTS.md +40 -0
  343. package/src/apothem/harnesses/codex/templates/hooks.json +127 -0
  344. package/src/apothem/harnesses/codex/uninstall.py +23 -0
  345. package/src/apothem/harnesses/codex/update.py +10 -0
  346. package/src/apothem/harnesses/codex/verify.py +11 -0
  347. package/src/apothem/harnesses/cursor/STANDARD-CONVENTION-PIN.md +79 -0
  348. package/src/apothem/harnesses/cursor/__init__.py +48 -0
  349. package/src/apothem/harnesses/cursor/capabilities.yml +42 -0
  350. package/src/apothem/harnesses/cursor/install.py +38 -0
  351. package/src/apothem/harnesses/cursor/templates/apothem-rules.mdc +40 -0
  352. package/src/apothem/harnesses/cursor/uninstall.py +25 -0
  353. package/src/apothem/harnesses/cursor/update.py +10 -0
  354. package/src/apothem/harnesses/cursor/verify.py +11 -0
  355. package/src/apothem/harnesses/gemini_cli/STANDARD-CONVENTION-PIN.md +102 -0
  356. package/src/apothem/harnesses/gemini_cli/__init__.py +52 -0
  357. package/src/apothem/harnesses/gemini_cli/capabilities.yml +43 -0
  358. package/src/apothem/harnesses/gemini_cli/install.py +43 -0
  359. package/src/apothem/harnesses/gemini_cli/templates/GEMINI.md +38 -0
  360. package/src/apothem/harnesses/gemini_cli/uninstall.py +25 -0
  361. package/src/apothem/harnesses/gemini_cli/update.py +10 -0
  362. package/src/apothem/harnesses/gemini_cli/verify.py +11 -0
  363. package/src/apothem/harnesses/github_copilot/STANDARD-CONVENTION-PIN.md +84 -0
  364. package/src/apothem/harnesses/github_copilot/__init__.py +47 -0
  365. package/src/apothem/harnesses/github_copilot/capabilities.yml +42 -0
  366. package/src/apothem/harnesses/github_copilot/install.py +40 -0
  367. package/src/apothem/harnesses/github_copilot/templates/copilot-instructions.md +33 -0
  368. package/src/apothem/harnesses/github_copilot/uninstall.py +25 -0
  369. package/src/apothem/harnesses/github_copilot/update.py +10 -0
  370. package/src/apothem/harnesses/github_copilot/verify.py +11 -0
  371. package/src/apothem/harnesses/glm/STANDARD-CONVENTION-PIN.md +77 -0
  372. package/src/apothem/harnesses/glm/__init__.py +56 -0
  373. package/src/apothem/harnesses/glm/capabilities.yml +33 -0
  374. package/src/apothem/harnesses/glm/install.py +45 -0
  375. package/src/apothem/harnesses/glm/templates/glm.toml +58 -0
  376. package/src/apothem/harnesses/glm/uninstall.py +25 -0
  377. package/src/apothem/harnesses/glm/update.py +10 -0
  378. package/src/apothem/harnesses/glm/verify.py +11 -0
  379. package/src/apothem/harnesses/hermes/STANDARD-CONVENTION-PIN.md +57 -0
  380. package/src/apothem/harnesses/hermes/__init__.py +33 -0
  381. package/src/apothem/harnesses/hermes/capabilities.yml +36 -0
  382. package/src/apothem/harnesses/hermes/install.py +17 -0
  383. package/src/apothem/harnesses/hermes/materializer.py +35 -0
  384. package/src/apothem/harnesses/hermes/uninstall.py +33 -0
  385. package/src/apothem/harnesses/hermes/update.py +10 -0
  386. package/src/apothem/harnesses/hermes/verify.py +11 -0
  387. package/src/apothem/harnesses/kimi_code/STANDARD-CONVENTION-PIN.md +128 -0
  388. package/src/apothem/harnesses/kimi_code/__init__.py +59 -0
  389. package/src/apothem/harnesses/kimi_code/capabilities.yml +40 -0
  390. package/src/apothem/harnesses/kimi_code/install.py +42 -0
  391. package/src/apothem/harnesses/kimi_code/templates/AGENTS.md +43 -0
  392. package/src/apothem/harnesses/kimi_code/uninstall.py +27 -0
  393. package/src/apothem/harnesses/kimi_code/update.py +10 -0
  394. package/src/apothem/harnesses/kimi_code/verify.py +11 -0
  395. package/src/apothem/harnesses/kiro/STANDARD-CONVENTION-PIN.md +77 -0
  396. package/src/apothem/harnesses/kiro/__init__.py +49 -0
  397. package/src/apothem/harnesses/kiro/capabilities.yml +36 -0
  398. package/src/apothem/harnesses/kiro/install.py +39 -0
  399. package/src/apothem/harnesses/kiro/templates/apothem-rules.md +36 -0
  400. package/src/apothem/harnesses/kiro/uninstall.py +25 -0
  401. package/src/apothem/harnesses/kiro/update.py +10 -0
  402. package/src/apothem/harnesses/kiro/verify.py +11 -0
  403. package/src/apothem/harnesses/open_claw/STANDARD-CONVENTION-PIN.md +62 -0
  404. package/src/apothem/harnesses/open_claw/__init__.py +35 -0
  405. package/src/apothem/harnesses/open_claw/capabilities.yml +35 -0
  406. package/src/apothem/harnesses/open_claw/install.py +17 -0
  407. package/src/apothem/harnesses/open_claw/materializer.py +36 -0
  408. package/src/apothem/harnesses/open_claw/uninstall.py +32 -0
  409. package/src/apothem/harnesses/open_claw/update.py +10 -0
  410. package/src/apothem/harnesses/open_claw/verify.py +11 -0
  411. package/src/apothem/harnesses/opencode/STANDARD-CONVENTION-PIN.md +76 -0
  412. package/src/apothem/harnesses/opencode/__init__.py +35 -0
  413. package/src/apothem/harnesses/opencode/capabilities.yml +43 -0
  414. package/src/apothem/harnesses/opencode/install.py +17 -0
  415. package/src/apothem/harnesses/opencode/materializer.py +31 -0
  416. package/src/apothem/harnesses/opencode/uninstall.py +34 -0
  417. package/src/apothem/harnesses/opencode/update.py +10 -0
  418. package/src/apothem/harnesses/opencode/verify.py +11 -0
  419. package/src/apothem/harnesses/qwen_code/STANDARD-CONVENTION-PIN.md +87 -0
  420. package/src/apothem/harnesses/qwen_code/__init__.py +37 -0
  421. package/src/apothem/harnesses/qwen_code/capabilities.yml +43 -0
  422. package/src/apothem/harnesses/qwen_code/install.py +19 -0
  423. package/src/apothem/harnesses/qwen_code/materializer.py +174 -0
  424. package/src/apothem/harnesses/qwen_code/templates/QWEN.md +30 -0
  425. package/src/apothem/harnesses/qwen_code/uninstall.py +34 -0
  426. package/src/apothem/harnesses/qwen_code/update.py +10 -0
  427. package/src/apothem/harnesses/qwen_code/verify.py +11 -0
  428. package/src/apothem/harnesses/trae/STANDARD-CONVENTION-PIN.md +70 -0
  429. package/src/apothem/harnesses/trae/__init__.py +49 -0
  430. package/src/apothem/harnesses/trae/capabilities.yml +34 -0
  431. package/src/apothem/harnesses/trae/install.py +38 -0
  432. package/src/apothem/harnesses/trae/templates/apothem-rules.md +37 -0
  433. package/src/apothem/harnesses/trae/uninstall.py +25 -0
  434. package/src/apothem/harnesses/trae/update.py +10 -0
  435. package/src/apothem/harnesses/trae/verify.py +11 -0
  436. package/src/apothem/harnesses/windsurf/STANDARD-CONVENTION-PIN.md +91 -0
  437. package/src/apothem/harnesses/windsurf/__init__.py +52 -0
  438. package/src/apothem/harnesses/windsurf/capabilities.yml +40 -0
  439. package/src/apothem/harnesses/windsurf/install.py +41 -0
  440. package/src/apothem/harnesses/windsurf/templates/apothem-rules.md +37 -0
  441. package/src/apothem/harnesses/windsurf/uninstall.py +25 -0
  442. package/src/apothem/harnesses/windsurf/update.py +10 -0
  443. package/src/apothem/harnesses/windsurf/verify.py +11 -0
  444. package/src/apothem/harnesses/zed/STANDARD-CONVENTION-PIN.md +92 -0
  445. package/src/apothem/harnesses/zed/__init__.py +57 -0
  446. package/src/apothem/harnesses/zed/capabilities.yml +38 -0
  447. package/src/apothem/harnesses/zed/install.py +41 -0
  448. package/src/apothem/harnesses/zed/templates/apothem-rules.md +32 -0
  449. package/src/apothem/harnesses/zed/uninstall.py +28 -0
  450. package/src/apothem/harnesses/zed/update.py +10 -0
  451. package/src/apothem/harnesses/zed/verify.py +11 -0
  452. package/src/apothem/hooks/README.md +81 -0
  453. package/src/apothem/hooks/__init__.py +24 -0
  454. package/src/apothem/hooks/askuserquestion_validator.py +380 -0
  455. package/src/apothem/hooks/dispatch.py +296 -0
  456. package/src/apothem/hooks/emit_hook_context.py +444 -0
  457. package/src/apothem/hooks/hooks.json +318 -0
  458. package/src/apothem/hooks/lib/README.md +39 -0
  459. package/src/apothem/hooks/lib/__init__.py +18 -0
  460. package/src/apothem/hooks/lib/bootstrap.ps1 +129 -0
  461. package/src/apothem/hooks/lib/bootstrap.sh +103 -0
  462. package/src/apothem/hooks/lib/events.py +51 -0
  463. package/src/apothem/hooks/lib/find-pwsh.ps1 +78 -0
  464. package/src/apothem/hooks/lib/find-pwsh.sh +76 -0
  465. package/src/apothem/hooks/lib/find-python.ps1 +63 -0
  466. package/src/apothem/hooks/lib/find-python.sh +97 -0
  467. package/src/apothem/hooks/lib/log.py +43 -0
  468. package/src/apothem/hooks/lib/resolve_root.py +264 -0
  469. package/src/apothem/hooks/messages/postcompact.md +14 -0
  470. package/src/apothem/hooks/messages/posttooluse-proactive-compaction.md +46 -0
  471. package/src/apothem/hooks/messages/precompact.md +14 -0
  472. package/src/apothem/hooks/messages/pretooluse-askuserquestion-recommended.md +65 -0
  473. package/src/apothem/hooks/messages/pretooluse-bash-plan-guard.md +97 -0
  474. package/src/apothem/hooks/messages/pretooluse-bash.md +39 -0
  475. package/src/apothem/hooks/messages/pretooluse-conformity.md +70 -0
  476. package/src/apothem/hooks/messages/pretooluse-dependency-guard.md +21 -0
  477. package/src/apothem/hooks/messages/pretooluse-edit-header-guard.md +61 -0
  478. package/src/apothem/hooks/messages/pretooluse-edit.md +21 -0
  479. package/src/apothem/hooks/messages/pretooluse-eval-guard.md +39 -0
  480. package/src/apothem/hooks/messages/pretooluse-notebookedit.md +11 -0
  481. package/src/apothem/hooks/messages/pretooluse-write-header-guard.md +45 -0
  482. package/src/apothem/hooks/messages/pretooluse-write-plan-guard.md +72 -0
  483. package/src/apothem/hooks/messages/pretooluse-write.md +21 -0
  484. package/src/apothem/hooks/messages/sessionstart.md +15 -0
  485. package/src/apothem/hooks/messages/stop.md +27 -0
  486. package/src/apothem/hooks/proactive_compaction_tracker.py +327 -0
  487. package/src/apothem/hooks/session_start_bootstrap.py +472 -0
  488. package/src/apothem/lib/README.md +42 -0
  489. package/src/apothem/lib/__init__.py +13 -0
  490. package/src/apothem/lib/atomic_io.py +189 -0
  491. package/src/apothem/lib/auditor.py +687 -0
  492. package/src/apothem/lib/clean_slate.py +396 -0
  493. package/src/apothem/lib/contexts.py +352 -0
  494. package/src/apothem/lib/data_home.py +255 -0
  495. package/src/apothem/lib/frontmatter.py +101 -0
  496. package/src/apothem/lib/harness_materializer.py +213 -0
  497. package/src/apothem/lib/harness_protocol.py +59 -0
  498. package/src/apothem/lib/harness_registry.py +282 -0
  499. package/src/apothem/lib/harness_registry_data.py +843 -0
  500. package/src/apothem/lib/install_ledger.py +347 -0
  501. package/src/apothem/lib/learning.py +540 -0
  502. package/src/apothem/lib/memory.py +347 -0
  503. package/src/apothem/lib/parallel_sweep.py +234 -0
  504. package/src/apothem/lib/plan_tiers.py +200 -0
  505. package/src/apothem/lib/plugin_bootstrap.py +132 -0
  506. package/src/apothem/lib/plugin_tree.py +599 -0
  507. package/src/apothem/lib/profile.py +755 -0
  508. package/src/apothem/lib/profile_projection.py +198 -0
  509. package/src/apothem/lib/propagation-manifest.yaml +878 -0
  510. package/src/apothem/lib/propagation.py +220 -0
  511. package/src/apothem/lib/python_resolver.py +189 -0
  512. package/src/apothem/lib/reporter.py +62 -0
  513. package/src/apothem/lib/workspace_migration.py +323 -0
  514. package/src/apothem/output-styles/README.md +41 -0
  515. package/src/apothem/output-styles/concise-engineer.md +49 -0
  516. package/src/apothem/output-styles/default-architect.md +52 -0
  517. package/src/apothem/output-styles/default.md +113 -0
  518. package/src/apothem/output-styles/forensic-auditor.md +63 -0
  519. package/src/apothem/py.typed +0 -0
  520. package/src/apothem/rules/README.md +121 -0
  521. package/src/apothem/rules/agent-capability-discipline-matrix.md +89 -0
  522. package/src/apothem/rules/agent-capability-discipline.md +78 -0
  523. package/src/apothem/rules/agent-orchestration-patterns.md +144 -0
  524. package/src/apothem/rules/agent-orchestration.md +65 -0
  525. package/src/apothem/rules/agents-md-convention.md +86 -0
  526. package/src/apothem/rules/agile-sprints-elements.md +135 -0
  527. package/src/apothem/rules/agile-sprints.md +64 -0
  528. package/src/apothem/rules/agnostic-posture-checklist.md +47 -0
  529. package/src/apothem/rules/agnostic-posture.md +48 -0
  530. package/src/apothem/rules/authoritative-referencing-quotation.md +50 -0
  531. package/src/apothem/rules/authoritative-referencing.md +66 -0
  532. package/src/apothem/rules/authority-inquiry-categories.md +58 -0
  533. package/src/apothem/rules/authority-inquiry.md +54 -0
  534. package/src/apothem/rules/auto-memory-topic-files.md +86 -0
  535. package/src/apothem/rules/auto-memory.md +67 -0
  536. package/src/apothem/rules/bidirectional-binding.md +123 -0
  537. package/src/apothem/rules/canonical-layout-reporting-tiers.md +212 -0
  538. package/src/apothem/rules/canonical-layout.md +60 -0
  539. package/src/apothem/rules/clean-architecture-layers.md +186 -0
  540. package/src/apothem/rules/clean-room-generation-protocols.md +124 -0
  541. package/src/apothem/rules/clean-room-generation.md +59 -0
  542. package/src/apothem/rules/code-craft-conventions.md +101 -0
  543. package/src/apothem/rules/code-craft-markdown.md +138 -0
  544. package/src/apothem/rules/code-craft-python.md +154 -0
  545. package/src/apothem/rules/code-craft-shell.md +192 -0
  546. package/src/apothem/rules/cognitive-identity-techniques.md +180 -0
  547. package/src/apothem/rules/cognitive-identity.md +81 -0
  548. package/src/apothem/rules/context-management-budget.md +46 -0
  549. package/src/apothem/rules/context-management-protocol.md +161 -0
  550. package/src/apothem/rules/context-management-scratch.md +128 -0
  551. package/src/apothem/rules/context-management.md +85 -0
  552. package/src/apothem/rules/definitiveness-virtues.md +67 -0
  553. package/src/apothem/rules/definitiveness.md +58 -0
  554. package/src/apothem/rules/determinism.md +81 -0
  555. package/src/apothem/rules/disclosure-ledger-markers.md +58 -0
  556. package/src/apothem/rules/disclosure-ledger.md +52 -0
  557. package/src/apothem/rules/dynamism.md +38 -0
  558. package/src/apothem/rules/etc-extension.md +57 -0
  559. package/src/apothem/rules/expertise-posture-elements.md +68 -0
  560. package/src/apothem/rules/expertise-posture.md +54 -0
  561. package/src/apothem/rules/freshness-facade.md +64 -0
  562. package/src/apothem/rules/harness-adapter-shape-schemas.md +162 -0
  563. package/src/apothem/rules/harness-adapter-shape.md +42 -0
  564. package/src/apothem/rules/host-discovery-manifests.md +50 -0
  565. package/src/apothem/rules/host-discovery.md +56 -0
  566. package/src/apothem/rules/i18n-discipline-locale-cohorts.md +120 -0
  567. package/src/apothem/rules/i18n-discipline.md +70 -0
  568. package/src/apothem/rules/interactive-questions-canonical-shapes.md +590 -0
  569. package/src/apothem/rules/interactive-questions-detail.md +41 -0
  570. package/src/apothem/rules/interactive-questions-sweep-matchers.md +184 -0
  571. package/src/apothem/rules/interactive-questions.md +89 -0
  572. package/src/apothem/rules/large-file-generation.md +112 -0
  573. package/src/apothem/rules/large-file-reading.md +59 -0
  574. package/src/apothem/rules/living-docs.md +85 -0
  575. package/src/apothem/rules/multi-agent-workflow.md +57 -0
  576. package/src/apothem/rules/operational-mandates-expanded.md +78 -0
  577. package/src/apothem/rules/operational-mandates.md +88 -0
  578. package/src/apothem/rules/option-annotation-form.md +60 -0
  579. package/src/apothem/rules/option-annotation.md +45 -0
  580. package/src/apothem/rules/own-voice-reimplementation.md +86 -0
  581. package/src/apothem/rules/performance-discipline.md +91 -0
  582. package/src/apothem/rules/persistent-conventions-vigilance-checklist.md +54 -0
  583. package/src/apothem/rules/persistent-conventions-vigilance.md +61 -0
  584. package/src/apothem/rules/plain-language.md +56 -0
  585. package/src/apothem/rules/planning-techniques.md +130 -0
  586. package/src/apothem/rules/pre-emission-gate-bars.md +86 -0
  587. package/src/apothem/rules/pre-emission-gate.md +54 -0
  588. package/src/apothem/rules/production-ready-prs-surfaces.md +162 -0
  589. package/src/apothem/rules/production-ready-prs.md +83 -0
  590. package/src/apothem/rules/propagation.md +63 -0
  591. package/src/apothem/rules/recommend-next-step.md +106 -0
  592. package/src/apothem/rules/refactoring-discipline.md +76 -0
  593. package/src/apothem/rules/session-closure.md +44 -0
  594. package/src/apothem/rules/sota-elevation-exemplars.md +76 -0
  595. package/src/apothem/rules/sota-elevation.md +52 -0
  596. package/src/apothem/rules/source-accessibility.md +58 -0
  597. package/src/apothem/rules/surgical-manipulation.md +48 -0
  598. package/src/apothem/rules/systemic-participation-relations.md +108 -0
  599. package/src/apothem/rules/systemic-participation.md +70 -0
  600. package/src/apothem/rules/ten-dimension-check-dimensions.md +52 -0
  601. package/src/apothem/rules/ten-dimension-check.md +59 -0
  602. package/src/apothem/rules/token-budget-discipline.md +81 -0
  603. package/src/apothem/rules/token-efficiency-rewrite-protocol.md +79 -0
  604. package/src/apothem/rules/token-efficiency-rewrite.md +77 -0
  605. package/src/apothem/rules/tool-use-discipline.md +48 -0
  606. package/src/apothem/rules/visual-leverage.md +102 -0
  607. package/src/apothem/schemas/NOTICE.md +9 -0
  608. package/src/apothem/schemas/README.md +104 -0
  609. package/src/apothem/schemas/__init__.py +176 -0
  610. package/src/apothem/schemas/advisory-finding.schema.json +111 -0
  611. package/src/apothem/schemas/agent.schema.json +106 -0
  612. package/src/apothem/schemas/authorship-header.txt +1 -0
  613. package/src/apothem/schemas/cohort-manifest.yaml +248 -0
  614. package/src/apothem/schemas/cohort-metadata-vocabulary.yaml +168 -0
  615. package/src/apothem/schemas/cohort.schema.json +113 -0
  616. package/src/apothem/schemas/command.schema.json +68 -0
  617. package/src/apothem/schemas/compatibility-matrix.yaml +432 -0
  618. package/src/apothem/schemas/context-fragment.schema.json +64 -0
  619. package/src/apothem/schemas/freshness-token-denylist.txt +51 -0
  620. package/src/apothem/schemas/handoff-manifest.yaml +353 -0
  621. package/src/apothem/schemas/header-exceptions.txt +141 -0
  622. package/src/apothem/schemas/header-visibility.yaml +39 -0
  623. package/src/apothem/schemas/learning-signal.schema.json +46 -0
  624. package/src/apothem/schemas/memory-record.schema.json +61 -0
  625. package/src/apothem/schemas/output-style.schema.json +40 -0
  626. package/src/apothem/schemas/plan.schema.json +51 -0
  627. package/src/apothem/schemas/plugin.schema.json +83 -0
  628. package/src/apothem/schemas/profile.example.yaml +70 -0
  629. package/src/apothem/schemas/profile.minimal.yaml +6 -0
  630. package/src/apothem/schemas/profile.schema.json +396 -0
  631. package/src/apothem/schemas/reference-token-denylist.txt +25 -0
  632. package/src/apothem/schemas/skill.schema.json +75 -0
  633. package/src/apothem/skills/README.md +93 -0
  634. package/src/apothem/skills/dependency-upgrade/SKILL.md +105 -0
  635. package/src/apothem/skills/dev-toolkit/SKILL.md +120 -0
  636. package/src/apothem/skills/diagram-authoring/SKILL.md +113 -0
  637. package/src/apothem/skills/document-authoring/SKILL.md +118 -0
  638. package/src/apothem/skills/ecosystem-audit/SKILL.md +108 -0
  639. package/src/apothem/skills/ecosystem-audit/references/audit-fortress.md +85 -0
  640. package/src/apothem/skills/ecosystem-audit/references/procedure.md +162 -0
  641. package/src/apothem/skills/eval-harness/SKILL.md +88 -0
  642. package/src/apothem/skills/incident-runbook/SKILL.md +92 -0
  643. package/src/apothem/skills/multi-source-research/SKILL.md +90 -0
  644. package/src/apothem/skills/plan-suite/SKILL.md +118 -0
  645. package/src/apothem/skills/plan-suite/master_template.md +1324 -0
  646. package/src/apothem/skills/projectify/SKILL.md +117 -0
  647. package/src/apothem/skills/prompt-engineering/SKILL.md +122 -0
  648. package/src/apothem/skills/refactor-extract/SKILL.md +85 -0
  649. package/src/apothem/skills/research-suite/SKILL.md +170 -0
  650. package/src/apothem/skills/research-suite/references/directory-structure.md +47 -0
  651. package/src/apothem/skills/research-suite/references/lifecycle.md +67 -0
  652. package/src/apothem/skills/research-suite/references/principal-investigator-framework.md +37 -0
  653. package/src/apothem/skills/research-suite/references/rigor-mandates.md +30 -0
  654. package/src/apothem/skills/research-suite/research_template.md +476 -0
  655. package/src/apothem/skills/secret-rotation/SKILL.md +87 -0
  656. package/src/apothem/skills/source-synthesis/SKILL.md +92 -0
  657. package/src/apothem/skills/surgical-guard/SKILL.md +118 -0
  658. package/src/apothem/skills/test-authoring/SKILL.md +85 -0
  659. package/src/apothem/skills/vuln-triage/SKILL.md +91 -0
  660. package/src/apothem/skills/workflow/SKILL.md +139 -0
  661. package/src/apothem/statuslines/README.md +26 -0
  662. package/src/apothem/statuslines/__init__.py +20 -0
  663. package/src/apothem/statuslines/conformity.json +5 -0
  664. package/src/apothem/statuslines/render.py +334 -0
  665. package/src/apothem/statuslines/statusline.md +50 -0
  666. package/src/apothem/templates/README.md +43 -0
  667. package/src/apothem/templates/agents-md-template.md +80 -0
  668. package/src/apothem/templates/consideration-log.md +39 -0
  669. package/src/apothem/templates/expertise-gap-log.md +56 -0
  670. package/src/apothem/templates/master-index-template.md +93 -0
  671. package/src/apothem/templates/potency-map.md +53 -0
  672. package/src/apothem/templates/preservation-audit.md +60 -0
  673. package/src/apothem/templates/question-resolution-audit.md +52 -0
  674. package/src/apothem/templates/trace-matrix-template.md +77 -0
@@ -0,0 +1,401 @@
1
+ # SPDX-License-Identifier: MIT
2
+
3
+ """Flag substantively-duplicated paragraphs across the governed corpus.
4
+
5
+ Why this enforcement exists. Spec section 3.1.e enumerates a five-class
6
+ redundancy taxonomy that erodes the demand-load discipline: (a)
7
+ parent-rule / companion sub-rule overlap, (b) cross-rule conceptual
8
+ duplication, (c) command / skill content overlap, (d) hook / rule
9
+ duplication, and (e) example duplication across docs. Each class
10
+ multiplies maintenance cost — a single edit must reach every duplicate
11
+ or the corpus drifts.
12
+
13
+ Detection strategy. The validator walks the four canonical authoring
14
+ trees (``rules/``, ``commands/``, ``skills/``, ``hooks/messages/``),
15
+ splits every Markdown file into paragraphs on blank-line boundaries,
16
+ normalises each paragraph (lowercase, collapse whitespace, strip
17
+ punctuation), tokenises into a set, and compares pairwise across files
18
+ using Jaccard similarity. Two paragraphs above ``--threshold`` (default
19
+ 0.80) AND carrying at least 40 substantive tokens are reported as a
20
+ duplication finding with the participating file paths and a suggested
21
+ canonical home (the file whose path prefix sorts earliest, as a
22
+ deterministic-but-reviewable hint — the operator picks the real
23
+ canonical home).
24
+
25
+ Scope carve-outs. Lines opening with ``(Companion Sub-Rule Anchor)`` are
26
+ EXPLICIT delegation pointers and are excluded from comparison. Fenced
27
+ code blocks are excluded (sample inputs and command snippets quote
28
+ external material rather than carry the author's prescriptive prose).
29
+ YAML frontmatter is excluded. The ``## Bindings`` tail section is
30
+ excluded — reciprocal binding statements legitimately overlap by
31
+ construction.
32
+
33
+ Heuristic-status disclaimer. Jaccard on tokenised paragraphs is a
34
+ heuristic. False positives are expected on canonical templates (banner
35
+ lines, gate attestation skeletons, common preambles). The operator
36
+ triages each finding; the threshold flag exists so a tighter or looser
37
+ gate can be tuned per corpus state without code changes.
38
+
39
+ Exit semantics. Exits 0 when no findings; exits 2 on any finding.
40
+ """
41
+
42
+ from __future__ import annotations
43
+
44
+ import argparse
45
+ import json
46
+ import re
47
+ import sys
48
+ from dataclasses import asdict, dataclass, field
49
+ from pathlib import Path
50
+ from typing import Final
51
+
52
+ GREP_NAME: Final[str] = "redundancy-grep"
53
+ RULE_ANCHOR: Final[str] = (
54
+ "rules/operational-mandates.md §CM-7 coherent-product non-redundancy"
55
+ )
56
+
57
+ EXIT_PASS: Final[int] = 0
58
+ EXIT_FAIL: Final[int] = 2
59
+
60
+ # Canonical authoring trees the validator walks. The relative roots are
61
+ # resolved against the project root passed on the command line.
62
+ CORPUS_SUBTREES: Final[tuple[str, ...]] = (
63
+ "src/apothem/rules",
64
+ "src/apothem/commands",
65
+ "src/apothem/skills",
66
+ "src/apothem/hooks/messages",
67
+ )
68
+
69
+ # Default Jaccard similarity threshold above which two paragraphs are
70
+ # reported as duplicates. Tuneable via --threshold.
71
+ DEFAULT_THRESHOLD: Final[float] = 0.80
72
+
73
+ # Minimum substantive token count for a paragraph to enter comparison.
74
+ # Shorter paragraphs (headings, one-liners, brief bullets) carry too
75
+ # little signal for Jaccard to discriminate genuine duplication from
76
+ # coincidental phrase overlap.
77
+ MIN_SUBSTANTIVE_TOKENS: Final[int] = 40
78
+
79
+ # Fenced code-block delimiter and frontmatter delimiter.
80
+ _FENCE_RE: Final[re.Pattern[str]] = re.compile(r"^```")
81
+ _FRONTMATTER_DELIM: Final[str] = "---"
82
+
83
+ # Companion-anchor pointer marker — excluded from comparison.
84
+ _COMPANION_ANCHOR_MARKER: Final[str] = "(Companion Sub-Rule Anchor)"
85
+
86
+ # Bindings tail section header. Everything from this header to EOF is
87
+ # excluded from the comparison surface.
88
+ _BINDINGS_HEADER_RE: Final[re.Pattern[str]] = re.compile(
89
+ r"^##+\s*Bindings\b", re.MULTILINE
90
+ )
91
+
92
+ # Markdown ATX heading recogniser. Captures the heading level (count of
93
+ # leading '#') and the title text.
94
+ _HEADING_RE: Final[re.Pattern[str]] = re.compile(r"^(#{1,6})\s+(.+?)\s*$")
95
+
96
+ # Canonical-scaffolding heading allow-list. Paragraphs whose enclosing
97
+ # heading (or any ancestor heading in the section hierarchy) contains any
98
+ # of these substrings as a heading title are excluded from comparison.
99
+ # The blocks under these headings are canonical-by-design — the same
100
+ # voice / contract / pipeline-position prose appears uniformly across
101
+ # every audit-fortress and plan-pipeline command and across every
102
+ # header-guard hook message, per `skills/ecosystem-audit/SKILL.md`
103
+ # Audit-Fortress Phase Skeleton and the operator-ratified canonical
104
+ # scaffolding pattern. Generic redundancy-grep flagging would force
105
+ # stripping the uniformity that the canonical scaffolding requires.
106
+ # Match is case-insensitive substring.
107
+ _SCAFFOLDING_HEADING_SUBSTRINGS: Final[tuple[str, ...]] = (
108
+ "pipeline contract",
109
+ "foundational stanzas",
110
+ "refusal & escalation",
111
+ "output surface",
112
+ "file-authoring contract",
113
+ "askuserquestion on ambiguity",
114
+ "inquiry cadence",
115
+ "audit-fortress",
116
+ "critical rules",
117
+ "mandates",
118
+ "findings report shape",
119
+ "axis-of-attention",
120
+ "axis attestation",
121
+ "borderline triage",
122
+ "severity triage",
123
+ "pre-emission gate",
124
+ "output discipline",
125
+ "inquiry triage",
126
+ "scope clarification",
127
+ # `## Resolution & Recovery` carries the canonical template/surface
128
+ # corruption-fallback contract that every pipeline suite-skill states in
129
+ # uniform voice (plan-suite cites TM-N/CP-N IDs, research-suite cites the
130
+ # R-mandate/lifecycle IDs) — same scaffolding class as "refusal &
131
+ # escalation"; per-pipeline specialisation lives in the prose, so the
132
+ # blocks stay self-contained rather than cross-referencing one another.
133
+ "resolution & recovery",
134
+ )
135
+
136
+ # Punctuation stripper for token normalisation.
137
+ _PUNCT_RE: Final[re.Pattern[str]] = re.compile(r"[^\w\s]+")
138
+
139
+
140
+ @dataclass(frozen=True)
141
+ class Finding:
142
+ issue: str
143
+ detail: str
144
+ files: list[str]
145
+ similarity: float
146
+ suggested_canonical_home: str
147
+ rule: str = RULE_ANCHOR
148
+
149
+
150
+ @dataclass(frozen=True)
151
+ class GrepResult:
152
+ grep: str
153
+ root: str
154
+ threshold: float
155
+ paragraph_count: int
156
+ passed: bool
157
+ findings: list[Finding] = field(default_factory=list)
158
+
159
+ def to_json(self) -> str:
160
+ payload = {
161
+ "grep": self.grep,
162
+ "root": self.root,
163
+ "threshold": self.threshold,
164
+ "paragraph_count": self.paragraph_count,
165
+ "passed": self.passed,
166
+ "findings": [asdict(f) for f in self.findings],
167
+ }
168
+ return json.dumps(payload, indent=2)
169
+
170
+
171
+ def _strip_frontmatter(text: str) -> str:
172
+ """Remove leading YAML frontmatter, if present."""
173
+ lines = text.splitlines()
174
+ if not lines or lines[0].strip() != _FRONTMATTER_DELIM:
175
+ return text
176
+ for idx in range(1, len(lines)):
177
+ if lines[idx].strip() == _FRONTMATTER_DELIM:
178
+ return "\n".join(lines[idx + 1 :])
179
+ return text
180
+
181
+
182
+ def _strip_bindings_tail(text: str) -> str:
183
+ """Trim everything from the first `## Bindings` header to EOF."""
184
+ match = _BINDINGS_HEADER_RE.search(text)
185
+ if match is None:
186
+ return text
187
+ return text[: match.start()]
188
+
189
+
190
+ def _strip_fenced_code(text: str) -> str:
191
+ """Remove fenced code blocks; the surrounding prose remains."""
192
+ out: list[str] = []
193
+ in_fence = False
194
+ for line in text.splitlines():
195
+ if _FENCE_RE.match(line):
196
+ in_fence = not in_fence
197
+ continue
198
+ if not in_fence:
199
+ out.append(line)
200
+ return "\n".join(out)
201
+
202
+
203
+ def _is_scaffolding_heading(title: str) -> bool:
204
+ """Return True iff the heading title matches any canonical-scaffolding
205
+ allow-list substring (case-insensitive)."""
206
+ lowered = title.lower()
207
+ return any(sub in lowered for sub in _SCAFFOLDING_HEADING_SUBSTRINGS)
208
+
209
+
210
+ def _split_paragraphs(text: str) -> list[str]:
211
+ """Split on blank-line boundaries; drop companion-anchor pointers and
212
+ paragraphs whose enclosing heading hierarchy includes a
213
+ canonical-scaffolding allow-listed section.
214
+
215
+ The walker tracks the current heading stack: each ATX heading
216
+ establishes the title at its level and clears every deeper level.
217
+ A paragraph is excluded when any active heading in the stack matches
218
+ the scaffolding allow-list.
219
+ """
220
+ out: list[str] = []
221
+ heading_stack: dict[int, str] = {}
222
+ current_block: list[str] = []
223
+
224
+ def flush_block() -> None:
225
+ if not current_block:
226
+ return
227
+ para = "\n".join(current_block).strip()
228
+ current_block.clear()
229
+ if not para:
230
+ return
231
+ if _COMPANION_ANCHOR_MARKER in para:
232
+ return
233
+ if any(_is_scaffolding_heading(title) for title in heading_stack.values()):
234
+ return
235
+ out.append(para)
236
+
237
+ for line in text.splitlines():
238
+ heading_match = _HEADING_RE.match(line)
239
+ if heading_match:
240
+ flush_block()
241
+ level = len(heading_match.group(1))
242
+ title = heading_match.group(2)
243
+ heading_stack[level] = title
244
+ for deeper in [k for k in heading_stack if k > level]:
245
+ del heading_stack[deeper]
246
+ continue
247
+ if not line.strip():
248
+ flush_block()
249
+ continue
250
+ current_block.append(line)
251
+ flush_block()
252
+ return out
253
+
254
+
255
+ def _tokenise(paragraph: str) -> frozenset[str]:
256
+ """Lowercase, strip punctuation, split on whitespace; return token set."""
257
+ normalised = _PUNCT_RE.sub(" ", paragraph.lower())
258
+ return frozenset(tok for tok in normalised.split() if tok)
259
+
260
+
261
+ def _jaccard(a: frozenset[str], b: frozenset[str]) -> float:
262
+ if not a or not b:
263
+ return 0.0
264
+ inter = len(a & b)
265
+ union = len(a | b)
266
+ return inter / union if union else 0.0
267
+
268
+
269
+ def _walk_corpus(root: Path) -> list[Path]:
270
+ """Return every `.md` file under the four canonical subtrees."""
271
+ files: list[Path] = []
272
+ for sub in CORPUS_SUBTREES:
273
+ base = root / sub
274
+ if not base.exists():
275
+ continue
276
+ files.extend(sorted(base.rglob("*.md")))
277
+ return files
278
+
279
+
280
+ def _extract_paragraphs(path: Path) -> list[tuple[str, frozenset[str]]]:
281
+ """Return (text, token-set) pairs for every comparable paragraph."""
282
+ try:
283
+ raw = path.read_text(encoding="utf-8")
284
+ except (OSError, UnicodeDecodeError):
285
+ return []
286
+ text = _strip_frontmatter(raw)
287
+ text = _strip_bindings_tail(text)
288
+ text = _strip_fenced_code(text)
289
+ out: list[tuple[str, frozenset[str]]] = []
290
+ for para in _split_paragraphs(text):
291
+ tokens = _tokenise(para)
292
+ if len(tokens) < MIN_SUBSTANTIVE_TOKENS:
293
+ continue
294
+ out.append((para, tokens))
295
+ return out
296
+
297
+
298
+ def _are_sibling_variants(path_a: Path, path_b: Path) -> bool:
299
+ """Return True iff two files are canonical sibling variants.
300
+
301
+ Two files in the same directory whose stems differ in exactly one
302
+ kebab-token position (e.g., ``pretooluse-edit-header-guard`` vs.
303
+ ``pretooluse-write-header-guard``) or where one stem is a strict
304
+ prefix of the other (parent / companion form,
305
+ e.g., ``sota-elevation`` vs. ``sota-elevation-exemplars``) are
306
+ canonical sibling variants. Their shared content IS the
307
+ design — the matcher excludes pairings between them.
308
+ """
309
+ if path_a.parent != path_b.parent:
310
+ return False
311
+ tokens_a = path_a.stem.split("-")
312
+ tokens_b = path_b.stem.split("-")
313
+ if tokens_a == tokens_b:
314
+ return False
315
+ # Parent / companion: one is a strict prefix of the other.
316
+ shorter, longer = sorted([tokens_a, tokens_b], key=len)
317
+ if longer[: len(shorter)] == shorter:
318
+ return True
319
+ # Equal length: differ in exactly one position.
320
+ if len(tokens_a) == len(tokens_b):
321
+ differences = sum(1 for a, b in zip(tokens_a, tokens_b, strict=True) if a != b)
322
+ return differences == 1
323
+ return False
324
+
325
+
326
+ def check_corpus(root: Path, threshold: float = DEFAULT_THRESHOLD) -> GrepResult:
327
+ """Walk the corpus; report duplicated paragraphs above ``threshold``."""
328
+ files = _walk_corpus(root)
329
+ # Flatten to (path, paragraph_text, tokens) tuples.
330
+ entries: list[tuple[Path, str, frozenset[str]]] = []
331
+ for f in files:
332
+ for text, tokens in _extract_paragraphs(f):
333
+ entries.append((f, text, tokens))
334
+ findings: list[Finding] = []
335
+ seen_pairs: set[tuple[int, int]] = set()
336
+ for i in range(len(entries)):
337
+ path_i, text_i, tokens_i = entries[i]
338
+ for j in range(i + 1, len(entries)):
339
+ path_j, _text_j, tokens_j = entries[j]
340
+ if path_i == path_j:
341
+ continue
342
+ if _are_sibling_variants(path_i, path_j):
343
+ continue
344
+ sim = _jaccard(tokens_i, tokens_j)
345
+ if sim < threshold:
346
+ continue
347
+ key = (i, j)
348
+ if key in seen_pairs:
349
+ continue
350
+ seen_pairs.add(key)
351
+ files_pair = sorted({path_i.as_posix(), path_j.as_posix()})
352
+ canonical_home = files_pair[0]
353
+ preview = text_i.replace("\n", " ").strip()
354
+ if len(preview) > 160:
355
+ preview = preview[:157] + "..."
356
+ findings.append(
357
+ Finding(
358
+ issue="substantively-duplicated paragraph",
359
+ detail=(
360
+ f"paragraph with jaccard similarity {sim:.2f} "
361
+ f"appears across {len(files_pair)} files; "
362
+ f"preview: {preview!r}"
363
+ ),
364
+ files=files_pair,
365
+ similarity=round(sim, 4),
366
+ suggested_canonical_home=canonical_home,
367
+ )
368
+ )
369
+ return GrepResult(
370
+ grep=GREP_NAME,
371
+ root=str(root),
372
+ threshold=threshold,
373
+ paragraph_count=len(entries),
374
+ passed=not findings,
375
+ findings=findings,
376
+ )
377
+
378
+
379
+ def _main(argv: list[str]) -> int:
380
+ parser = argparse.ArgumentParser(prog=GREP_NAME, description=__doc__)
381
+ parser.add_argument(
382
+ "root",
383
+ nargs="?",
384
+ default=".",
385
+ help="project root to walk (default: current directory)",
386
+ )
387
+ parser.add_argument(
388
+ "--threshold",
389
+ type=float,
390
+ default=DEFAULT_THRESHOLD,
391
+ help=f"jaccard similarity threshold (default: {DEFAULT_THRESHOLD})",
392
+ )
393
+ args = parser.parse_args(argv[1:])
394
+ root = Path(args.root).resolve()
395
+ result = check_corpus(root, threshold=args.threshold)
396
+ print(result.to_json())
397
+ return EXIT_PASS if result.passed else EXIT_FAIL
398
+
399
+
400
+ if __name__ == "__main__":
401
+ sys.exit(_main(sys.argv))
@@ -0,0 +1,230 @@
1
+ # SPDX-License-Identifier: MIT
2
+
3
+ """Flag leaked reference-platform branding tokens on authored surfaces.
4
+
5
+ Why this enforcement exists. Apothem reimplements a peer platform's
6
+ feature-set in its own voice; the own-voice discipline requires that no
7
+ authored surface — rules, commands, skills, agents, documentation, brand
8
+ assets — leak the reference platform's slug or brand vocabulary. A
9
+ mechanical sweep proves zero in-scope hits so the product narrative reads
10
+ as its own work rather than as a paraphrase of the reference platform.
11
+
12
+ Scope. Corpus-level standalone validator. Walks the working tree under the
13
+ supplied root and inspects ONLY authored in-scope surfaces (the rules,
14
+ commands, skills, agents directories, the documentation tree, and the
15
+ brand-asset tree). The denylist data file, the conformity machinery, the
16
+ schemas directory, the test tree, and the plan-suite scratch are all
17
+ exempt — they are not the authored product narrative the discipline holds
18
+ to the zero-leak bar.
19
+
20
+ Detection. The forbidden tokens live in the package-relative denylist data
21
+ file, never in this module. Pure-alpha slugs match at word boundaries to
22
+ avoid false positives on larger words; punctuation-bearing tokens match as
23
+ escaped literals. All matching is case-insensitive.
24
+
25
+ Posture. The result is advisory: the sweep surfaces findings and never
26
+ silent-blocks by default, honoring apothem's agnostic gate posture. CI
27
+ opts into strict enforcement separately. Exits 0 when zero findings across
28
+ every in-scope file; exits 2 on any finding.
29
+ """
30
+
31
+ from __future__ import annotations
32
+
33
+ import json
34
+ import re
35
+ import sys
36
+ from dataclasses import asdict, dataclass, field
37
+ from pathlib import Path
38
+ from typing import Final
39
+
40
+ GREP_NAME: Final[str] = "reference-token-grep"
41
+ RULE_ANCHOR: Final[str] = "rules/own-voice-reimplementation.md"
42
+
43
+ EXIT_PASS: Final[int] = 0
44
+ EXIT_FAIL: Final[int] = 2
45
+
46
+ # The denylist data file is package-relative: the conformity package ships
47
+ # beside its ``schemas/`` sibling in both supported layouts — the repo
48
+ # checkout (``src/apothem/{conformity,schemas}``) and the installed tree
49
+ # (``<install-root>/apothem/{conformity,schemas}``) — so one parent hop
50
+ # from this module reaches it in either shape. The data file holds the
51
+ # forbidden tokens so this module never names them.
52
+ _DENYLIST_PATH: Final[Path] = (
53
+ Path(__file__).resolve().parents[1] / "schemas" / "reference-token-denylist.txt"
54
+ )
55
+
56
+ # Authored in-scope surface roots (relative to the supplied root). Only text
57
+ # files under these directories are scanned.
58
+ _IN_SCOPE_DIRS: Final[tuple[str, ...]] = (
59
+ "src/apothem/rules",
60
+ "src/apothem/commands",
61
+ "src/apothem/skills",
62
+ "src/apothem/agents",
63
+ "site/content/docs",
64
+ "assets",
65
+ )
66
+
67
+ # Text-file suffixes scanned under the in-scope roots.
68
+ _TEXT_SUFFIXES: Final[frozenset[str]] = frozenset(
69
+ {".md", ".mdx", ".txt", ".svg", ".json", ".yaml", ".yml"}
70
+ )
71
+
72
+ # Exempt path fragments. A candidate whose POSIX-relative path contains any
73
+ # of these fragments is never scanned — the conformity machinery, the
74
+ # schemas data files (the denylist itself), the test tree, and the
75
+ # plan-suite scratch all legitimately reference or carry the tokens.
76
+ _EXEMPT_FRAGMENTS: Final[tuple[str, ...]] = (
77
+ ".plans/",
78
+ "tests/",
79
+ "src/apothem/conformity/",
80
+ "src/apothem/schemas/",
81
+ )
82
+
83
+
84
+ @dataclass(frozen=True)
85
+ class Finding:
86
+ """One leaked reference-platform token on an authored surface."""
87
+
88
+ surface: str
89
+ kind: str
90
+ detail: str
91
+ rule: str = RULE_ANCHOR
92
+
93
+
94
+ @dataclass(frozen=True)
95
+ class GrepResult:
96
+ """Aggregated walk result for a single corpus sweep."""
97
+
98
+ grep: str
99
+ root: str
100
+ files_inspected: int
101
+ passed: bool
102
+ findings: list[Finding] = field(default_factory=list)
103
+
104
+ def to_json(self) -> str:
105
+ payload = {
106
+ "grep": self.grep,
107
+ "root": self.root,
108
+ "files_inspected": self.files_inspected,
109
+ "passed": self.passed,
110
+ "findings": [asdict(f) for f in self.findings],
111
+ "advisory": True,
112
+ }
113
+ return json.dumps(payload, indent=2)
114
+
115
+
116
+ def _load_tokens() -> list[str]:
117
+ """Parse the denylist data file into a list of forbidden tokens.
118
+
119
+ Pre-conditions: the package-relative denylist file exists.
120
+ Post-conditions: returns every non-empty, non-comment line, stripped.
121
+ """
122
+ try:
123
+ raw = _DENYLIST_PATH.read_text(encoding="utf-8")
124
+ except OSError:
125
+ return []
126
+ tokens: list[str] = []
127
+ for line in raw.splitlines():
128
+ stripped = line.strip()
129
+ if not stripped or stripped.startswith("#"):
130
+ continue
131
+ tokens.append(stripped)
132
+ return tokens
133
+
134
+
135
+ def _compile_tokens(tokens: list[str]) -> re.Pattern[str] | None:
136
+ """Compile the denylist into one case-insensitive alternation regex.
137
+
138
+ Pure-alphabetic tokens are anchored at word boundaries (``\\btoken\\b``)
139
+ so a larger word merely containing the substring is not flagged.
140
+ Punctuation-bearing tokens are escaped literals — word boundaries do not
141
+ apply cleanly across ``.`` / ``-`` characters, so the escaped literal is
142
+ matched as-is. Returns None when the denylist is empty.
143
+ """
144
+ if not tokens:
145
+ return None
146
+ alternatives: list[str] = []
147
+ for token in tokens:
148
+ if token.isalpha():
149
+ alternatives.append(r"\b" + re.escape(token) + r"\b")
150
+ else:
151
+ alternatives.append(re.escape(token))
152
+ return re.compile(r"(?i)(?:" + "|".join(alternatives) + r")")
153
+
154
+
155
+ def _is_in_scope(rel_posix: str) -> bool:
156
+ """Return True iff a relative POSIX path is an authored in-scope surface."""
157
+ for fragment in _EXEMPT_FRAGMENTS:
158
+ if fragment in rel_posix or rel_posix.startswith(fragment.rstrip("/")):
159
+ return False
160
+ return any(rel_posix == d or rel_posix.startswith(d + "/") for d in _IN_SCOPE_DIRS)
161
+
162
+
163
+ def _scan_file(path: Path, rel_posix: str, pattern: re.Pattern[str]) -> list[Finding]:
164
+ """Scan one text file; return one Finding per token match."""
165
+ try:
166
+ content = path.read_text(encoding="utf-8")
167
+ except (OSError, UnicodeDecodeError):
168
+ return []
169
+ findings: list[Finding] = []
170
+ for line_index, line in enumerate(content.splitlines(), start=1):
171
+ for match in pattern.finditer(line):
172
+ findings.append(
173
+ Finding(
174
+ surface=rel_posix,
175
+ kind="reference-token",
176
+ detail=f"line {line_index}: '{match.group()}'",
177
+ )
178
+ )
179
+ return findings
180
+
181
+
182
+ def check(root: Path) -> GrepResult:
183
+ """Walk the corpus under ``root``; flag leaked reference-platform tokens.
184
+
185
+ Pre-conditions: ``root`` is the repository root (or an arbitrary subtree).
186
+ Post-conditions: ``result.passed`` is True iff every authored in-scope
187
+ text file contained zero denylisted tokens.
188
+ """
189
+ tokens = _load_tokens()
190
+ pattern = _compile_tokens(tokens)
191
+ findings: list[Finding] = []
192
+ inspected = 0
193
+ root_resolved = root.resolve()
194
+ if pattern is not None:
195
+ for suffix in sorted(_TEXT_SUFFIXES):
196
+ for path in root.rglob(f"*{suffix}"):
197
+ if not path.is_file():
198
+ continue
199
+ try:
200
+ rel_posix = path.resolve().relative_to(root_resolved).as_posix()
201
+ except ValueError:
202
+ continue
203
+ if not _is_in_scope(rel_posix):
204
+ continue
205
+ inspected += 1
206
+ findings.extend(_scan_file(path, rel_posix, pattern))
207
+ return GrepResult(
208
+ grep=GREP_NAME,
209
+ root=str(root),
210
+ files_inspected=inspected,
211
+ passed=not findings,
212
+ findings=findings,
213
+ )
214
+
215
+
216
+ def _read_input(argv: list[str]) -> Path:
217
+ if len(argv) >= 2:
218
+ return Path(argv[1])
219
+ return Path.cwd()
220
+
221
+
222
+ def _main(argv: list[str]) -> int:
223
+ root = _read_input(argv)
224
+ result = check(root)
225
+ print(result.to_json())
226
+ return EXIT_PASS if result.passed else EXIT_FAIL
227
+
228
+
229
+ if __name__ == "__main__":
230
+ sys.exit(_main(sys.argv))