gravity-cli 0.11.0__tar.gz → 0.12.0__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 (285) hide show
  1. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/AGENT_STANDARD_V2.md +3 -2
  2. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/PKG-INFO +6 -5
  3. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/README.md +4 -3
  4. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/manifest_v2.py +2 -2
  5. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/googlesheets.yaml +9 -0
  6. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/slack.yaml +4 -1
  7. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/pyproject.toml +1 -1
  8. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/pyproject.toml +2 -2
  9. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/BUILDER_GUIDE.md +3 -4
  10. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/BUILDER_GUIDE_V2.md +4 -4
  11. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/CHANGELOG.md +12 -0
  12. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/connect.py +5 -3
  13. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/guide.py +2 -2
  14. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/init.py +1 -3
  15. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/run.py +11 -6
  16. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/dev.py +2 -2
  17. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/dev_page/index.html +2 -2
  18. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/docs/Gravity.agent.md +3 -4
  19. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/minimal/manifest.yaml +9 -0
  20. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/minimal/src/agent.py +5 -1
  21. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_connect.py +1 -1
  22. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_connect_v2.py +25 -1
  23. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_dev_v2.py +9 -0
  24. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_v2_cli.py +3 -2
  25. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/uv.lock +6 -6
  26. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/.env.example +0 -0
  27. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/.github/workflows/ci.yml +0 -0
  28. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/.github/workflows/composio-watch.yml +0 -0
  29. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/.github/workflows/release.yml +0 -0
  30. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/.gitignore +0 -0
  31. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/AGENT_STANDARD.md +0 -0
  32. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/LICENSE +0 -0
  33. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/NOTICE +0 -0
  34. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/RELEASING.md +0 -0
  35. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/TEMPLATES.md +0 -0
  36. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/LICENSE +0 -0
  37. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/NOTICE +0 -0
  38. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/README.md +0 -0
  39. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/__init__.py +0 -0
  40. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/__main__.py +0 -0
  41. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/built_ins.py +0 -0
  42. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/catalog.py +0 -0
  43. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/catalog.yaml +0 -0
  44. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/catalog_imported.yaml +0 -0
  45. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/contract.py +0 -0
  46. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/cron.py +0 -0
  47. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/describe.py +0 -0
  48. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/errors.py +0 -0
  49. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/export.py +0 -0
  50. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/gen_catalog.py +0 -0
  51. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/gen_vocabulary.py +0 -0
  52. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/instance.py +0 -0
  53. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/manifest.py +0 -0
  54. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/rules.py +0 -0
  55. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/rules_cases.json +0 -0
  56. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/source_scan.py +0 -0
  57. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/specs.py +0 -0
  58. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/validation.py +0 -0
  59. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/__init__.py +0 -0
  60. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/__main__.py +0 -0
  61. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/capabilities.yaml +0 -0
  62. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/airtable.yaml +0 -0
  63. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/asana.yaml +0 -0
  64. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/browser_tool.yaml +0 -0
  65. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/composio_search.yaml +0 -0
  66. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/dropbox.yaml +0 -0
  67. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/exa.yaml +0 -0
  68. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/excel.yaml +0 -0
  69. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/firecrawl.yaml +0 -0
  70. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/github.yaml +0 -0
  71. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/gmail.yaml +0 -0
  72. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/googlecalendar.yaml +0 -0
  73. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/googledocs.yaml +0 -0
  74. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/googledrive.yaml +0 -0
  75. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/googleslides.yaml +0 -0
  76. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/googletasks.yaml +0 -0
  77. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/hackernews.yaml +0 -0
  78. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/hubspot.yaml +0 -0
  79. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/instagram.yaml +0 -0
  80. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/jira.yaml +0 -0
  81. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/linear.yaml +0 -0
  82. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/linkedin.yaml +0 -0
  83. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/microsoft_teams.yaml +0 -0
  84. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/notion.yaml +0 -0
  85. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/outlook.yaml +0 -0
  86. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/perplexityai.yaml +0 -0
  87. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/pinterest.yaml +0 -0
  88. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/reddit.yaml +0 -0
  89. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/tavily.yaml +0 -0
  90. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/connectors/youtube.yaml +0 -0
  91. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/core_shapes.yaml +0 -0
  92. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/generated_shapes.yaml +0 -0
  93. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/policy.yaml +0 -0
  94. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/airtable.json +0 -0
  95. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/asana.json +0 -0
  96. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/browser_tool.json +0 -0
  97. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/composio_search.json +0 -0
  98. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/dropbox.json +0 -0
  99. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/exa.json +0 -0
  100. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/excel.json +0 -0
  101. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/firecrawl.json +0 -0
  102. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/github.json +0 -0
  103. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/gmail.json +0 -0
  104. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/googlecalendar.json +0 -0
  105. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/googledocs.json +0 -0
  106. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/googledrive.json +0 -0
  107. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/googlesheets.json +0 -0
  108. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/googleslides.json +0 -0
  109. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/googletasks.json +0 -0
  110. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/hackernews.json +0 -0
  111. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/hubspot.json +0 -0
  112. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/instagram.json +0 -0
  113. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/jira.json +0 -0
  114. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/linear.json +0 -0
  115. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/linkedin.json +0 -0
  116. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/microsoft_teams.json +0 -0
  117. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/notion.json +0 -0
  118. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/outlook.json +0 -0
  119. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/perplexityai.json +0 -0
  120. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/pinterest.json +0 -0
  121. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/reddit.json +0 -0
  122. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/slack.json +0 -0
  123. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/tavily.json +0 -0
  124. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas/youtube.json +0 -0
  125. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/schemas.py +0 -0
  126. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/shapes.d/ochat.yaml +0 -0
  127. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/shapes.d/ocrm.yaml +0 -0
  128. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/shapes.d/ogh.yaml +0 -0
  129. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/shapes.d/oms.yaml +0 -0
  130. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/shapes.d/oweb.yaml +0 -0
  131. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/shapes.d/owork.yaml +0 -0
  132. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/shapes.d/shared.yaml +0 -0
  133. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/sync.py +0 -0
  134. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/ochat.yaml +0 -0
  135. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/ocrm.yaml +0 -0
  136. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/ogh.yaml +0 -0
  137. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/oms.yaml +0 -0
  138. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/oweb.yaml +0 -0
  139. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/owork.yaml +0 -0
  140. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/rchat.yaml +0 -0
  141. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/rfiles.yaml +0 -0
  142. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/rgh.yaml +0 -0
  143. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/rtrack.yaml +0 -0
  144. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.d/rwork.yaml +0 -0
  145. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/gravity_schema/vocabulary/verbs.yaml +0 -0
  146. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/schema/manifest.schema.json +0 -0
  147. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/conftest.py +0 -0
  148. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/fixtures/demo_manifests.yaml +0 -0
  149. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_accounts.py +0 -0
  150. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_actions_memory.py +0 -0
  151. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_catalog_parity.py +0 -0
  152. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_cron.py +0 -0
  153. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_describe.py +0 -0
  154. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_errors.py +0 -0
  155. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_generated_tables.py +0 -0
  156. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_instance.py +0 -0
  157. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_json_schema.py +0 -0
  158. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_kind_outputs.py +0 -0
  159. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_manifest.py +0 -0
  160. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_manifest_v2.py +0 -0
  161. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_place_maker.py +0 -0
  162. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_rules.py +0 -0
  163. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_slots.py +0 -0
  164. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_source_scan.py +0 -0
  165. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_sync.py +0 -0
  166. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_validation.py +0 -0
  167. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/packages/gravity-schema/tests/test_vocabulary.py +0 -0
  168. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/scripts/composio-watch.sh +0 -0
  169. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/__init__.py +0 -0
  170. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/__main__.py +0 -0
  171. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/_runner_script.py +0 -0
  172. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/api.py +0 -0
  173. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/changelog.py +0 -0
  174. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/cli.py +0 -0
  175. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/__init__.py +0 -0
  176. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/adapt.py +0 -0
  177. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/build.py +0 -0
  178. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/capabilities.py +0 -0
  179. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/changelog.py +0 -0
  180. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/check.py +0 -0
  181. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/dev.py +0 -0
  182. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/docs.py +0 -0
  183. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/help.py +0 -0
  184. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/login.py +0 -0
  185. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/memory.py +0 -0
  186. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/push.py +0 -0
  187. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/runs.py +0 -0
  188. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/schedule.py +0 -0
  189. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/tools.py +0 -0
  190. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/update.py +0 -0
  191. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/commands/validate.py +0 -0
  192. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/config.py +0 -0
  193. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/docs/Gravity.getting-started.md +0 -0
  194. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/docs/problem-to-agent.md +0 -0
  195. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/inputs.py +0 -0
  196. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/localrun.py +0 -0
  197. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/manifest.py +0 -0
  198. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/project.py +0 -0
  199. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/chat/.gitignore +0 -0
  200. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/chat/manifest.yaml +0 -0
  201. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/chat/requirements.txt +0 -0
  202. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/chat/src/agent.py +0 -0
  203. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/deepagent/.gitignore +0 -0
  204. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/deepagent/manifest.yaml +0 -0
  205. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/deepagent/requirements.txt +0 -0
  206. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/deepagent/src/agent.py +0 -0
  207. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/minimal/.gitignore +0 -0
  208. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/minimal/manifest.yaml +0 -0
  209. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/minimal/requirements.txt +0 -0
  210. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/minimal/src/agent.py +0 -0
  211. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/.gitignore +0 -0
  212. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/manifest.yaml +0 -0
  213. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/requirements.txt +0 -0
  214. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/src/agent.py +0 -0
  215. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/src/gateway.py +0 -0
  216. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/src/nodes/agent.py +0 -0
  217. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/src/prompts.py +0 -0
  218. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/structured/src/state.py +0 -0
  219. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/chat/.gitignore +0 -0
  220. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/chat/manifest.yaml +0 -0
  221. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/chat/requirements.txt +0 -0
  222. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/chat/src/agent.py +0 -0
  223. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/chat/tests/test_agent.py +0 -0
  224. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/deepagent/.gitignore +0 -0
  225. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/deepagent/manifest.yaml +0 -0
  226. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/deepagent/requirements.txt +0 -0
  227. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/deepagent/src/agent.py +0 -0
  228. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/deepagent/tests/test_agent.py +0 -0
  229. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/minimal/.gitignore +0 -0
  230. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/minimal/requirements.txt +0 -0
  231. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/minimal/tests/test_agent.py +0 -0
  232. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/.gitignore +0 -0
  233. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/manifest.yaml +0 -0
  234. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/requirements.txt +0 -0
  235. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/src/__init__.py +0 -0
  236. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/src/agent.py +0 -0
  237. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/src/gateway.py +0 -0
  238. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/src/nodes/__init__.py +0 -0
  239. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/src/nodes/agent.py +0 -0
  240. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/src/prompts.py +0 -0
  241. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/src/state.py +0 -0
  242. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/templates/v2/structured/tests/test_agent.py +0 -0
  243. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/timeline.py +0 -0
  244. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/ui.py +0 -0
  245. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/updater.py +0 -0
  246. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/src/gravity_cli/workspace.py +0 -0
  247. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter/manifest.yaml +0 -0
  248. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter/requirements.txt +0 -0
  249. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter/src/agent.py +0 -0
  250. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter/src/summary.py +0 -0
  251. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter/tests/test_summary.py +0 -0
  252. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter-v2/manifest.yaml +0 -0
  253. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter-v2/requirements.txt +0 -0
  254. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter-v2/src/agent.py +0 -0
  255. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter-v2/src/summary.py +0 -0
  256. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/starter-v2/tests/test_summary.py +0 -0
  257. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/conftest.py +0 -0
  258. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_adapt.py +0 -0
  259. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_agent_guide.py +0 -0
  260. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_agents.py +0 -0
  261. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_api.py +0 -0
  262. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_build_push.py +0 -0
  263. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_changelog.py +0 -0
  264. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_check.py +0 -0
  265. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_dev.py +0 -0
  266. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_gateway_token.py +0 -0
  267. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_inputs_memory.py +0 -0
  268. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_localrun.py +0 -0
  269. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_manifest_integration.py +0 -0
  270. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_run.py +0 -0
  271. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_run_v2.py +0 -0
  272. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_runs.py +0 -0
  273. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_schedule.py +0 -0
  274. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_schedule_v2.py +0 -0
  275. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_session.py +0 -0
  276. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_templates.py +0 -0
  277. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_templates_v2.py +0 -0
  278. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_timeline.py +0 -0
  279. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_tools.py +0 -0
  280. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_ui.py +0 -0
  281. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_updater.py +0 -0
  282. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_validate.py +0 -0
  283. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_validate_v2.py +0 -0
  284. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_welcome.py +0 -0
  285. {gravity_cli-0.11.0 → gravity_cli-0.12.0}/tests/test_workspace.py +0 -0
