hyperweave 0.2.1__tar.gz → 0.2.2__tar.gz

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 (330) hide show
  1. {hyperweave-0.2.1 → hyperweave-0.2.2}/.gitignore +2 -2
  2. {hyperweave-0.2.1 → hyperweave-0.2.2}/CHANGELOG.md +6 -0
  3. {hyperweave-0.2.1 → hyperweave-0.2.2}/PKG-INFO +1 -1
  4. hyperweave-0.2.2/scripts/extract_glyphs.py +276 -0
  5. hyperweave-0.2.2/scripts/generate_hw_compliant.py +327 -0
  6. hyperweave-0.2.2/scripts/generate_proofset.py +613 -0
  7. hyperweave-0.2.2/scripts/stress_test.py +521 -0
  8. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/_version.py +2 -2
  9. {hyperweave-0.2.1 → hyperweave-0.2.2}/.dockerignore +0 -0
  10. {hyperweave-0.2.1 → hyperweave-0.2.2}/.github/workflows/ci.yml +0 -0
  11. {hyperweave-0.2.1 → hyperweave-0.2.2}/.github/workflows/deploy.yml +0 -0
  12. {hyperweave-0.2.1 → hyperweave-0.2.2}/.github/workflows/publish.yml +0 -0
  13. {hyperweave-0.2.1 → hyperweave-0.2.2}/Dockerfile +0 -0
  14. {hyperweave-0.2.1 → hyperweave-0.2.2}/LICENSE +0 -0
  15. {hyperweave-0.2.1 → hyperweave-0.2.2}/README.md +0 -0
  16. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/buttons/button-liquid.svg +0 -0
  17. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/cards/card-butterfly.svg +0 -0
  18. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/cards/card-python.svg +0 -0
  19. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/cards/card-sunflower.svg +0 -0
  20. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/cards/card-waves.svg +0 -0
  21. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/badge_critical.svg +0 -0
  22. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/badge_passing.svg +0 -0
  23. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/badge_warning.svg +0 -0
  24. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/banner.svg +0 -0
  25. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/icons/discord.svg +0 -0
  26. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/icons/notion.svg +0 -0
  27. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/icons/reddit.svg +0 -0
  28. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/icons/spotify.svg +0 -0
  29. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/icons/youtube.svg +0 -0
  30. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/marquee_counter.svg +0 -0
  31. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/marquee_horizontal.svg +0 -0
  32. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/marquee_vertical.svg +0 -0
  33. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/profile-cards/chart_stars_full.svg +0 -0
  34. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/profile-cards/stats.svg +0 -0
  35. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/brutalist-emerald/strip.svg +0 -0
  36. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/badge_critical.svg +0 -0
  37. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/badge_passing.svg +0 -0
  38. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/badge_warning.svg +0 -0
  39. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/banner.svg +0 -0
  40. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/icons/bluesky.svg +0 -0
  41. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/icons/github.svg +0 -0
  42. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/icons/instagram.svg +0 -0
  43. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/icons/mastodon.svg +0 -0
  44. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/icons/x.svg +0 -0
  45. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/marquee_counter.svg +0 -0
  46. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/marquee_horizontal.svg +0 -0
  47. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/marquee_vertical.svg +0 -0
  48. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/profile-cards/chart_stars_full.svg +0 -0
  49. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/profile-cards/stats.svg +0 -0
  50. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/chrome-horizon/strip.svg +0 -0
  51. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/telemetry/master_card.svg +0 -0
  52. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/telemetry/receipt.svg +0 -0
  53. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/examples/telemetry/rhythm_strip.svg +0 -0
  54. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/footers/inneraura-footer-liquid.svg +0 -0
  55. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/footers/inneraura-footer-purple.svg +0 -0
  56. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/footers/inneraura-footer.svg +0 -0
  57. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/hyperweave-banner.svg +0 -0
  58. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-discord.svg +0 -0
  59. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-docs.svg +0 -0
  60. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-github.svg +0 -0
  61. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-instagram.svg +0 -0
  62. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-linkedin.svg +0 -0
  63. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-tiktok.svg +0 -0
  64. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-x.svg +0 -0
  65. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/icons/cobalt-sapphire-youtube.svg +0 -0
  66. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/marquees/badge-showcase-triple.svg +0 -0
  67. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/marquees/genome-marquee-triple.svg +0 -0
  68. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/marquees/sample-badges.svg +0 -0
  69. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/404.svg +0 -0
  70. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/callout-icons.svg +0 -0
  71. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/divider.svg +0 -0
  72. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/favicon.svg +0 -0
  73. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/hero-banner.svg +0 -0
  74. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/hyperweave-banner-v2.svg +0 -0
  75. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/hyperweave-navbar-logo.svg +0 -0
  76. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/loader.svg +0 -0
  77. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/mintlify-assets/og-image.svg +0 -0
  78. {hyperweave-0.2.1 → hyperweave-0.2.2}/assets/timelines/hyperweave-roadmap.svg +0 -0
  79. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/assets/favicon.svg +0 -0
  80. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/assets/hyperweave-banner.svg +0 -0
  81. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/assets/hyperweave-navbar-logo.svg +0 -0
  82. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/assets/og-image.svg +0 -0
  83. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/explanation/architecture.mdx +0 -0
  84. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/explanation/camo-compatibility.mdx +0 -0
  85. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/explanation/cim-compliance.mdx +0 -0
  86. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/explanation/genome-profile-system.mdx +0 -0
  87. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/explanation/metadata-tiers.mdx +0 -0
  88. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/how-to/add-motion-to-badges.mdx +0 -0
  89. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/how-to/create-session-receipts.mdx +0 -0
  90. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/how-to/set-up-claude-code-hooks.mdx +0 -0
  91. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/how-to/use-live-data-badges.mdx +0 -0
  92. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/introduction.mdx +0 -0
  93. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/mint.json +0 -0
  94. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/quickstart.mdx +0 -0
  95. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/reference/cli.mdx +0 -0
  96. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/reference/compose-spec.mdx +0 -0
  97. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/reference/genomes.mdx +0 -0
  98. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/reference/http-api.mdx +0 -0
  99. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/reference/mcp-tools.mdx +0 -0
  100. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/reference/motions.mdx +0 -0
  101. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/reference/telemetry-contract.mdx +0 -0
  102. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/spec/hyperweave-protocol.mdx +0 -0
  103. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/tutorials/build-an-artifact-kit.mdx +0 -0
  104. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/tutorials/compose-your-first-badge.mdx +0 -0
  105. {hyperweave-0.2.1 → hyperweave-0.2.2}/docs/tutorials/install-session-telemetry.mdx +0 -0
  106. {hyperweave-0.2.1 → hyperweave-0.2.2}/fly.toml +0 -0
  107. {hyperweave-0.2.1 → hyperweave-0.2.2}/hooks/install.py +0 -0
  108. {hyperweave-0.2.1 → hyperweave-0.2.2}/hooks/session_end.sh +0 -0
  109. {hyperweave-0.2.1 → hyperweave-0.2.2}/justfile +0 -0
  110. {hyperweave-0.2.1 → hyperweave-0.2.2}/pyproject.toml +0 -0
  111. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/__init__.py +0 -0
  112. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/__main__.py +0 -0
  113. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/cli.py +0 -0
  114. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/__init__.py +0 -0
  115. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/assembler.py +0 -0
  116. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/context.py +0 -0
  117. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/engine.py +0 -0
  118. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/lanes.py +0 -0
  119. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/resolver.py +0 -0
  120. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/resolvers/__init__.py +0 -0
  121. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/resolvers/chart.py +0 -0
  122. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/resolvers/stats.py +0 -0
  123. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/compose/resolvers/timeline.py +0 -0
  124. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/config/__init__.py +0 -0
  125. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/config/genome_validator.py +0 -0
  126. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/config/loader.py +0 -0
  127. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/config/registry.py +0 -0
  128. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/config/settings.py +0 -0
  129. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/connectors/__init__.py +0 -0
  130. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/connectors/arxiv.py +0 -0
  131. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/connectors/base.py +0 -0
  132. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/connectors/cache.py +0 -0
  133. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/connectors/github.py +0 -0
  134. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/connectors/rest.py +0 -0
  135. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/__init__.py +0 -0
  136. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/color.py +0 -0
  137. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/contracts.py +0 -0
  138. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/enums.py +0 -0
  139. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/models.py +0 -0
  140. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/schema.py +0 -0
  141. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/text.py +0 -0
  142. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/core/thresholds.py +0 -0
  143. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/css/accessibility.css +0 -0
  144. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/css/bridge.css +0 -0
  145. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/css/expression.css +0 -0
  146. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/css/phase-colors.css +0 -0
  147. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/css/status.css +0 -0
  148. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/css/telemetry.css +0 -0
  149. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/font-metrics/inter.json +0 -0
  150. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/fonts/jetbrains-mono.b64 +0 -0
  151. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/fonts/jetbrains-mono.meta.json +0 -0
  152. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/fonts/orbitron.b64 +0 -0
  153. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/fonts/orbitron.meta.json +0 -0
  154. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/genomes/brutalist-emerald.json +0 -0
  155. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/genomes/chrome-horizon.json +0 -0
  156. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/genomes/telemetry-void.json +0 -0
  157. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/glyphs.json +0 -0
  158. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/border/chromatic-pulse.yaml +0 -0
  159. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/border/corner-trace.yaml +0 -0
  160. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/border/dual-orbit.yaml +0 -0
  161. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/border/entanglement.yaml +0 -0
  162. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/border/rimrun.yaml +0 -0
  163. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/bars.yaml +0 -0
  164. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/breach.yaml +0 -0
  165. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/broadcast.yaml +0 -0
  166. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/cascade.yaml +0 -0
  167. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/collapse.yaml +0 -0
  168. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/converge.yaml +0 -0
  169. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/crash.yaml +0 -0
  170. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/drop.yaml +0 -0
  171. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/kinetic/pulse.yaml +0 -0
  172. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/motions/static.yaml +0 -0
  173. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/policies/normal.json +0 -0
  174. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/policies/permissive.json +0 -0
  175. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/policies/ungoverned.json +0 -0
  176. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/profiles/brutalist.contract.json +0 -0
  177. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/profiles/brutalist.yaml +0 -0
  178. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/profiles/chrome.contract.json +0 -0
  179. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/profiles/chrome.yaml +0 -0
  180. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/specimens.yaml +0 -0
  181. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/telemetry/model-pricing.yaml +0 -0
  182. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/telemetry/stage-config.yaml +0 -0
  183. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/telemetry/stage-labels.yaml +0 -0
  184. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/telemetry/tool-classes.yaml +0 -0
  185. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/telemetry/tool-colors.yaml +0 -0
  186. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/arrow.json +0 -0
  187. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/aurora.json +0 -0
  188. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/beacon.json +0 -0
  189. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/bracket3d.json +0 -0
  190. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/chevron.json +0 -0
  191. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/crosshair.json +0 -0
  192. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/diamond.json +0 -0
  193. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/rocket.json +0 -0
  194. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/rules/bar.json +0 -0
  195. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/rules/dashed.json +0 -0
  196. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/rules/five-wave.json +0 -0
  197. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/rules/spectral.json +0 -0
  198. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/rules/straight.json +0 -0
  199. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/rules/wave.json +0 -0
  200. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/data/terminals/stijl.json +0 -0
  201. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/kit.py +0 -0
  202. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/mcp/__init__.py +0 -0
  203. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/mcp/__main__.py +0 -0
  204. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/mcp/server.py +0 -0
  205. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/py.typed +0 -0
  206. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/render/__init__.py +0 -0
  207. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/render/chart_engine.py +0 -0
  208. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/render/fonts.py +0 -0
  209. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/render/glyphs.py +0 -0
  210. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/render/motion.py +0 -0
  211. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/render/templates.py +0 -0
  212. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/serve/__init__.py +0 -0
  213. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/serve/app.py +0 -0
  214. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/__init__.py +0 -0
  215. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/capture.py +0 -0
  216. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/contract.py +0 -0
  217. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/corrections.py +0 -0
  218. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/cost.py +0 -0
  219. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/models.py +0 -0
  220. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/parser.py +0 -0
  221. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/telemetry/stages.py +0 -0
  222. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/filter.svg.j2 +0 -0
  223. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/glyph-inline.svg.j2 +0 -0
  224. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/glyph.svg.j2 +0 -0
  225. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/gradient.svg.j2 +0 -0
  226. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/metadata.svg.j2 +0 -0
  227. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/metric.svg.j2 +0 -0
  228. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/phase-segment.svg.j2 +0 -0
  229. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/rule.svg.j2 +0 -0
  230. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/status.svg.j2 +0 -0
  231. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/terminal.svg.j2 +0 -0
  232. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/components/treemap.svg.j2 +0 -0
  233. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/document.svg.j2 +0 -0
  234. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/error-badge.svg.j2 +0 -0
  235. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/badge/brutalist-content.j2 +0 -0
  236. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/badge/brutalist-defs.j2 +0 -0
  237. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/badge/chrome-content.j2 +0 -0
  238. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/badge/chrome-defs.j2 +0 -0
  239. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/badge/default-content.j2 +0 -0
  240. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/badge/default-defs.j2 +0 -0
  241. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/badge.svg.j2 +0 -0
  242. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/banner/brutalist-defs.j2 +0 -0
  243. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/banner/chrome-defs.j2 +0 -0
  244. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/banner/default-defs.j2 +0 -0
  245. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/banner.svg.j2 +0 -0
  246. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/catalog.svg.j2 +0 -0
  247. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/chart/brutalist-content.j2 +0 -0
  248. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/chart/brutalist-defs.j2 +0 -0
  249. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/chart/chrome-content.j2 +0 -0
  250. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/chart/chrome-defs.j2 +0 -0
  251. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/chart.svg.j2 +0 -0
  252. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/divider.svg.j2 +0 -0
  253. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/icon/brutalist-content.j2 +0 -0
  254. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/icon/brutalist-defs.j2 +0 -0
  255. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/icon/chrome-content.j2 +0 -0
  256. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/icon/chrome-defs.j2 +0 -0
  257. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/icon/default-content.j2 +0 -0
  258. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/icon/default-defs.j2 +0 -0
  259. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/icon.svg.j2 +0 -0
  260. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-counter/brutalist-content.j2 +0 -0
  261. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-counter/brutalist-defs.j2 +0 -0
  262. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-counter/chrome-content.j2 +0 -0
  263. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-counter/chrome-defs.j2 +0 -0
  264. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-counter.svg.j2 +0 -0
  265. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-horizontal/brutalist-content.j2 +0 -0
  266. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-horizontal/brutalist-defs.j2 +0 -0
  267. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-horizontal/chrome-content.j2 +0 -0
  268. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-horizontal/chrome-defs.j2 +0 -0
  269. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-horizontal.svg.j2 +0 -0
  270. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-vertical/brutalist-content.j2 +0 -0
  271. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-vertical/brutalist-defs.j2 +0 -0
  272. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-vertical/chrome-content.j2 +0 -0
  273. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-vertical/chrome-defs.j2 +0 -0
  274. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/marquee-vertical.svg.j2 +0 -0
  275. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/master-card.svg.j2 +0 -0
  276. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/receipt.svg.j2 +0 -0
  277. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/rhythm-strip.svg.j2 +0 -0
  278. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/stats/brutalist-content.j2 +0 -0
  279. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/stats/brutalist-defs.j2 +0 -0
  280. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/stats/chrome-content.j2 +0 -0
  281. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/stats/chrome-defs.j2 +0 -0
  282. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/stats.svg.j2 +0 -0
  283. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/brutalist-content.j2 +0 -0
  284. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/brutalist-defs.j2 +0 -0
  285. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/brutalist-status.j2 +0 -0
  286. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/chrome-content.j2 +0 -0
  287. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/chrome-defs.j2 +0 -0
  288. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/chrome-status.j2 +0 -0
  289. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/default-content.j2 +0 -0
  290. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/default-defs.j2 +0 -0
  291. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip/default-status.j2 +0 -0
  292. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/strip.svg.j2 +0 -0
  293. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/timeline/default-content.j2 +0 -0
  294. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/frames/timeline.svg.j2 +0 -0
  295. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/border/chromatic-pulse.svg.j2 +0 -0
  296. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/border/corner-trace.svg.j2 +0 -0
  297. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/border/dual-orbit.svg.j2 +0 -0
  298. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/border/entanglement.svg.j2 +0 -0
  299. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/border/rimrun.svg.j2 +0 -0
  300. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/bars.svg.j2 +0 -0
  301. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/breach.svg.j2 +0 -0
  302. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/broadcast.svg.j2 +0 -0
  303. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/cascade.svg.j2 +0 -0
  304. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/collapse.svg.j2 +0 -0
  305. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/converge.svg.j2 +0 -0
  306. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/crash.svg.j2 +0 -0
  307. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/drop.svg.j2 +0 -0
  308. {hyperweave-0.2.1 → hyperweave-0.2.2}/src/hyperweave/templates/motions/kinetic/pulse.svg.j2 +0 -0
  309. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/__init__.py +0 -0
  310. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/conftest.py +0 -0
  311. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/fixtures/github_contributions/synthetic.html +0 -0
  312. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/fixtures/session.json +0 -0
  313. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/fixtures/session.jsonl +0 -0
  314. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_assembler.py +0 -0
  315. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_chart_engine.py +0 -0
  316. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_chart_frame.py +0 -0
  317. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_connectors.py +0 -0
  318. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_core.py +0 -0
  319. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_github_scrape.py +0 -0
  320. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_kit.py +0 -0
  321. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_mcp.py +0 -0
  322. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_paradigm_dispatch.py +0 -0
  323. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_proofset.py +0 -0
  324. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_render.py +0 -0
  325. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_serve.py +0 -0
  326. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_stats_card.py +0 -0
  327. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_telemetry.py +0 -0
  328. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_telemetry_integration.py +0 -0
  329. {hyperweave-0.2.1 → hyperweave-0.2.2}/tests/test_timeline.py +0 -0
  330. {hyperweave-0.2.1 → hyperweave-0.2.2}/uv.lock +0 -0