@@ -16,7 +16,7 @@ that package disagree, the package wins and this document has a bug.
16
16
  (`issue.list`) and what it changes (`issue.create`); the consumer picks the
17
17
  app — Linear, Jira, Asana — when they set it up. `contract: v1` manifests
18
18
  (tool names) are still accepted while the platform moves to v2; their standard is
19
- AGENT_STANDARD.md. **v2 is a preview:** it runs only against a gateway that serves v2.
19
+ AGENT_STANDARD.md. Gravity runs both.
20
20
 
21
21
  ## 1. Layout
22
22
 
@@ -373,7 +373,8 @@ outputs: # what the consumer may ask the result to become
373
373
  capability that takes its rendering — markdown: `message.send`,
374
374
  `message.create`, `document.create`, `issue.create`, `comment.create`,
375
375
  `post.create`, `file.create`; docx and pptx: `file.create`, `message.send`
376
- (and `presentation.create` for a deck); rows: `row.append`, `file.create`.
376
+ (and `presentation.create` for a deck); rows: `row.append`, `spreadsheet.create`,
377
+ `file.create`; xlsx: `file.create`, `spreadsheet.create` (a new Google Sheet, every table a tab).
377
378
  `default` (expected; `gravity validate` warns without it) is where it goes
378
379
  unless the consumer picks otherwise: a download, or a destination and its