@@ -27,10 +27,10 @@ htmlcov/
27
27
  archive/
28
28
  .claude/
29
29
  # CLAUDE.md
30
- docs/_notes/
30
+ docs/_notes/
31
31
  outputs/
32
- scripts/
33
32
  specs/
33
+ # scripts/ is version-controlled (tests/test_proofset.py imports generate_proofset.py)
34
34
 
35
35
  assets/cards/butterfly-mcp.svg
36
36
  assets/cards/card-moon.svg
@@ -5,6 +5,12 @@ All notable changes to HyperWeave are documented in this file.
5
5
  The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
6
6
  and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
7
 
8
+ ## [0.2.2] - 2026-04-13
9
+
10
+ ### Fixed
11
+
12
+ - **CI test job** was red on the v0.2.1 push because `tests/test_proofset.py` imports `scripts/generate_proofset.py`, but `scripts/` was excluded from version control by `.gitignore`. The three test runners saw `FileNotFoundError: No such file or directory: scripts/generate_proofset.py`. `scripts/` is now tracked (it is a dev-tools directory, not a runtime dependency, and remains excluded from the PyPI wheel by `[tool.hatch.build.targets.wheel].packages`).
13
+
8
14
  ## [0.2.1] - 2026-04-13
9
15
 
10
16
  Post-v0.2.0 stabilization: typography alignment, mobile rendering fix, and a streak computation correction.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: hyperweave
3
- Version: 0.2.1
3
+ Version: 0.2.2
4
4
  Summary: Headless visual output layer for AI agents. One API call → self-contained SVG.
5
5
  Project-URL: Repository, https://github.com/InnerAura/hyperweave
6
6
  Project-URL: Issues, https://github.com/InnerAura/hyperweave/issues
@@ -0,0 +1,276 @@
1
+ #!/usr/bin/env python3
2
+ """Extract curated glyphs from Simple Icons and output data/glyphs.json.
3
+
4
+ Build-time only. Requires: npm install simple-icons (temp dev dependency).
5
+
6
+ Usage:
7
+ npm install simple-icons # one-time
8
+ python scripts/extract_glyphs.py
9
+
10
+ Output:
11
+ src/hyperweave/data/glyphs.json
12
+ """
13
+
14
+ from __future__ import annotations
15
+
16
+ import json
17
+ import subprocess
18
+ import sys
19
+ from pathlib import Path
20
+
21
+ # Curated icon set per PRD SS10
22
+ # Keys = Simple Icons export names (camelCase with 'si' prefix)
23
+ # Values = (our slug, category)
24
+ CURATED_ICONS: dict[str, tuple[str, str]] = {
25
+ # Social (LinkedIn/Slack removed from SI v16 — trademark)
26
+ "siGithub": ("github", "social"),
27
+ "siX": ("x", "social"),
28
+ "siDiscord": ("discord", "social"),
29
+ "siYoutube": ("youtube", "social"),
30
+ "siSpotify": ("spotify", "social"),
31
+ "siInstagram": ("instagram", "social"),
32
+ "siTiktok": ("tiktok", "social"),
33
+ "siReddit": ("reddit", "social"),
34
+ "siMastodon": ("mastodon", "social"),
35
+ "siBluesky": ("bluesky", "social"),
36
+ # Dev
37
+ "siPython": ("python", "dev"),
38
+ "siNpm": ("npm", "dev"),
39
+ "siDocker": ("docker", "dev"),
40
+ "siRust": ("rust", "dev"),
41
+ "siGo": ("go", "dev"),
42
+ "siTypescript": ("typescript", "dev"),
43
+ "siJavascript": ("javascript", "dev"),
44
+ "siReact": ("react", "dev"),
45
+ "siVuedotjs": ("vue", "dev"),
46
+ "siSvelte": ("svelte", "dev"),
47
+ "siNextdotjs": ("nextjs", "dev"),
48
+ "siNodedotjs": ("nodejs", "dev"),
49
+ "siDeno": ("deno", "dev"),
50
+ "siSwift": ("swift", "dev"),
51
+ "siKotlin": ("kotlin", "dev"),
52
+ "siCplusplus": ("cplusplus", "dev"),
53
+ "siRuby": ("ruby", "dev"),
54
+ "siPhp": ("php", "dev"),
55
+ "siElixir": ("elixir", "dev"),
56
+ "siZig": ("zig", "dev"),
57
+ # Platforms (AWS/Azure/Heroku removed from SI v16 — trademark)
58
+ "siPypi": ("pypi", "platforms"),
59
+ "siHuggingface": ("huggingface", "platforms"),
60
+ "siArxiv": ("arxiv", "platforms"),
61
+ "siKaggle": ("kaggle", "platforms"),
62
+ "siVercel": ("vercel", "platforms"),
63
+ "siNetlify": ("netlify", "platforms"),
64
+ "siCloudflare": ("cloudflare", "platforms"),
65
+ "siGooglecloud": ("googlecloud", "platforms"),
66
+ "siDigitalocean": ("digitalocean", "platforms"),
67
+ "siSupabase": ("supabase", "platforms"),
68
+ "siFirebase": ("firebase", "platforms"),
69
+ "siGithubactions": ("githubactions", "platforms"),
70
+ "siGitlab": ("gitlab", "platforms"),
71
+ "siBitbucket": ("bitbucket", "platforms"),
72
+ # Tools (VS Code removed from SI v16 — trademark)
73
+ "siNeovim": ("neovim", "tools"),
74
+ "siFigma": ("figma", "tools"),
75
+ "siNotion": ("notion", "tools"),
76
+ "siObsidian": ("obsidian", "tools"),
77
+ "siLinear": ("linear", "tools"),
78
+ "siPostman": ("postman", "tools"),
79
+ "siGrafana": ("grafana", "tools"),
80
+ "siPrometheus": ("prometheus", "tools"),
81
+ "siJetbrains": ("jetbrains", "tools"),
82
+ "siSublimetext": ("sublimetext", "tools"),
83
+ "siStorybook": ("storybook", "tools"),
84
+ "siEslint": ("eslint", "tools"),
85
+ "siPrettier": ("prettier", "tools"),
86
+ # AI / ML (OpenAI removed from SI v16 — trademark)
87
+ "siAnthropic": ("anthropic", "ai"),
88
+ "siTensorflow": ("tensorflow", "ai"),
89
+ "siPytorch": ("pytorch", "ai"),
90
+ "siJupyter": ("jupyter", "ai"),
91
+ "siApachespark": ("spark", "ai"),
92
+ "siGithubcopilot": ("githubcopilot", "ai"),
93
+ # Infrastructure (AWS/Azure/Heroku removed from SI v16 — trademark)
94
+ "siKubernetes": ("kubernetes", "infra"),
95
+ "siTerraform": ("terraform", "infra"),
96
+ "siNginx": ("nginx", "infra"),
97
+ "siRedis": ("redis", "infra"),
98
+ "siPostgresql": ("postgresql", "infra"),
99
+ "siMongodb": ("mongodb", "infra"),
100
+ "siElasticsearch": ("elasticsearch", "infra"),
101
+ "siApachekafka": ("kafka", "infra"),
102
+ "siRabbitmq": ("rabbitmq", "infra"),
103
+ "siGnubash": ("bash", "infra"),
104
+ "siGit": ("git", "infra"),
105
+ # Web / Frameworks
106
+ "siTailwindcss": ("tailwindcss", "dev"),
107
+ "siVite": ("vite", "dev"),
108
+ "siBun": ("bun", "dev"),
109
+ "siPnpm": ("pnpm", "dev"),
110
+ "siAstro": ("astro", "dev"),
111
+ "siRemix": ("remix", "dev"),
112
+ "siFlutter": ("flutter", "dev"),
113
+ "siDart": ("dart", "dev"),
114
+ "siHtml5": ("html5", "dev"),
115
+ "siSass": ("sass", "dev"),
116
+ "siMarkdown": ("markdown", "dev"),
117
+ # Mobile / OS
118
+ "siAndroid": ("android", "platforms"),
119
+ "siApple": ("apple", "platforms"),
120
+ "siLinux": ("linux", "platforms"),
121
+ # Commerce / Services
122
+ "siStripe": ("stripe", "platforms"),
123
+ "siShopify": ("shopify", "platforms"),
124
+ "siAuth0": ("auth0", "platforms"),
125
+ }
126
+
127
+ # Geometric shapes (hand-authored, not from Simple Icons)
128
+ # Defined in 640x640 viewBox per PRD SS10
129
+ GEOMETRIC_SHAPES: dict[str, dict[str, str | None]] = {
130
+ "triangle": {
131
+ "path": "M320 53.3 586.6 533.3H53.4Z",
132
+ "viewBox": "0 0 640 640",
133
+ "brand_color": None,
134
+ "category": "geometric",
135
+ },
136
+ "diamond": {
137
+ "path": "M320 53.3 506.7 320 320 586.7 133.3 320Z",
138
+ "viewBox": "0 0 640 640",
139
+ "brand_color": None,
140
+ "category": "geometric",
141
+ },
142
+ "hexagon": {
143
+ "path": "M320 53.3 566.4 186.7V453.3L320 586.7 73.6 453.3V186.7Z",
144
+ "viewBox": "0 0 640 640",
145
+ "brand_color": None,
146
+ "category": "geometric",
147
+ },
148
+ "shield": {
149
+ "path": "M320 53.3 533.3 186.7V373.3C533.3 480 320 586.7 320 586.7S106.7 480 106.7 373.3V186.7Z",
150
+ "viewBox": "0 0 640 640",
151
+ "brand_color": None,
152
+ "category": "geometric",
153
+ },
154
+ "circle": {
155
+ "path": "M320 106.7A213.3 213.3 0 11106.7 320 213.3 213.3 0 01320 106.7Z",
156
+ "viewBox": "0 0 640 640",
157
+ "brand_color": None,
158
+ "category": "geometric",
159
+ },
160
+ "star": {
161
+ "path": (
162
+ "M320 53.3 396.4 237.8 586.7 253.3 440 381.5 483.3 566.7"
163
+ " 320 471.1 156.7 566.7 200 381.5 53.3 253.3 243.6 237.8Z"
164
+ ),
165
+ "viewBox": "0 0 640 640",
166
+ "brand_color": None,
167
+ "category": "geometric",
168
+ },
169
+ }
170
+
171
+
172
+ def extract_from_npm() -> dict[str, dict[str, object]]:
173
+ """Extract icons from the simple-icons npm package via Node.js subprocess.
174
+
175
+ Uses `node -e` to require simple-icons, extract all curated paths,
176
+ and return JSON to stdout. This avoids parsing JS manually.
177
+ """
178
+ # Build the Node.js extraction script
179
+ icon_keys = list(CURATED_ICONS.keys())
180
+ icon_keys_json = json.dumps(icon_keys)
181
+ slugs_json = json.dumps({k: v[0] for k, v in CURATED_ICONS.items()})
182
+ cats_json = json.dumps({k: v[1] for k, v in CURATED_ICONS.items()})
183
+
184
+ node_script = f"""
185
+ const si = require('simple-icons');
186
+ const keys = {icon_keys_json};
187
+ const slugs = {slugs_json};
188
+ const cats = {cats_json};
189
+ const result = {{}};
190
+ for (const key of keys) {{
191
+ const icon = si[key];
192
+ if (!icon) {{
193
+ process.stderr.write('WARN: ' + key + ' not found in simple-icons\\n');
194
+ continue;
195
+ }}
196
+ result[slugs[key]] = {{
197
+ path: icon.path,
198
+ viewBox: '0 0 24 24',
199
+ brand_color: '#' + icon.hex,
200
+ category: cats[key],
201
+ }};
202
+ }}
203
+ process.stdout.write(JSON.stringify(result));
204
+ """
205
+
206
+ try:
207
+ proc = subprocess.run(
208
+ ["node", "-e", node_script],
209
+ capture_output=True,
210
+ text=True,
211
+ timeout=30,
212
+ )
213
+ if proc.returncode != 0:
214
+ print(f"Node.js extraction failed: {proc.stderr}", file=sys.stderr)
215
+ return {}
216
+ if proc.stderr:
217
+ # Print warnings (missing icons)
218
+ for line in proc.stderr.strip().splitlines():
219
+ print(line, file=sys.stderr)
220
+
221
+ return json.loads(proc.stdout)
222
+
223
+ except FileNotFoundError:
224
+ print("Node.js not found. Install Node.js to extract Simple Icons.", file=sys.stderr)
225
+ return {}
226
+ except subprocess.TimeoutExpired:
227
+ print("Node.js extraction timed out.", file=sys.stderr)
228
+ return {}
229
+ except json.JSONDecodeError as e:
230
+ print(f"Invalid JSON from Node.js: {e}", file=sys.stderr)
231
+ return {}
232
+
233
+
234
+ def main() -> None:
235
+ """Run glyph extraction and write data/glyphs.json."""
236
+ output_path = Path(__file__).resolve().parent.parent / "src" / "hyperweave" / "data" / "glyphs.json"
237
+
238
+ # Extract from npm (via Node subprocess)
239
+ glyphs = extract_from_npm()
240
+
241
+ if not glyphs:
242
+ print("No SI icons extracted. Check that simple-icons is installed.", file=sys.stderr)
243
+ print("Run: npm install simple-icons", file=sys.stderr)
244
+ sys.exit(1)
245
+
246
+ # Add geometric shapes (always)
247
+ for glyph_id, definition in GEOMETRIC_SHAPES.items():
248
+ glyphs[glyph_id] = definition # type: ignore[assignment]
249
+
250
+ # Sort by category then name for readability
251
+ sorted_glyphs = dict(
252
+ sorted(
253
+ glyphs.items(),
254
+ key=lambda x: (x[1].get("category", "zzz"), x[0]),
255
+ )
256
+ )
257
+
258
+ # Write output
259
+ output_path.parent.mkdir(parents=True, exist_ok=True)
260
+ with output_path.open("w", encoding="utf-8") as f:
261
+ json.dump(sorted_glyphs, f, indent=2)
262
+ f.write("\n")
263
+
264
+ # Summary
265
+ by_cat: dict[str, int] = {}
266
+ for v in sorted_glyphs.values():
267
+ cat = v.get("category", "unknown")
268
+ by_cat[cat] = by_cat.get(cat, 0) + 1
269
+
270
+ print(f"Wrote {len(sorted_glyphs)} glyphs to {output_path}")
271
+ for cat, count in sorted(by_cat.items()):
272
+ print(f" {cat}: {count}")
273
+
274
+
275
+ if __name__ == "__main__":
276
+ main()
@@ -0,0 +1,327 @@
1
+ #!/usr/bin/env python3
2
+ """Generate HW-compliant versions of all specimen SVGs.
3
+
4
+ For each specimen SVG in specs/components/ and specs/motion/:
5
+ 1. Do NOT modify originals
6
+ 2. Create hw-compliant/ subfolder within each specimen's directory
7
+ 3. Regenerate with full HyperWeave v8.0 protocol scaffolding
8
+ 4. ZERO visual changes
9
+
10
+ Usage:
11
+ python3 scripts/generate_hw_compliant.py
12
+ """
13
+
14
+ from __future__ import annotations
15
+
16
+ import re
17
+ import uuid
18
+ from datetime import UTC, datetime
19
+ from pathlib import Path
20
+
21
+ ROOT = Path(__file__).resolve().parent.parent
22
+ SPECS = ROOT / "specs"
23
+
24
+
25
+ def _has_hw_metadata(svg: str) -> bool:
26
+ """Check if SVG already has HW protocol metadata."""
27
+ return "hw:artifact" in svg and "xmlns:hw" in svg and 'role="img"' in svg
28
+
29
+
30
+ def _has_reduced_motion(svg: str) -> bool:
31
+ return "prefers-reduced-motion" in svg
32
+
33
+
34
+ def _has_color_scheme(svg: str) -> bool:
35
+ return "prefers-color-scheme" in svg
36
+
37
+
38
+ def _extract_viewbox(svg: str) -> str:
39
+ m = re.search(r'viewBox="([^"]+)"', svg, re.IGNORECASE)
40
+ return m.group(1) if m else "0 0 800 220"
41
+
42
+
43
+ def _extract_dims(svg: str) -> tuple[str, str]:
44
+ """Extract width/height from SVG, preserving original values exactly."""
45
+ w = re.search(r'width="([^"]+)"', svg)
46
+ h = re.search(r'height="([^"]+)"', svg)
47
+ return (w.group(1) if w else "800", h.group(1) if h else "220")
48
+
49
+
50
+ def _extract_svg_tag(svg: str) -> tuple[str, str]:
51
+ """Split into the opening <svg ...> tag and everything after."""
52
+ m = re.match(r"(<svg[^>]*>)(.*)", svg, re.DOTALL)
53
+ if m:
54
+ return m.group(1), m.group(2)
55
+ return "<svg>", svg
56
+
57
+
58
+ def _augment_svg_tag(tag: str, attrs: dict[str, str]) -> str:
59
+ """Add attributes to an existing <svg ...> tag without replacing originals.
60
+
61
+ Preserves ALL original attributes (xmlns, viewBox, width, height, etc.).
62
+ Only ADDS attributes that don't already exist in the tag.
63
+ """
64
+ for key, val in attrs.items():
65
+ # Skip if attribute already exists
66
+ if f"{key}=" in tag or f"{key} =" in tag:
67
+ continue
68
+ # Insert before the closing >
69
+ tag = tag.rstrip(">").rstrip() + f'\n {key}="{val}">'
70
+ # Fix: ensure single closing >
71
+ tag = tag.replace(">>", ">")
72
+ return tag
73
+
74
+
75
+ def _infer_type(path: Path) -> str:
76
+ """Infer artifact type from directory structure."""
77
+ parts = str(path).lower()
78
+ if "divider" in parts:
79
+ return "divider"
80
+ if "icon" in parts:
81
+ return "icon"
82
+ if "banner" in parts or "holofoil" in parts:
83
+ return "banner"
84
+ if "marquee" in parts:
85
+ return "marquee"
86
+ if "border-frame" in parts:
87
+ return "motion-primitive"
88
+ if "kinetic-typography" in parts:
89
+ return "kinetic-typography"
90
+ return "specimen"
91
+
92
+
93
+ def _infer_motion_id(path: Path) -> str:
94
+ """Infer motion ID from filename."""
95
+ name = path.stem.lower()
96
+ mapping = {
97
+ "002-chromatic-pulse": "chromatic-pulse",
98
+ "003-corner-trace": "corner-trace",
99
+ "004-dual-orbit": "dual-orbit",
100
+ "020-quantum-entanglement": "entanglement",
101
+ "rim-runners": "rimrun",
102
+ "banner_bars": "bars",
103
+ "banner_broadcast": "broadcast",
104
+ "banner_cascade": "cascade",
105
+ "banner_convergence": "converge",
106
+ "banner_drop": "drop",
107
+ "crash": "crash",
108
+ "chromatic_impact_physics": "impact",
109
+ "quantum_tunneling_breach": "breach",
110
+ "pulse": "pulse",
111
+ "z_axis_illusion_via_exponential_scale_blur_convergence": "collapse",
112
+ }
113
+ return mapping.get(name, name)
114
+
115
+
116
+ def _slug(path: Path) -> str:
117
+ return path.stem.lower().replace(" ", "-").replace("_", "-")
118
+
119
+
120
+ def _check_cim(svg: str) -> tuple[bool, str]:
121
+ """Check CIM compliance and return waiver if needed."""
122
+ non_cim_indicators = []
123
+ if "stop-color" in svg and "animate" in svg.lower():
124
+ non_cim_indicators.append("stop-color animation")
125
+ if "stroke-dashoffset" in svg and "animate" in svg.lower():
126
+ non_cim_indicators.append("stroke-dashoffset animation")
127
+ if "stroke-width" in svg and "<animate" in svg.lower() and "stroke-width" in svg.split("<animate")[1][:200]:
128
+ non_cim_indicators.append("stroke-width animation")
129
+ if "letter-spacing" in svg and "animate" in svg.lower():
130
+ non_cim_indicators.append("letter-spacing animation")
131
+ if "stdDeviation" in svg and "animate" in svg.lower():
132
+ non_cim_indicators.append("filter blur animation")
133
+ if "baseFrequency" in svg and "animate" in svg.lower():
134
+ non_cim_indicators.append("turbulence animation")
135
+ if "clip-path" in svg and "@keyframes" in svg:
136
+ non_cim_indicators.append("clip-path animation")
137
+ # Check for animated gradients
138
+ if re.search(r'<animate[^>]*attributeName="x[12]"', svg, re.IGNORECASE):
139
+ non_cim_indicators.append("gradient coordinate animation")
140
+
141
+ if non_cim_indicators:
142
+ return False, f"Non-CIM: {', '.join(non_cim_indicators)}"
143
+ return True, ""
144
+
145
+
146
+ def wrap_specimen(src: Path) -> str:
147
+ """Wrap a raw specimen SVG with HW v8.0 protocol scaffolding.
148
+
149
+ CRITICAL: The original <svg> tag's xmlns, viewBox, width, height are
150
+ preserved EXACTLY. We only ADD new attributes (xmlns:hw, role,
151
+ aria-labelledby, data-hw-*). Never replace existing ones.
152
+ """
153
+ svg = src.read_text(encoding="utf-8").strip()
154
+
155
+ # Already compliant — add only missing layers
156
+ if _has_hw_metadata(svg):
157
+ if not _has_reduced_motion(svg):
158
+ svg = _inject_reduced_motion(svg)
159
+ if not _has_color_scheme(svg):
160
+ svg = _inject_color_scheme(svg)
161
+ return svg
162
+
163
+ # Raw specimen — full protocol wrap
164
+ artifact_id = str(uuid.uuid4())
165
+ uid = f"hw-{artifact_id[:8]}"
166
+ now = datetime.now(UTC).isoformat()
167
+ w, h = _extract_dims(svg)
168
+ art_type = _infer_type(src)
169
+ slug = _slug(src)
170
+ motion_id = _infer_motion_id(src) if "motion" in str(src) else "static"
171
+ cim_ok, cim_waiver = _check_cim(svg)
172
+
173
+ # Extract the original <svg ...> tag and inner content
174
+ svg_tag, inner = _extract_svg_tag(svg)
175
+ if inner.rstrip().endswith("</svg>"):
176
+ inner = inner.rstrip()[:-6]
177
+
178
+ # Augment the ORIGINAL tag — preserve xmlns, viewBox, width, height
179
+ augmented = _augment_svg_tag(
180
+ svg_tag,
181
+ {
182
+ "xmlns:hw": "https://hyperweave.dev/hw/v8.0",
183
+ "role": "img",
184
+ "aria-labelledby": f"{uid}-title {uid}-desc",
185
+ "data-hw-id": artifact_id,
186
+ "data-hw-frame": art_type,
187
+ "data-hw-chromatic": "adaptive",
188
+ "data-hw-motion": motion_id,
189
+ },
190
+ )
191
+
192
+ perf = "composite-only" if cim_ok else "paint-ok"
193
+ cim_str = "true" if cim_ok else "false"
194
+ tradeoffs = "CIM-compliant: uses only compositor-friendly properties." if cim_ok else f"CIM waiver: {cim_waiver}"
195
+
196
+ return f'''{augmented}
197
+
198
+ <title id="{uid}-title">{slug} -- HyperWeave Specimen</title>
199
+ <desc id="{uid}-desc">HW-compliant version of {src.name}. Type: {art_type}. Zero visual changes from original.</desc>
200
+
201
+ <metadata>
202
+ <hw:artifact id="{artifact_id}" type="{art_type}" series="specimens" version="1.0.0"
203
+ xmlns:hw="https://hyperweave.dev/hw/v8.0">
204
+ <hw:provenance>
205
+ <hw:generator>HyperWeave Specimen Wrapper v0.1 (InnerAura Labs)</hw:generator>
206
+ <hw:created>{now}</hw:created>
207
+ <hw:human-directed>true</hw:human-directed>
208
+ <hw:source-file>{src.relative_to(ROOT)}</hw:source-file>
209
+ </hw:provenance>
210
+ <hw:spec size="{w}x{h}" performance="{perf}"
211
+ theme="adaptive" a11y="WCAG-AA"/>
212
+ <hw:composition>
213
+ <hw:frame>{art_type}</hw:frame>
214
+ <hw:environment motion="{motion_id}" status="active"/>
215
+ </hw:composition>
216
+ <hw:aesthetic>
217
+ <hw:motion vocabulary="{motion_id}" cim-compliant="{cim_str}"/>
218
+ </hw:aesthetic>
219
+ <hw:reasoning>
220
+ <hw:intent>Specimen artifact wrapped with HW v8.0 protocol for Layer 1 editorial publishing.</hw:intent>
221
+ <hw:approach>Zero-visual-change wrapping: original SVG preserved, HW metadata injected around it.</hw:approach>
222
+ <hw:tradeoffs>{tradeoffs}</hw:tradeoffs>
223
+ </hw:reasoning>
224
+ </hw:artifact>
225
+ </metadata>
226
+
227
+ <style>
228
+ @media (prefers-reduced-motion: reduce) {{
229
+ *, *::before, *::after {{
230
+ animation-duration: 0.01ms !important;
231
+ animation-iteration-count: 1 !important;
232
+ transition-duration: 0.01ms !important;
233
+ }}
234
+ animate, animateTransform, animateMotion, set {{
235
+ display: none !important;
236
+ }}
237
+ }}
238
+ @media (prefers-color-scheme: light) {{
239
+ svg {{ --hw-scheme: light; }}
240
+ }}
241
+ @media (prefers-color-scheme: dark) {{
242
+ svg {{ --hw-scheme: dark; }}
243
+ }}
244
+ </style>
245
+
246
+ <!-- Original specimen content (zero visual changes) -->
247
+ <g data-hw-zone="specimen-content">
248
+ {_indent(inner, 4)}
249
+ </g>
250
+
251
+ </svg>'''
252
+
253
+
254
+ def _inject_reduced_motion(svg: str) -> str:
255
+ """Inject prefers-reduced-motion into existing compliant SVG."""
256
+ rm_block = """
257
+ @media (prefers-reduced-motion: reduce) {
258
+ *, *::before, *::after {
259
+ animation-duration: 0.01ms !important;
260
+ animation-iteration-count: 1 !important;
261
+ transition-duration: 0.01ms !important;
262
+ }
263
+ animate, animateTransform, animateMotion, set {
264
+ display: none !important;
265
+ }
266
+ }"""
267
+ # Try to inject into existing <style> block
268
+ if "<style>" in svg:
269
+ return svg.replace("<style>", f"<style>{rm_block}", 1)
270
+ # Or add before </svg>
271
+ return svg.replace("</svg>", f"<style>{rm_block}</style>\n</svg>")
272
+
273
+
274
+ def _inject_color_scheme(svg: str) -> str:
275
+ """Inject prefers-color-scheme into existing compliant SVG."""
276
+ cs_block = """
277
+ @media (prefers-color-scheme: light) { svg { --hw-scheme: light; } }
278
+ @media (prefers-color-scheme: dark) { svg { --hw-scheme: dark; } }"""
279
+ if "</style>" in svg:
280
+ return svg.replace("</style>", f"{cs_block}\n</style>", 1)
281
+ return svg
282
+
283
+
284
+ def _indent(text: str, spaces: int) -> str:
285
+ """Indent every line by N spaces."""
286
+ pad = " " * spaces
287
+ return "\n".join(f"{pad}{line}" if line.strip() else line for line in text.splitlines())
288
+
289
+
290
+ def generate() -> None:
291
+ total = 0
292
+ dirs = [
293
+ SPECS / "components" / "dividers",
294
+ SPECS / "components" / "icons",
295
+ SPECS / "components" / "banners",
296
+ SPECS / "components" / "marquees",
297
+ SPECS / "motion" / "motion-border-frames",
298
+ SPECS / "motion" / "motion-kinetic-typography",
299
+ ]
300
+
301
+ for d in dirs:
302
+ if not d.exists():
303
+ continue
304
+ svgs = sorted(d.glob("*.svg"))
305
+ if not svgs:
306
+ continue
307
+
308
+ out_dir = d / "hw-compliant"
309
+ out_dir.mkdir(exist_ok=True)
310
+
311
+ for src in svgs:
312
+ wrapped = wrap_specimen(src)
313
+ out = out_dir / src.name
314
+ out.write_text(wrapped, encoding="utf-8")
315
+ total += 1
316
+
317
+ cim_ok, _ = _check_cim(wrapped)
318
+ already = _has_hw_metadata(src.read_text())
319
+ status = "copy" if already else "wrap"
320
+ cim_tag = "CIM" if cim_ok else "NON-CIM"
321
+ print(f" [{status:4s}] [{cim_tag:7s}] {src.relative_to(ROOT)}")
322
+
323
+ print(f"\nWrote {total} hw-compliant specimens.")
324
+
325
+
326
+ if __name__ == "__main__":
327
+ generate()