379
380
  app. The consumer can change it, and picks the place (a Slack channel, a
@@ -1,12 +1,12 @@
1
1
  Metadata-Version: 2.5
2
2
  Name: gravity-cli
3
- Version: 0.11.0
3
+ Version: 0.12.0
4
4
  Summary: gravity cli — init, run, and push python agents to the Gravity marketplace
5
5
  License-Expression: Apache-2.0
6
6
  License-File: LICENSE
7
7
  License-File: NOTICE
8
8
  Requires-Python: >=3.12
9
- Requires-Dist: gravity-schema==0.11.0
9
+ Requires-Dist: gravity-schema==0.12.0
10
10
  Requires-Dist: httpx>=0.27.0
11
11
  Requires-Dist: keyring>=25.0.0
12
12
  Requires-Dist: python-dotenv>=1.0.0
@@ -756,17 +756,18 @@ outputs: # extra formats the platform renders and deliv
756
756
 
757
757
  Unknown fields are rejected rather than ignored, so a typo is reported instead of silently dropped.
758
758
 
759
- ### Contract v2 (preview)
759
+ ### Contract v2
760
760
 
761
761
  The CLI also reads `contract: v2` manifests, where an agent names **capabilities** (`message.list`, `issue.create`)
762
762
  instead of tools, and the person picks the app when they set it up: Gmail or Outlook, Linear or Jira. What it reads
763
763
  goes under `sources`, what it changes under `writes`; code calls `gravity.read("inbox")` and `gravity.act("send", ...)`.
764
- v2 runs only against a gateway that serves it, and Gravity's hosted gateway runs v1 for now.
764
+ Gravity runs both contracts. A v2 agent runs once a consumer has set it up (their app and place for each source,
765
+ write and output); `gravity init` stays on v1 by default until that setup page is on the web app.
765
766
 
766
767
  ```bash
767
768
  gravity init my-agent --contract v2 # the v2 templates
768
769
  gravity capabilities message # what exists, and which apps serve it
769
- gravity check message.list --app gmail # try one on your own account (v2 gateway)
770
+ gravity check message.list --app gmail # try one on your own account
770
771
  gravity run --use inbox=outlook # pick the app for a local run
771
772
  gravity guide --contract v2 # the v2 guide; the rules are in AGENT_STANDARD_V2.md
772
773
  ```
@@ -739,17 +739,18 @@ outputs: # extra formats the platform renders and deliv
739
739
 
740
740
  Unknown fields are rejected rather than ignored, so a typo is reported instead of silently dropped.
741
741
 
742
- ### Contract v2 (preview)
742
+ ### Contract v2
743
743
 
744
744
  The CLI also reads `contract: v2` manifests, where an agent names **capabilities** (`message.list`, `issue.create`)
745
745
  instead of tools, and the person picks the app when they set it up: Gmail or Outlook, Linear or Jira. What it reads
746
746
  goes under `sources`, what it changes under `writes`; code calls `gravity.read("inbox")` and `gravity.act("send", ...)`.
747
- v2 runs only against a gateway that serves it, and Gravity's hosted gateway runs v1 for now.
747
+ Gravity runs both contracts. A v2 agent runs once a consumer has set it up (their app and place for each source,
748
+ write and output); `gravity init` stays on v1 by default until that setup page is on the web app.
748
749
 
749
750
  ```bash
750
751
  gravity init my-agent --contract v2 # the v2 templates
751
752
  gravity capabilities message # what exists, and which apps serve it
752
- gravity check message.list --app gmail # try one on your own account (v2 gateway)
753
+ gravity check message.list --app gmail # try one on your own account
753
754
  gravity run --use inbox=outlook # pick the app for a local run
754
755
  gravity guide --contract v2 # the v2 guide; the rules are in AGENT_STANDARD_V2.md
755
756
  ```
@@ -54,8 +54,8 @@ RENDERER_DESTINATIONS: dict[Renderer, tuple[str, ...]] = {
54
54
  Renderer.DOCX: ("file.create", "document.create", "message.send"),
55
55
  Renderer.PPTX: ("file.create", "presentation.create", "message.send"),
56
56
  Renderer.PDF: ("file.create", "message.send"),
57
- Renderer.ROWS: ("row.append", "file.create"),
58
- Renderer.XLSX: ("file.create",),
57
+ Renderer.ROWS: ("row.append", "spreadsheet.create", "file.create"),
58
+ Renderer.XLSX: ("file.create", "spreadsheet.create"),
59
59
  }
60
60
 
61
61
  # A filter on one of these fields takes one of the shape's listed values.
@@ -537,10 +537,19 @@ writes:
537
537
  args: {spreadsheet_id: "{target}", ranges: ["{sheet ?? ='Sheet1'}"]}
538
538
  check: rows_present
539
539
  spreadsheet.create:
540
+ # draft.tables (optional), each {name, range, values}: an output delivered as a new spreadsheet, every table a tab.
541
+ # The first fills the tab a new spreadsheet comes with (its range names no tab: "A1", whatever the locale calls
542
+ # it); each later one gets its own tab first. values: the header line, then the table's lines
540
543
  steps:
541
544
  - action: GOOGLESHEETS_CREATE_GOOGLE_SHEET1
542
545
  args: {title: "{draft.title}"}
543
546
  save: {id: "data.response_data.spreadsheetId ?? data.spreadsheetId", link: "data.response_data.spreadsheetUrl ?? data.spreadsheetUrl"}
547
+ - action: GOOGLESHEETS_ADD_SHEET
548
+ each: draft.tables|rest
549
+ args: {spreadsheet_id: "{id}", title: "{item.name}"}
550
+ - action: GOOGLESHEETS_SPREADSHEETS_VALUES_APPEND
551
+ each: draft.tables
552
+ args: {spreadsheetId: "{id}", range: "{item.range}", valueInputOption: RAW, values: "{item.values}"}
544
553
  returns: {id: id, title: draft.title, link: link}
545
554
  # verified live 2026-10-12
546
555
  row.update: &sheet_row_update
@@ -1397,7 +1397,10 @@ writes:
1397
1397
  target: {resource: channel, label: Channel}
1398
1398
  steps:
1399
1399
  - action: SLACK_SEND_MESSAGE
1400
- args: {channel: "{target}", markdown_text: "{draft.text}", thread_ts: "{draft.thread}"}
1400
+ # a draft with `blocks` (Gravity's digest, pictures and all) posts them, its text only as their fallback:
1401
+ # Slack takes markdown_text or blocks, never both
1402
+ args: {channel: "{target}", markdown_text: "{draft|text_unless_blocks}", blocks: "{draft.blocks}",
1403
+ fallback_text: "{draft|text_if_blocks}", thread_ts: "{draft.thread}"}
1401
1404
  save: {id: "data.ts ?? data.message.ts", channel: "data.channel ?? ={target}"}
1402
1405
  returns: {id: id, channel: channel, text: draft.text}
1403
1406
  read_back:
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "gravity-schema"
3
- version = "0.11.0"
3
+ version = "0.12.0"
4
4
  description = "Gravity agent manifest contract — models, validation, and JSON Schema export"
5
5
  readme = "README.md"
6
6
  license = "Apache-2.0"
@@ -1,13 +1,13 @@
1
1
  [project]
2
2
  name = "gravity-cli"
3
- version = "0.11.0"
3
+ version = "0.12.0"
4
4
  description = "gravity cli — init, run, and push python agents to the Gravity marketplace"
5
5
  readme = "README.md"
6
6
  license = "Apache-2.0"
7
7
  license-files = ["LICENSE", "NOTICE"]
8
8
  requires-python = ">=3.12"
9
9
  dependencies = [
10
- "gravity-schema==0.11.0", # released in lockstep: always the same version as this package
10
+ "gravity-schema==0.12.0", # released in lockstep: always the same version as this package
11
11
  "typer>=0.15.0",
12
12
  "httpx>=0.27.0",
13
13
  "rich>=13.9.0",
@@ -869,9 +869,8 @@ see, locally or hosted:
869
869
  - [ ] `gravity validate` passes and a `gravity run` (or `gravity dev` run) produced the result you expect (§8, §9)
870
870
  - [ ] No keys or secrets anywhere; nothing your code needs lives outside `src/` and `tests/`
871
871
 
872
- ## 12. Contract v2 (preview)
872
+ ## 12. Contract v2
873
873
 
874
- This guide is contract v1, what Gravity runs today. Contract v2 names what an agent reads and changes as
875
- capabilities (`message.list`, `issue.create`) instead of tools, and the person picks the app at setup. It runs only
876
- against a gateway that serves v2. Its guide is `gravity guide --contract v2`, and `gravity init my-agent --contract v2`
874
+ This guide is contract v1. Contract v2 names what an agent reads and changes as capabilities (`message.list`,
875
+ `issue.create`) instead of tools, and the person picks the app at setup. Gravity runs both. Its guide is `gravity guide --contract v2`, and `gravity init my-agent --contract v2`
877
876
  starts one.
@@ -1,8 +1,8 @@
1
- # Build an agent for Gravity: contract v2 (preview)
1
+ # Build an agent for Gravity: contract v2
2
2
 
3
- > **Preview.** Contract v2 runs only against a gateway that serves it; Gravity's hosted gateway runs contract v1
4
- > for now, and `gravity guide` (without `--contract v2`) is v1's guide. Start a v2 agent with
5
- > `gravity init my-agent --contract v2`. Everything else here is how v2 works once your gateway serves it.
3
+ > Gravity runs contract v1 and v2; `gravity guide` (without `--contract v2`) is v1's guide. Start a v2 agent with
4
+ > `gravity init my-agent --contract v2`. A v2 agent runs once its consumer has set it up: their app and place for
5
+ > each source, write and output.
6
6
 
7
7
  Everything you need to build, test and submit a Gravity agent, in the order you'll do it. What you can use on
8
8
  which app is in `gravity capabilities`; the exact rules are in `AGENT_STANDARD_V2.md` in the gravity-cli repo.
@@ -4,6 +4,18 @@ Shown by `gravity update` and `gravity changelog`, and after an update. Each rel
4
4
  then one bullet per change: `- new|improved|fixed: A one-line headline. The detail behind it.`
5
5
  Write it for a builder, not for a maintainer. `tests/test_changelog.py` fails a release that has no entry.
6
6
 
7
+ ## 0.12.0 - 2026-10-31
8
+
9
+ - new: Contract v2 is no longer a preview: Gravity's hosted platform runs v1 and v2 agents side by side. A v2 agent runs once its consumer has set it up (their app and place for each source, write and output). `gravity init` still starts v1 unless you pass `--contract v2`.
10
+ - new: A v2 output can go to a new Google Sheet: `spreadsheet.create` takes a `rows` or `xlsx` output and makes a spreadsheet with a tab for every table in your corpus.
11
+ - improved: A v2 output sent to Slack posts the same digest Gravity shows (headings, tables, pictures as Slack blocks), not a plain-text copy.
12
+ - improved: The v2 minimal template shows how to declare an output and return the corpus it's rendered from; an output without a corpus fails at delivery.
13
+
14
+ ## 0.11.1 - 2026-10-31
15
+
16
+ - fixed: `gravity connect sheets` (and the other v1 app names) works again on a gateway that serves both contracts. 0.9.0 through 0.11.0 took the v2 path on any gateway that served v2, where v1's names aren't apps; now only a v2-only gateway gets it.
17
+ - fixed: Light and dark mode's secondary text on the local dashboard has enough contrast to read, and a v1 gateway's error there says what to do about it.
18
+
7
19
  ## 0.11.0 - 2026-10-30
8
20
 
9
21
  - new: Show progress while your agent runs. Write `{"note": "Scoring 12 candidates"}` or `{"partial": {"key": "candidates", "items": [...]}}` with LangGraph's `get_stream_writer()` from any node: `gravity run` and `gravity dev` show each note as a line and the results so far, as the run page on Gravity does. See "Progress while it runs" in Gravity.agent.md.
@@ -1,7 +1,9 @@
1
1
  """gravity connect: link your own accounts (Gmail, Slack...) so your agents' runs can use them.
2
2
 
3
3
  Through the gateway, as the account your gateway token belongs to. Two gateway protocols, told apart by the
4
- gateway's GET /healthz (`gateway_v2`):
4
+ gateway's GET /healthz (`gateway_contracts`). A gateway that still serves v1 is asked the v1 way, whatever the
5
+ agent: v1's app names (sheets, calendar) keep working, and it connects the same Composio account v2 runs use.
6
+ Only a gateway that serves v2 alone is asked the v2 way:
5
7
 
6
8
  v1 (tool names): GET /connections -> {"user", "connected": [toolkit]}; POST /connections {"toolkit"} ->
7
9
  {"redirect_url", "toolkit", "already_connected"}. App names as tool names spell them (gmail, sheets).
@@ -22,7 +24,7 @@ from gravity_schema import VOCABULARY
22
24
 
23
25
  from .. import Problem, ui
24
26
  from .login import gateway_token, token_fix
25
- from .run import gateway_urls, gateway_v2
27
+ from .run import gateway_contracts, gateway_urls
26
28
 
27
29
  WAIT_SECONDS = 300
28
30
  POLL_SECONDS = 3
@@ -204,4 +206,4 @@ def connect_command(
204
206
  app: str = typer.Argument(None, help="The app: gmail, slack, sheets, calendar, linear, github..."),
205
207
  ):
206
208
  """Connect an account your agents' tools act on. With no app, list what is connected."""
207
- (_connect_v2 if gateway_v2() else _connect_v1)(app)
209
+ (_connect_v2 if gateway_contracts() == {"v2"} else _connect_v1)(app)
@@ -10,13 +10,13 @@ from gravity_schema import CONTRACT_V1, CONTRACT_V2
10
10
  from .. import Problem, ui
11
11
 
12
12
  GUIDE = Path(__file__).parent.parent / "BUILDER_GUIDE.md" # ships inside the package
13
- GUIDE_V2 = GUIDE.with_name("BUILDER_GUIDE_V2.md") # contract v2, a preview
13
+ GUIDE_V2 = GUIDE.with_name("BUILDER_GUIDE_V2.md") # contract v2
14
14
 
15
15
 
16
16
  def guide_command(
17
17
  save: bool = typer.Option(False, "--save", help="Write the guide to the current folder instead of showing it"),
18
18
  contract: Annotated[str, typer.Option(
19
- "--contract", metavar="v1|v2", help="v1 (tools, what the platform runs today) or v2 (capabilities, a preview)",
19
+ "--contract", metavar="v1|v2", help="v1 (tools) or v2 (capabilities, the app picked at setup)",
20
20
  )] = CONTRACT_V1,
21
21
  ):
22
22
  """How to build a good agent: the builder guide."""
@@ -48,8 +48,7 @@ def init_command(
48
48
  # Annotated, so a call from Python (the welcome's first agent, tests) gets the plain default.
49
49
  contract: Annotated[str, typer.Option(
50
50
  "--contract", metavar="v1|v2",
51
- help="v1 names the tools the agent calls; v2 names capabilities and the user picks the app (preview: "
52
- "needs a gateway that runs v2)",
51
+ help="v1 names the tools the agent calls; v2 names capabilities and the user picks the app at setup",
53
52
  )] = CONTRACT_V1,
54
53
  ):
55
54
  """Scaffold a working agent: manifest, pinned deps and a src/agent.py that runs."""
@@ -99,6 +98,5 @@ def init_command(
99
98
  workspace.refresh(dest)
100
99
  install = "uv venv && uv pip install -r requirements.txt"
101
100
  if contract == CONTRACT_V2:
102
- ui.note("Contract v2 is a preview: it runs only against a gateway that serves v2.")
103
101
  install += f" && {SDK_INSTALL}"
104
102
  ui.next_steps(f"cd {name}", install, 'gravity run --input query="hello"')
@@ -38,9 +38,9 @@ def gateway_urls() -> tuple[str, str]:
38
38
  return url, url.rstrip("/").removesuffix("/mcp")
39
39
 
40
40
 
41
- def gateway_v2(base: str | None = None) -> bool:
42
- """Does the gateway serve contract v2? One that says so lists "v2" in /healthz `contracts`; until then a v1
43
- gateway is the one whose /healthz lists the `tools` it serves."""
41
+ def gateway_contracts(base: str | None = None) -> frozenset[str]:
42
+ """The contracts the gateway serves: what /healthz lists in `contracts`; before it said, a v1 gateway is the
43
+ one whose /healthz lists the `tools` it serves, and anything else v2 only."""
44
44
  base = base or gateway_urls()[1]
45
45
  try:
46
46
  resp = httpx.get(f"{base}/healthz", timeout=10)
@@ -48,10 +48,15 @@ def gateway_v2(base: str | None = None) -> bool:
48
48
  except (httpx.HTTPError, ValueError):
49
49
  health = None
50
50
  if not isinstance(health, dict):
51
- return False # unreachable or not a gateway's answer: the first real call reports it, in v1's words
51
+ return frozenset({"v1"}) # unreachable or not a gateway's answer: the first real call reports it, in v1's words
52
52
  if isinstance(health.get("contracts"), list):
53
- return "v2" in health["contracts"]
54
- return "tools" not in health
53
+ return frozenset(map(str, health["contracts"]))
54
+ return frozenset({"v1"} if "tools" in health else {"v2"})
55
+
56
+
57
+ def gateway_v2(base: str | None = None) -> bool:
58
+ """Does the gateway run contract v2 agents?"""
59
+ return "v2" in gateway_contracts(base)
55
60
 
56
61
 
57
62
  V1_GATEWAY = ("This agent is contract v2, and the gateway at {base} runs contract v1",
@@ -199,8 +199,8 @@ class DevState:
199
199
  "needed": [{"toolkit": t, "connected": t in connected} for t in wanted]}
200
200
  else:
201
201
  if not run_cmd.gateway_v2(base):
202
- title, detail, _ = run_cmd.V1_GATEWAY
203
- raise Problem(title.format(base=base), detail)
202
+ title, detail, fix = run_cmd.V1_GATEWAY
203
+ raise Problem(title.format(base=base), detail, fix)
204
204
  picked = self._picks(m)
205
205
  wanted = sorted({p.app for section in (picked.sources, picked.writes) for p in section.values() if p.app})
206
206
  statuses = []
@@ -7,14 +7,14 @@
7
7
  <title>Gravity · local dashboard</title>
8
8
  <style>
9
9
  :root {
10
- --bg: #f8eef1; --surface: #fffafb; --surface-2: #fdf4f6; --ink: #2b2126; --ink-2: #5d4a52; --muted: #957a84;
10
+ --bg: #f8eef1; --surface: #fffafb; --surface-2: #fdf4f6; --ink: #2b2126; --ink-2: #5d4a52; --muted: #7f656f;
11
11
  --line: rgba(43, 33, 38, 0.12); --primary: #F8B300; --primary-deep: #a87700; --primary-soft: #fdf1cc;
12
12
  --ok: #3f7d43; --ok-soft: #eef6ee; --bad: #b53a25; --bad-soft: #fdece7; --code: #f3e6ea;
13
13
  --serif: Georgia, "Times New Roman", serif; --sans: ui-sans-serif, system-ui, -apple-system, "Segoe UI", sans-serif;
14
14
  --mono: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
15
15
  }
16
16
  @media (prefers-color-scheme: dark) {
17
- :root { --bg: #1d1618; --surface: #261d20; --surface-2: #2c2226; --ink: #f3e9ec; --ink-2: #cdb9c0; --muted: #9c838c;
17
+ :root { --bg: #1d1618; --surface: #261d20; --surface-2: #2c2226; --ink: #f3e9ec; --ink-2: #cdb9c0; --muted: #aa949c;
18
18
  --line: rgba(255, 255, 255, 0.12); --primary-deep: #f0b93a; --primary-soft: #3a2f12; --ok: #7bc47f; --ok-soft: #1f2e20;
19
19
  --bad: #f08a77; --bad-soft: #3a1f1a; --code: #33282c; }
20
20
  }
@@ -1155,11 +1155,10 @@ your folder: read them as examples of structure, and follow the method.
1155
1155
  - [ ] `gravity validate` passes; a `gravity run` or `gravity dev` run produced the result you expect
1156
1156
  - [ ] No keys or secrets in any file; nothing the code needs lives outside `src/` and `tests/`
1157
1157
 
1158
- ## 17. Contract v2 (preview): capabilities instead of tools
1158
+ ## 17. Contract v2: capabilities instead of tools
1159
1159
 
1160
- Everything above is contract v1, which is what Gravity's hosted platform runs. Contract v2 is a preview: build on it
1161
- only when the person says their gateway serves v2 (`gravity connect` and `gravity check` work against it). The CLI
1162
- reads both, picked by the manifest's `contract`; `gravity guide --contract v2` is the full v2 guide and
1160
+ Everything above is contract v1. Gravity's hosted platform runs v1 and v2; build on v2 when the person asks for it
1161
+ (`gravity init --contract v2`), else stay on v1. The CLI reads both, picked by the manifest's `contract`; `gravity guide --contract v2` is the full v2 guide and
1163
1162
  `AGENT_STANDARD_V2.md` its exact rules.
1164
1163
 
1165
1164
  In v2 the manifest never names an app or a tool. It names **capabilities**, `<shape>.<verb>` (`message.list`,
@@ -38,6 +38,15 @@ models:
38
38
  # label: "Where follow-ups go"
39
39
  # approvals:
40
40
  # required_for: [issue.create] # each call waits for the consumer's yes
41
+ #
42
+ # What the result can become, delivered by Gravity after the run (the agent declares no write for it). An agent with
43
+ # outputs returns a corpus in its final state (see src/agent.py); without one the delivery fails.
44
+ # outputs:
45
+ # summary:
46
+ # renderer: markdown # markdown | docx | pptx | pdf | rows | xlsx
47
+ # label: "Summary"
48
+ # destinations: [download, message.send]
49
+ # default: {destination: message.send, app: gmail}
41
50
 
42
51
  resources:
43
52
  memory_mb: 512 # a request — the platform clamps, never guarantees
@@ -13,6 +13,7 @@ from langgraph.prebuilt import create_react_agent
13
13
  class State(TypedDict):
14
14
  inputs: dict
15
15
  result: str
16
+ corpus: dict # what the manifest's outputs are rendered from (unused without outputs)
16
17
 
17
18
 
18
19
  # ← manifest.runtime.entrypoint. An async factory the runner calls per run; building the
@@ -41,7 +42,10 @@ async def graph():
41
42
  async def run_agent(state: State):
42
43
  query = state["inputs"].get("query", "")
43
44
  result = await react.ainvoke({"messages": [{"role": "user", "content": query}]})
44
- return {"result": result["messages"][-1].content}
45
+ text = result["messages"][-1].content
46
+ # With `outputs` in the manifest, return the corpus they're rendered from as well:
47
+ # return {**gravity.Corpus(title="Summary", summary=text).to_state(), "result": text}
48
+ return {"result": text}
45
49
 
46
50
  workflow = StateGraph(State)
47
51
  workflow.add_node("agent", run_agent)
@@ -12,7 +12,7 @@ from gravity_cli.commands import connect
12
12
  @pytest.fixture(autouse=True)
13
13
  def v1_gateway(monkeypatch):
14
14
  """These tests are the v1 gateway's protocol; test_connect_v2.py has v2's."""
15
- monkeypatch.setattr(connect, "gateway_v2", lambda: False)
15
+ monkeypatch.setattr(connect, "gateway_contracts", lambda: frozenset({"v1"}))
16
16
 
17
17
 
18
18
  @pytest.fixture
@@ -12,7 +12,7 @@ from gravity_cli.commands import connect
12
12
  @pytest.fixture(autouse=True)
13
13
  def v2_gateway(monkeypatch):
14
14
  """These tests are the v2 protocol's; test_connect.py has the v1 gateway's."""
15
- monkeypatch.setattr(connect, "gateway_v2", lambda: True)
15
+ monkeypatch.setattr(connect, "gateway_contracts", lambda: frozenset({"v2"}))
16
16
 
17
17
 
18
18
  @pytest.fixture
@@ -183,3 +183,27 @@ def test_which_protocol_the_gateway_speaks(monkeypatch, status, body, v2):
183
183
  monkeypatch.setattr(run, "gateway_urls", lambda: ("https://gw/mcp", "https://gw"))
184
184
  monkeypatch.setattr(run.httpx, "get", lambda url, timeout: Resp(status, body))
185
185
  assert run.gateway_v2() is v2
186
+
187
+
188
+ def test_a_gateway_that_serves_both_connects_the_v1_way(monkeypatch):
189
+ """Once the gateway runs v1 and v2, `gravity connect sheets` (v1's app name) must keep working: it is asked the
190
+ v1 way, which knows v1's names and Composio's, and connects the account v2 runs use too."""
191
+ asked = []
192
+ monkeypatch.setattr(connect, "gateway_contracts", lambda: frozenset({"v1", "v2"}))
193
+ monkeypatch.setattr(connect, "_connect_v1", lambda app: asked.append(("v1", app)))
194
+ monkeypatch.setattr(connect, "_connect_v2", lambda app: asked.append(("v2", app)))
195
+ connect.connect_command("sheets")
196
+ assert asked == [("v1", "sheets")]
197
+
198
+
199
+ @pytest.mark.parametrize(("body", "served"), [
200
+ ({"ok": True, "tools": ["example.echo"]}, {"v1"}),
201
+ ({"ok": True}, {"v2"}),
202
+ ({"ok": True, "tools": ["example.echo"], "contracts": ["v1", "v2"]}, {"v1", "v2"}),
203
+ ])
204
+ def test_which_contracts_the_gateway_serves(monkeypatch, body, served):
205
+ from gravity_cli.commands import run
206
+
207
+ monkeypatch.setattr(run, "gateway_urls", lambda: ("https://gw/mcp", "https://gw"))
208
+ monkeypatch.setattr(run.httpx, "get", lambda url, timeout: Resp(200, body))
209
+ assert run.gateway_contracts() == served
@@ -185,6 +185,15 @@ def test_gateway_info_says_which_apps_the_runs_use_are_connected(server, gateway
185
185
  assert ("POST", "http://gw.test/connections", {"apps": ["googletasks", "linear"]}) in gateway
186
186
 
187
187
 
188
+ def test_a_v1_gateway_says_what_to_do_about_it(server, gateway, monkeypatch):
189
+ """The Accounts card's error for a gateway that runs only v1 names the way out, as the CLI's does."""
190
+ monkeypatch.setattr(run_cmd, "gateway_v2", lambda base=None: False)
191
+ client, _ = server
192
+ info = client.get("/api/gateway").json()
193
+ assert not info["ok"] and "runs contract v1" in info["error"]
194
+ assert "GRAVITY_GATEWAY_URL" in info["error"] and "keep the agent on contract v1" in info["error"]
195
+
196
+
188
197
  def test_connect_goes_to_the_gateway_and_rejects_an_unknown_app(server, gateway):
189
198
  client, _ = server
190
199
  assert client.post("/api/connections", json={"app": "Gmail; drop"}).status_code == 400
@@ -23,10 +23,11 @@ def test_templates_are_v2_and_their_example_is_valid_when_uncommented(tmp_path,
23
23
  (tmp_path / "manifest.yaml").write_text(text, encoding="utf-8")
24
24
  assert load_manifest(tmp_path / "manifest.yaml").contract == "v2"
25
25
  # the commented example, uncommented, is a valid manifest too: it names real capabilities
26
- example = re.sub(r"^# (sources:|writes:|approvals:| .*)$", r"\1", text, flags=re.MULTILINE)
26
+ example = re.sub(r"^# (sources:|writes:|approvals:|outputs:| .*)$", r"\1", text, flags=re.MULTILINE)
27
27
  (tmp_path / "manifest.yaml").write_text(example, encoding="utf-8")
28
28
  m = load_manifest(tmp_path / "manifest.yaml")
29
- assert m.capabilities == {"issue.list", "issue.create"} and m.approvals.required_for == ["issue.create"]
29
+ output = {"message.send"} if template == "minimal" else set() # the one that shows an output, sent by mail
30
+ assert m.capabilities == {"issue.list", "issue.create", *output} and m.approvals.required_for == ["issue.create"]
30
31
 
31
32
 
32
33
  STARTER = Path(__file__).resolve().parents[1] / "starter-v2" # the contract v2 example; starter/ is v1
@@ -59,7 +59,7 @@ name = "cffi"
59
59
  version = "2.1.1"
60
60
  source = { registry = "https://pypi.org/simple" }
61
61
  dependencies = [
62
- { name = "pycparser", marker = "implementation_name != 'PyPy' and sys_platform != 'win32'" },
62
+ { name = "pycparser", marker = "implementation_name != 'PyPy'" },
63
63
  ]
64
64
  sdist = { url = "https://files.pythonhosted.org/packages/9e/ef/008a1939e372c06329a3fce4279c02f328488f3526744906eeec3da7ad5f/cffi-2.1.1.tar.gz", hash = "sha256:dd31f52ea1086513bb9df30f8fcee9b8918323ae067a3d5b78bc826a000712be", size = 530807, upload-time = "2026-08-03T21:21:18.939Z" }
65
65
  wheels = [
@@ -123,7 +123,7 @@ name = "cryptography"
123
123
  version = "50.0.0"
124
124
  source = { registry = "https://pypi.org/simple" }
125
125
  dependencies = [
126
- { name = "cffi", marker = "platform_python_implementation != 'PyPy' and sys_platform != 'win32'" },
126
+ { name = "cffi", marker = "platform_python_implementation != 'PyPy'" },
127
127
  ]
128
128
  sdist = { url = "https://files.pythonhosted.org/packages/de/41/6cbdcf9142d00fe82836fbb51e503e58088575cf7a0fe1dbff6695bf0840/cryptography-50.0.0.tar.gz", hash = "sha256:eeac2acb5a20ed25e0ad6d1df9891a520b78b404266b6d11778f25d5d691a6c9", size = 880201, upload-time = "2026-07-31T14:25:10.11Z" }
129
129
  wheels = [
@@ -164,7 +164,7 @@ wheels = [
164
164
 
165
165
  [[package]]
166
166
  name = "gravity-cli"
167
- version = "0.11.0"
167
+ version = "0.12.0"
168
168
  source = { editable = "." }
169
169
  dependencies = [
170
170
  { name = "gravity-schema" },
@@ -201,7 +201,7 @@ dev = [
201
201
 
202
202
  [[package]]
203
203
  name = "gravity-schema"
204
- version = "0.11.0"
204
+ version = "0.12.0"
205
205
  source = { editable = "packages/gravity-schema" }
206
206
  dependencies = [
207
207
  { name = "pydantic" },
@@ -619,8 +619,8 @@ name = "secretstorage"
619
619
  version = "3.5.0"
620
620
  source = { registry = "https://pypi.org/simple" }
621
621
  dependencies = [
622
- { name = "cryptography", marker = "sys_platform != 'win32'" },
623
- { name = "jeepney", marker = "sys_platform != 'win32'" },
622
+ { name = "cryptography" },
623
+ { name = "jeepney" },
624
624
  ]
625
625
  sdist = { url = "https://files.pythonhosted.org/packages/1c/03/e834bcd866f2f8a49a85eaff47340affa3bfa391ee9912a952a1faa68c7b/secretstorage-3.5.0.tar.gz", hash = "sha256:f04b8e4689cbce351744d5537bf6b1329c6fc68f91fa666f60a380edddcd11be", size = 19884, upload-time = "2025-11-23T19:02:53.191Z" }
626
626
  wheels = [
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes