rockycode 0.1.1__tar.gz → 0.1.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 (218) hide show
  1. rockycode-0.1.2/.github/workflows/release.yml +27 -0
  2. {rockycode-0.1.1 → rockycode-0.1.2}/CHANGELOG.md +19 -0
  3. {rockycode-0.1.1 → rockycode-0.1.2}/PKG-INFO +29 -19
  4. {rockycode-0.1.1 → rockycode-0.1.2}/README.md +27 -17
  5. {rockycode-0.1.1 → rockycode-0.1.2}/README.zh-CN.md +15 -10
  6. {rockycode-0.1.1 → rockycode-0.1.2}/pyproject.toml +1 -1
  7. rockycode-0.1.2/rockycode/__init__.py +11 -0
  8. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/cli.py +13 -2
  9. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/server.py +2 -1
  10. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/pricing.py +16 -14
  11. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/package.json +1 -1
  12. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_pricing.py +9 -9
  13. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_serve.py +16 -2
  14. {rockycode-0.1.1 → rockycode-0.1.2}/uv.lock +1 -1
  15. rockycode-0.1.1/.github/workflows/release.yml +0 -73
  16. rockycode-0.1.1/rockycode/__init__.py +0 -1
  17. {rockycode-0.1.1 → rockycode-0.1.2}/.dockerignore +0 -0
  18. {rockycode-0.1.1 → rockycode-0.1.2}/.github/workflows/ci.yml +0 -0
  19. {rockycode-0.1.1 → rockycode-0.1.2}/.gitignore +0 -0
  20. {rockycode-0.1.1 → rockycode-0.1.2}/CONTRIBUTING.md +0 -0
  21. {rockycode-0.1.1 → rockycode-0.1.2}/Dockerfile +0 -0
  22. {rockycode-0.1.1 → rockycode-0.1.2}/Dockerfile.sandbox +0 -0
  23. {rockycode-0.1.1 → rockycode-0.1.2}/LICENSE +0 -0
  24. {rockycode-0.1.1 → rockycode-0.1.2}/SECURITY.md +0 -0
  25. {rockycode-0.1.1 → rockycode-0.1.2}/bench/tasks/dev10.json +0 -0
  26. {rockycode-0.1.1 → rockycode-0.1.2}/bench/tasks/test20.json +0 -0
  27. {rockycode-0.1.1 → rockycode-0.1.2}/brand/rockycode-note.svg +0 -0
  28. {rockycode-0.1.1 → rockycode-0.1.2}/brand/rockycode-wordmark.svg +0 -0
  29. {rockycode-0.1.1 → rockycode-0.1.2}/docker-compose.yml +0 -0
  30. {rockycode-0.1.1 → rockycode-0.1.2}/prompts/README.md +0 -0
  31. {rockycode-0.1.1 → rockycode-0.1.2}/prompts/rocky-v1.txt +0 -0
  32. {rockycode-0.1.1 → rockycode-0.1.2}/prompts/rocky-v2-search-first.txt +0 -0
  33. {rockycode-0.1.1 → rockycode-0.1.2}/prompts/rocky-v3-decisive.txt +0 -0
  34. {rockycode-0.1.1 → rockycode-0.1.2}/prompts/rocky-zh-closer.txt +0 -0
  35. {rockycode-0.1.1 → rockycode-0.1.2}/prompts/rocky-zh-full-closer.txt +0 -0
  36. {rockycode-0.1.1 → rockycode-0.1.2}/prompts/rocky-zh-full.txt +0 -0
  37. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/banner.py +0 -0
  38. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/config.py +0 -0
  39. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/dream/__init__.py +0 -0
  40. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/dream/core.py +0 -0
  41. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/dream/judge.py +0 -0
  42. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/dream/mining.py +0 -0
  43. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/dream/proposals.py +0 -0
  44. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/__init__.py +0 -0
  45. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/artifact.py +0 -0
  46. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/budget.py +0 -0
  47. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/checks.py +0 -0
  48. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/compaction.py +0 -0
  49. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/container.py +0 -0
  50. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/effort.py +0 -0
  51. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/events.py +0 -0
  52. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/explore.py +0 -0
  53. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/goal.py +0 -0
  54. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/goal_review.py +0 -0
  55. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/goal_session.py +0 -0
  56. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/headless.py +0 -0
  57. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/images.py +0 -0
  58. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/loop.py +0 -0
  59. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/lsp.py +0 -0
  60. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/mcp.py +0 -0
  61. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/modes.py +0 -0
  62. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/outcome.py +0 -0
  63. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/permission.py +0 -0
  64. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/planmode.py +0 -0
  65. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/providers.py +0 -0
  66. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/redact.py +0 -0
  67. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/safety.py +0 -0
  68. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/sandbox.py +0 -0
  69. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/skills.py +0 -0
  70. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/titler.py +0 -0
  71. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/tools.py +0 -0
  72. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/trajectory.py +0 -0
  73. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/vision.py +0 -0
  74. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/web.py +0 -0
  75. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/engine/worktree.py +0 -0
  76. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/memory/__init__.py +0 -0
  77. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/memory/index.py +0 -0
  78. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/memory/store.py +0 -0
  79. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/modes/learn/learn.md +0 -0
  80. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/modes/research/deep-research.md +0 -0
  81. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/modes/research/paper-reading.md +0 -0
  82. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/modes/research/prove.md +0 -0
  83. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/modes/research/whiteboard.md +0 -0
  84. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/onboarding.py +0 -0
  85. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/palette.py +0 -0
  86. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/prompts/__init__.py +0 -0
  87. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/prompts/rocky.py +0 -0
  88. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/routines.py +0 -0
  89. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/runners/__init__.py +0 -0
  90. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/runners/agent.py +0 -0
  91. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/runners/data.py +0 -0
  92. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/runners/raw.py +0 -0
  93. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/score.py +0 -0
  94. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/session.py +0 -0
  95. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/skills/architecture-viz/SKILL.md +0 -0
  96. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/skills/architecture-viz/template.html +0 -0
  97. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/skills/lean-prover/SKILL.md +0 -0
  98. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/skills/lean-prover/torchlean-api.md +0 -0
  99. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/__init__.py +0 -0
  100. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/app.py +0 -0
  101. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/clipboard.py +0 -0
  102. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/exitsheet.py +0 -0
  103. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/goal_screen.py +0 -0
  104. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/mdterm.py +0 -0
  105. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/mdview.py +0 -0
  106. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/modelpicker.py +0 -0
  107. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/modepicker.py +0 -0
  108. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/permission.py +0 -0
  109. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/plangate.py +0 -0
  110. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/prompt_history.py +0 -0
  111. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/proposalcard.py +0 -0
  112. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/resume.py +0 -0
  113. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/rocky_pet.py +0 -0
  114. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode/tui/routinecard.py +0 -0
  115. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/.gitignore +0 -0
  116. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/.vscode/launch.json +0 -0
  117. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/.vscode/tasks.json +0 -0
  118. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/.vscodeignore +0 -0
  119. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/CHANGELOG.md +0 -0
  120. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/LICENSE +0 -0
  121. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/README.md +0 -0
  122. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/esbuild.config.mjs +0 -0
  123. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/media/chat.html +0 -0
  124. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/media/icon-marketplace.svg +0 -0
  125. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/media/icon.png +0 -0
  126. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/media/marked.js +0 -0
  127. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/media/rocky-icon.svg +0 -0
  128. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/package-lock.json +0 -0
  129. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/artifactTree.ts +0 -0
  130. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/diffManager.ts +0 -0
  131. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/editorContext.ts +0 -0
  132. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/extension.ts +0 -0
  133. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/permissionManager.ts +0 -0
  134. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/protocol.ts +0 -0
  135. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/rockyConnection.ts +0 -0
  136. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/rockyProvider.ts +0 -0
  137. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/statusBar.ts +0 -0
  138. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/src/webview-highlight.ts +0 -0
  139. {rockycode-0.1.1 → rockycode-0.1.2}/rockycode-vscode/tsconfig.json +0 -0
  140. {rockycode-0.1.1 → rockycode-0.1.2}/tests/fake_lsp_server.py +0 -0
  141. {rockycode-0.1.1 → rockycode-0.1.2}/tests/fake_mcp_server.py +0 -0
  142. {rockycode-0.1.1 → rockycode-0.1.2}/tests/invariants.py +0 -0
  143. {rockycode-0.1.1 → rockycode-0.1.2}/tests/real_planmode.py +0 -0
  144. {rockycode-0.1.1 → rockycode-0.1.2}/tests/real_reasoning_roundtrip.py +0 -0
  145. {rockycode-0.1.1 → rockycode-0.1.2}/tests/real_tool_contract.py +0 -0
  146. {rockycode-0.1.1 → rockycode-0.1.2}/tests/run_all.py +0 -0
  147. {rockycode-0.1.1 → rockycode-0.1.2}/tests/run_real.py +0 -0
  148. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_approver.py +0 -0
  149. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_artifact.py +0 -0
  150. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_bash.py +0 -0
  151. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_bash_grant.py +0 -0
  152. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_bilang_prompt.py +0 -0
  153. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_budget.py +0 -0
  154. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_checks.py +0 -0
  155. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_compaction.py +0 -0
  156. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_container.py +0 -0
  157. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_credentials.py +0 -0
  158. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_docker_sandbox_cancel.py +0 -0
  159. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_dream.py +0 -0
  160. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_dream_trigger.py +0 -0
  161. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_effort.py +0 -0
  162. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_engine.py +0 -0
  163. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_exec.py +0 -0
  164. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_explore.py +0 -0
  165. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_goal.py +0 -0
  166. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_goal_driver.py +0 -0
  167. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_goal_review.py +0 -0
  168. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_goal_runner.py +0 -0
  169. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_hardkill_resume.py +0 -0
  170. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_images.py +0 -0
  171. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_interrupt.py +0 -0
  172. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_judge.py +0 -0
  173. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_lsp.py +0 -0
  174. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_mcp.py +0 -0
  175. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_mdterm.py +0 -0
  176. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_mdview.py +0 -0
  177. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_memory.py +0 -0
  178. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_memory_index.py +0 -0
  179. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_mining.py +0 -0
  180. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_modes.py +0 -0
  181. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_onboarding.py +0 -0
  182. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_outcome.py +0 -0
  183. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_parallel.py +0 -0
  184. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_permission.py +0 -0
  185. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_planmode.py +0 -0
  186. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_prompt_history.py +0 -0
  187. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_proposals.py +0 -0
  188. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_providers.py +0 -0
  189. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_redact.py +0 -0
  190. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_resume_handoff.py +0 -0
  191. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_routine_run.py +0 -0
  192. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_routines.py +0 -0
  193. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_safety.py +0 -0
  194. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_score.py +0 -0
  195. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_session.py +0 -0
  196. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_skills.py +0 -0
  197. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_submit_race.py +0 -0
  198. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_today.py +0 -0
  199. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tools.py +0 -0
  200. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tools_jail.py +0 -0
  201. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_trajectory.py +0 -0
  202. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_artifact_modal.py +0 -0
  203. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_bash_gate.py +0 -0
  204. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_copy.py +0 -0
  205. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_envwarn.py +0 -0
  206. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_exitsheet.py +0 -0
  207. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_goal_screen.py +0 -0
  208. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_input_nav.py +0 -0
  209. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_model.py +0 -0
  210. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_permission.py +0 -0
  211. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_plan.py +0 -0
  212. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_proposals.py +0 -0
  213. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_read_grant.py +0 -0
  214. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_routines.py +0 -0
  215. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_scroll.py +0 -0
  216. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_shell.py +0 -0
  217. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_tui_toggle.py +0 -0
  218. {rockycode-0.1.1 → rockycode-0.1.2}/tests/smoke_web.py +0 -0
@@ -0,0 +1,27 @@
1
+ name: Release
2
+
3
+ # One job: build sdist+wheel on ubuntu, publish to PyPI via Trusted Publishing.
4
+ # The old macos-13 matrix (built a cbor2 x86_64-mac wheel for the release page)
5
+ # is gone: the runner label was retired, so it never actually ran — 0.1.0 and
6
+ # 0.1.1 both sat in its queue until cancelled and shipped fine without it — and
7
+ # cbor2 still publishes no x86_64-mac wheel to attach anyway (arm64 only; an
8
+ # Intel-Mac install builds it from source via Rust, PyPI-side, as it always
9
+ # has). GitHub releases are created by hand: gh release create --notes-file.
10
+ on:
11
+ push:
12
+ tags: ["v*"]
13
+ workflow_dispatch:
14
+
15
+ jobs:
16
+ pypi:
17
+ runs-on: ubuntu-latest
18
+ permissions:
19
+ id-token: write # OIDC — this is what Trusted Publishing uses
20
+ steps:
21
+ - uses: actions/checkout@v4
22
+ - name: Setup uv
23
+ uses: astral-sh/setup-uv@v5
24
+ - name: Build rockycode (sdist + wheel — only our project lands in dist/)
25
+ run: uv build
26
+ - name: Publish to PyPI (Trusted Publishing, no token)
27
+ uses: pypa/gh-action-pypi-publish@release/v1
@@ -9,6 +9,25 @@ change between minor versions.
9
9
 
10
10
  _Nothing yet._
11
11
 
12
+ ## [0.1.2] — `--version` flag, GA price tables
13
+
14
+ ### Added
15
+ - `rockycode --version` / `-V` prints the installed version. One version
16
+ source: package metadata (pyproject) — the serve handshake reports the same
17
+ value instead of a hardcoded string.
18
+
19
+ ### Changed
20
+ - DeepSeek price tables refreshed to the GA snapshots (V4-Flash-0731 /
21
+ V4-Pro-0813), both USD and CNY, verified 2026-08-20 at the source;
22
+ peak-valley billing confirmed live (2× in the published UTC windows).
23
+ - README results updated: `deepseek-v4-flash` GA carries three clean full-500
24
+ SWE-bench Verified rounds (88.8% average, 95.4% pass@3); the
25
+ `deepseek-v4-pro` column is explicitly marked preview (pre-0813).
26
+
27
+ ### CI
28
+ - Release workflow reduced to the single ubuntu PyPI Trusted-Publishing job;
29
+ the dead macos-13 matrix (retired runner, never ran) is gone.
30
+
12
31
  ## [0.1.1] — session artifacts, images in chat, real sandbox cancel
13
32
 
14
33
  ### Added
@@ -1,6 +1,6 @@
1
- Metadata-Version: 2.4
1
+ Metadata-Version: 2.5
2
2
  Name: rockycode
3
- Version: 0.1.1
3
+ Version: 0.1.2
4
4
  Summary: A coding agent harness, benchmarked on SWE-bench Verified. amaze!
5
5
  Author: rockycode contributors
6
6
  License: MIT
@@ -42,8 +42,8 @@ Built for the DeepSeek V4 series, with a unique research mode, bench-tested, and
42
42
 
43
43
  [English](README.md) · [简体中文](README.zh-CN.md)
44
44
 
45
- ![SWE-bench Verified](https://img.shields.io/badge/SWE--bench_Verified-79.8%25_V4--flash-7d5cc6)
46
- ![V4-pro preview](https://img.shields.io/badge/V4--pro_preview-81.8%25_pass@3-8d6cd0)
45
+ ![SWE-bench Verified](https://img.shields.io/badge/SWE--bench_Verified-88.8%25_V4--flash_GA-7d5cc6)
46
+ ![V4-pro preview](https://img.shields.io/badge/V4--pro_preview-74.9%25-8d6cd0)
47
47
  ![Python](https://img.shields.io/badge/Python-3.11%2B-9d7cd8)
48
48
  ![License](https://img.shields.io/badge/License-MIT-a9b1d6)
49
49
 
@@ -77,31 +77,37 @@ against it.
77
77
 
78
78
  ## Results — SWE-bench Verified
79
79
 
80
- Full-set numbers: **independent full-500 runs** (three each for
81
- `deepseek-v4-pro` and `minimax-m3`, one so far for `deepseek-v4-flash`), same
80
+ Full-set numbers: **independent full-500 runs**, three rounds per model, same
82
81
  harness and config for all (100-step cap, 32,768 max output tokens, reasoning
83
82
  effort `max`, thinking on), scored with the official SWE-bench harness. No
84
- tuning against the tasks.
83
+ tuning against the tasks. Mind the versions: the `deepseek-v4-flash` column is
84
+ the **GA release** (V4-Flash-0731), while the `deepseek-v4-pro` rounds ran
85
+ before the GA V4-Pro-0813 shipped — that column is the **preview** pro, so the
86
+ flash/pro gap reflects a version difference, not a same-vintage comparison.
85
87
 
86
- | run | `deepseek-v4-pro` | `deepseek-v4-flash` | `minimax-m3` |
88
+ | run | `deepseek-v4-flash` (GA) | `deepseek-v4-pro` (preview) | `minimax-m3` |
87
89
  |---|---|---|---|
88
- | round 1 | 75.6% (378/500) | 79.8% (399/500) | 72.8% (364/500) |
89
- | round 2 | 74.8% (374/500) | — | 71.2% (356/500) |
90
- | round 3 | 74.4% (372/500) | — | 70.0% (350/500) |
91
- | **average** | **74.9%** | **79.8%** *(1 run)* | **71.3%** |
92
- | union of runs (pass@3) | 81.8% (409/500) | — | 83.6% (418/500) |
90
+ | round 1 | 90.0% (450/500) | 75.6% (378/500) | 72.8% (364/500) |
91
+ | round 2 | 88.6% (443/500) | 74.8% (374/500) | 71.2% (356/500) |
92
+ | round 3 | 87.8% (439/500) | 74.4% (372/500) | 70.0% (350/500) |
93
+ | **average** | **88.8%** | **74.9%** | **71.3%** |
94
+ | union of runs (pass@3) | 95.4% (477/500) | 81.8% (409/500) | 83.6% (418/500) |
93
95
 
94
96
  Read the two summary rows differently. The **average** is the
95
97
  leaderboard-comparable number — each round is an independent single-pass run
96
98
  over the full 500. The **union** is pass@3: tasks solved by at least one
97
- round. The gap between them (~7 points for DeepSeek, ~12 for MiniMax) is
98
- run-to-run variance, not capability — the models already reach these tasks
99
- under this harness, they just don't hold them every run. Closing that gap
100
- (verify-before-finish gating and run selection, not more prompting) is the
101
- current line of work. For reference, DeepSeek reports 80.6% with its own
102
- scaffold; the three-run union crosses that mark. Per-round breakdowns:
99
+ round. The gap between them (~7 points for both DeepSeek models, ~12 for
100
+ MiniMax) is run-to-run variance, not capability — the models already reach
101
+ these tasks under this harness, they just don't hold them every run. Closing
102
+ that gap (verify-before-finish gating and run selection, not more prompting)
103
+ is the current line of work. For reference, DeepSeek reported 80.6% for V4
104
+ Pro (Preview) with its own scaffold. Per-round breakdowns:
103
105
  [@rockycode_ai](https://x.com/rockycode_ai).
104
106
 
107
+ Two earlier flash rounds (79.8% — previously listed here — and 81.2%) hit
108
+ local network outages mid-run, visible as contiguous blocks of empty-patch
109
+ tasks; they were replaced by clean re-runs rather than averaged in.
110
+
105
111
  We plan to add **DeepSWE-bench** support as well — currently in progress.
106
112
 
107
113
  ## Getting started
@@ -121,6 +127,10 @@ uv tool install rockycode # recommended — puts the `rockycode` command on
121
127
  rockycode # the first run walks you through API-key setup
122
128
  ```
123
129
 
130
+ Already installed and a new release is out? **`uv tool upgrade rockycode`** —
131
+ note that re-running `uv tool install` does NOT upgrade: it sees the existing
132
+ install and quietly keeps the old version.
133
+
124
134
  Don't have uv yet? One command installs it:
125
135
  `curl -LsSf https://astral.sh/uv/install.sh | sh` — Windows and other options
126
136
  in the [uv install docs](https://docs.astral.sh/uv/getting-started/installation/).
@@ -9,8 +9,8 @@ Built for the DeepSeek V4 series, with a unique research mode, bench-tested, and
9
9
 
10
10
  [English](README.md) · [简体中文](README.zh-CN.md)
11
11
 
12
- ![SWE-bench Verified](https://img.shields.io/badge/SWE--bench_Verified-79.8%25_V4--flash-7d5cc6)
13
- ![V4-pro preview](https://img.shields.io/badge/V4--pro_preview-81.8%25_pass@3-8d6cd0)
12
+ ![SWE-bench Verified](https://img.shields.io/badge/SWE--bench_Verified-88.8%25_V4--flash_GA-7d5cc6)
13
+ ![V4-pro preview](https://img.shields.io/badge/V4--pro_preview-74.9%25-8d6cd0)
14
14
  ![Python](https://img.shields.io/badge/Python-3.11%2B-9d7cd8)
15
15
  ![License](https://img.shields.io/badge/License-MIT-a9b1d6)
16
16
 
@@ -44,31 +44,37 @@ against it.
44
44
 
45
45
  ## Results — SWE-bench Verified
46
46
 
47
- Full-set numbers: **independent full-500 runs** (three each for
48
- `deepseek-v4-pro` and `minimax-m3`, one so far for `deepseek-v4-flash`), same
47
+ Full-set numbers: **independent full-500 runs**, three rounds per model, same
49
48
  harness and config for all (100-step cap, 32,768 max output tokens, reasoning
50
49
  effort `max`, thinking on), scored with the official SWE-bench harness. No
51
- tuning against the tasks.
50
+ tuning against the tasks. Mind the versions: the `deepseek-v4-flash` column is
51
+ the **GA release** (V4-Flash-0731), while the `deepseek-v4-pro` rounds ran
52
+ before the GA V4-Pro-0813 shipped — that column is the **preview** pro, so the
53
+ flash/pro gap reflects a version difference, not a same-vintage comparison.
52
54
 
53
- | run | `deepseek-v4-pro` | `deepseek-v4-flash` | `minimax-m3` |
55
+ | run | `deepseek-v4-flash` (GA) | `deepseek-v4-pro` (preview) | `minimax-m3` |
54
56
  |---|---|---|---|
55
- | round 1 | 75.6% (378/500) | 79.8% (399/500) | 72.8% (364/500) |
56
- | round 2 | 74.8% (374/500) | — | 71.2% (356/500) |
57
- | round 3 | 74.4% (372/500) | — | 70.0% (350/500) |
58
- | **average** | **74.9%** | **79.8%** *(1 run)* | **71.3%** |
59
- | union of runs (pass@3) | 81.8% (409/500) | — | 83.6% (418/500) |
57
+ | round 1 | 90.0% (450/500) | 75.6% (378/500) | 72.8% (364/500) |
58
+ | round 2 | 88.6% (443/500) | 74.8% (374/500) | 71.2% (356/500) |
59
+ | round 3 | 87.8% (439/500) | 74.4% (372/500) | 70.0% (350/500) |
60
+ | **average** | **88.8%** | **74.9%** | **71.3%** |
61
+ | union of runs (pass@3) | 95.4% (477/500) | 81.8% (409/500) | 83.6% (418/500) |
60
62
 
61
63
  Read the two summary rows differently. The **average** is the
62
64
  leaderboard-comparable number — each round is an independent single-pass run
63
65
  over the full 500. The **union** is pass@3: tasks solved by at least one
64
- round. The gap between them (~7 points for DeepSeek, ~12 for MiniMax) is
65
- run-to-run variance, not capability — the models already reach these tasks
66
- under this harness, they just don't hold them every run. Closing that gap
67
- (verify-before-finish gating and run selection, not more prompting) is the
68
- current line of work. For reference, DeepSeek reports 80.6% with its own
69
- scaffold; the three-run union crosses that mark. Per-round breakdowns:
66
+ round. The gap between them (~7 points for both DeepSeek models, ~12 for
67
+ MiniMax) is run-to-run variance, not capability — the models already reach
68
+ these tasks under this harness, they just don't hold them every run. Closing
69
+ that gap (verify-before-finish gating and run selection, not more prompting)
70
+ is the current line of work. For reference, DeepSeek reported 80.6% for V4
71
+ Pro (Preview) with its own scaffold. Per-round breakdowns:
70
72
  [@rockycode_ai](https://x.com/rockycode_ai).
71
73
 
74
+ Two earlier flash rounds (79.8% — previously listed here — and 81.2%) hit
75
+ local network outages mid-run, visible as contiguous blocks of empty-patch
76
+ tasks; they were replaced by clean re-runs rather than averaged in.
77
+
72
78
  We plan to add **DeepSWE-bench** support as well — currently in progress.
73
79
 
74
80
  ## Getting started
@@ -88,6 +94,10 @@ uv tool install rockycode # recommended — puts the `rockycode` command on
88
94
  rockycode # the first run walks you through API-key setup
89
95
  ```
90
96
 
97
+ Already installed and a new release is out? **`uv tool upgrade rockycode`** —
98
+ note that re-running `uv tool install` does NOT upgrade: it sees the existing
99
+ install and quietly keeps the old version.
100
+
91
101
  Don't have uv yet? One command installs it:
92
102
  `curl -LsSf https://astral.sh/uv/install.sh | sh` — Windows and other options
93
103
  in the [uv install docs](https://docs.astral.sh/uv/getting-started/installation/).
@@ -9,8 +9,8 @@
9
9
 
10
10
  [English](README.md) · [简体中文](README.zh-CN.md)
11
11
 
12
- ![SWE-bench Verified](https://img.shields.io/badge/SWE--bench_Verified-79.8%25_V4--flash-7d5cc6)
13
- ![V4-pro preview](https://img.shields.io/badge/V4--pro_preview-81.8%25_pass@3-8d6cd0)
12
+ ![SWE-bench Verified](https://img.shields.io/badge/SWE--bench_Verified-88.8%25_V4--flash_GA-7d5cc6)
13
+ ![V4-pro preview](https://img.shields.io/badge/V4--pro_preview-74.9%25-8d6cd0)
14
14
  ![Python](https://img.shields.io/badge/Python-3.11%2B-9d7cd8)
15
15
  ![License](https://img.shields.io/badge/License-MIT-a9b1d6)
16
16
 
@@ -37,17 +37,19 @@ rockycode 是一个编程智能体 harness,为 DeepSeek V4 系列适配,也
37
37
 
38
38
  ## 能力量化:SWE bench
39
39
 
40
- 完整 500 题的成绩:**独立的完整 500 题运行**(`deepseek-v4-pro` 与 `minimax-m3` 各 3 轮,`deepseek-v4-flash` 目前 1 轮),所有模型使用完全相同的 harness 与配置(步数上限 100、单次最大输出 32,768 token、推理力度 `max`、thinking 开启),由官方 SWE-bench harness 打分,未针对任务做任何调优。
40
+ 完整 500 题的成绩:**独立的完整 500 题运行**,每个模型各 3 轮,所有模型使用完全相同的 harness 与配置(步数上限 100、单次最大输出 32,768 token、推理力度 `max`、thinking 开启),由官方 SWE-bench harness 打分,未针对任务做任何调优。注意版本差异:`deepseek-v4-flash` 一列是**正式版(GA,V4-Flash-0731)**;而 `deepseek-v4-pro` 的三轮在 GA 版 V4-Pro-0813 发布之前运行,该列是 **preview 版**成绩 —— flash 与 pro 的差距里含有版本差,不是同代对比。
41
41
 
42
- | 轮次 | `deepseek-v4-pro` | `deepseek-v4-flash` | `minimax-m3` |
42
+ | 轮次 | `deepseek-v4-flash`(GA) | `deepseek-v4-pro`(preview) | `minimax-m3` |
43
43
  |---|---|---|---|
44
- | 第 1 轮 | 75.6%(378/500) | 79.8%(399/500) | 72.8%(364/500) |
45
- | 第 2 轮 | 74.8%(374/500) | — | 71.2%(356/500) |
46
- | 第 3 轮 | 74.4%(372/500) | — | 70.0%(350/500) |
47
- | **平均** | **74.9%** | **79.8%**(1 轮) | **71.3%** |
48
- | 多轮并集(pass@3) | 81.8%(409/500) | — | 83.6%(418/500) |
44
+ | 第 1 轮 | 90.0%(450/500) | 75.6%(378/500) | 72.8%(364/500) |
45
+ | 第 2 轮 | 88.6%(443/500) | 74.8%(374/500) | 71.2%(356/500) |
46
+ | 第 3 轮 | 87.8%(439/500) | 74.4%(372/500) | 70.0%(350/500) |
47
+ | **平均** | **88.8%** | **74.9%** | **71.3%** |
48
+ | 多轮并集(pass@3) | 95.4%(477/500) | 81.8%(409/500) | 83.6%(418/500) |
49
49
 
50
- 两行汇总要分开读。**平均值**是可以与排行榜对比的数字 —— 每一轮都是独立的单次完整 500 题。**并集**是 pass@3:至少被某一轮解出的任务。两者之间的差距(DeepSeek 约 7 个点、MiniMax 约 12 个点)是轮次间方差,不是能力上限 —— 模型在这套 harness 下已经"够得着"这些任务,只是无法每一轮都稳住。当前的工作重心就是收掉这个差距:finish 前的验证门控与多轮选择,而不是继续改提示词。作为参照:DeepSeek 用自家 scaffold 报告 80.6%,三轮并集已越过这个数字。逐轮拆解请关注我们的X账号(@rockycode_ai)。
50
+ 两行汇总要分开读。**平均值**是可以与排行榜对比的数字 —— 每一轮都是独立的单次完整 500 题。**并集**是 pass@3:至少被某一轮解出的任务。两者之间的差距(DeepSeek 两个模型各约 7 个点、MiniMax 约 12 个点)是轮次间方差,不是能力上限 —— 模型在这套 harness 下已经"够得着"这些任务,只是无法每一轮都稳住。当前的工作重心就是收掉这个差距:finish 前的验证门控与多轮选择,而不是继续改提示词。作为参照:DeepSeek 用自家 scaffold 报告 V4 Pro (Preview) 为 80.6%。逐轮拆解请关注我们的X账号(@rockycode_ai)。
51
+
52
+ 另有两轮较早的 flash-preview 运行(79.8% —— 即此前列在这里的那一轮 —— 与 81.2%)在运行途中遭遇本地网络中断,表现为连续任务块返回空补丁;这两轮已用干净的重跑替换,未计入平均。
51
53
 
52
54
  我们计划支持DeepSWE bench,目前还在调试中。
53
55
 
@@ -62,6 +64,9 @@ uv tool install rockycode # 推荐 —— `rockycode` 命令直接进 PATH
62
64
  rockycode # 首次运行会引导你完成 API key 设置
63
65
  ```
64
66
 
67
+ 已经装过、想升到新版本?用 **`uv tool upgrade rockycode`** ——
68
+ 注意重复执行 `uv tool install` 不会升级:它看到已有安装就静默保留旧版本。
69
+
65
70
  还没有 uv?一条命令安装:
66
71
  `curl -LsSf https://astral.sh/uv/install.sh | sh`(Windows 及其他方式见
67
72
  [uv 安装文档](https://docs.astral.sh/uv/getting-started/installation/))。
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "rockycode"
3
- version = "0.1.1"
3
+ version = "0.1.2"
4
4
  description = "A coding agent harness, benchmarked on SWE-bench Verified. amaze!"
5
5
  requires-python = ">=3.11"
6
6
  readme = "README.md"
@@ -0,0 +1,11 @@
1
+ # Version comes from installed package metadata (single source: pyproject) —
2
+ # a hardcoded string here shipped stale once ("0.1.0" inside the 0.1.1 wheel).
3
+ # Lazy module __getattr__ keeps `import rockycode` free of the metadata scan.
4
+ def __getattr__(name: str):
5
+ if name == "__version__":
6
+ from importlib.metadata import PackageNotFoundError, version
7
+ try:
8
+ return version("rockycode")
9
+ except PackageNotFoundError: # running from a bare checkout, uninstalled
10
+ return "unknown"
11
+ raise AttributeError(name)
@@ -29,7 +29,7 @@ bootstrap_credentials()
29
29
  # `rockycode` without args → `rockycode chat`; a leading flag (`rockycode
30
30
  # --resume …`, `rockycode --yolo`) reaches chat too — nobody should have to
31
31
  # remember to type "chat" first.
32
- _TOP_LEVEL_FLAGS = {"--help", "-h", "--version", "--install-completion", "--show-completion"}
32
+ _TOP_LEVEL_FLAGS = {"--help", "-h", "--version", "-V", "--install-completion", "--show-completion"}
33
33
  if len(sys.argv) == 1:
34
34
  sys.argv.append("chat")
35
35
  elif sys.argv[1].startswith("-") and sys.argv[1] not in _TOP_LEVEL_FLAGS:
@@ -67,8 +67,19 @@ def _env_int(name: str, default: int) -> int:
67
67
  return default
68
68
 
69
69
 
70
+ def _version_flag(value: bool) -> None:
71
+ if value:
72
+ import rockycode
73
+ print(f"rockycode {rockycode.__version__}") # plain print: script-friendly
74
+ raise typer.Exit()
75
+
76
+
70
77
  @app.callback()
71
- def _root() -> None:
78
+ def _root(
79
+ version: bool = typer.Option(
80
+ False, "--version", "-V", callback=_version_flag, is_eager=True,
81
+ help="Print the version and exit."),
82
+ ) -> None:
72
83
  """Force Typer into multi-command mode."""
73
84
 
74
85
 
@@ -413,9 +413,10 @@ async def run_server(
413
413
  # chain: env, .env files serve loaded, keychain) so the client's
414
414
  # "setup required" card reflects reality instead of guessing
415
415
  # from the editor's own environment.
416
+ import rockycode
416
417
  from rockycode.onboarding import is_configured
417
418
  _write_line(_response(msg_id, {
418
- "version": "0.1.1",
419
+ "version": rockycode.__version__,
419
420
  "session_id": sess.session_id,
420
421
  "model": model,
421
422
  "configured": is_configured(),
@@ -9,7 +9,9 @@ DeepSeek changes them:
9
9
  https://api-docs.deepseek.com/quick_start/pricing (USD table)
10
10
  https://api-docs.deepseek.com/zh-cn/quick_start/pricing (CNY table)
11
11
 
12
- Verified: 2026-07-04 (per 1,000,000 tokens).
12
+ Verified: 2026-08-20 (per 1,000,000 tokens). Tables list the GA snapshots
13
+ DeepSeek-V4-Flash-0731 and DeepSeek-V4-Pro-0813; both are billed off-peak base
14
+ with a 2x peak surcharge.
13
15
 
14
16
  To update WITHOUT editing the install (survives upgrades), drop a
15
17
  ~/.rockycode/pricing.toml that overrides any values below. It is a FILE on
@@ -24,18 +26,17 @@ from datetime import datetime, time as dtime, timezone
24
26
  from pathlib import Path
25
27
 
26
28
  PRICING_SOURCE_URL = "https://api-docs.deepseek.com/quick_start/pricing"
27
- PRICING_VERIFIED = "2026-07-04"
29
+ PRICING_VERIFIED = "2026-08-20"
28
30
  OVERRIDE_PATH = Path.home() / ".rockycode" / "pricing.toml"
29
31
 
30
32
  # Official list prices, per 1M tokens, each currency from its OWN table.
31
33
  DEFAULT_PRICING: dict = {
32
34
  "peak": {
33
- # DeepSeek peak-valley pricing (announced): peak-hour rate = 2x regular,
34
- # for ALL billing items, during these UTC windows — 01:00–04:00 and
35
- # 06:00–10:00. It starts MID-JULY 2026, so the logic is wired but gated
36
- # behind effective_date: before that date nothing is surcharged even
37
- # inside a window, and it auto-activates on the date with no code change.
38
- # Confirm the exact start date and adjust here or in the override file.
35
+ # DeepSeek peak-valley pricing, LIVE and confirmed at the source
36
+ # 2026-08-20: peak-hour rate = 2x the off-peak base below, for ALL
37
+ # billing items, during these UTC windows — 01:00–04:00 and 06:00–10:00
38
+ # (Beijing 9:00–12:00 / 14:00–18:00). effective_date stays so usage
39
+ # from before the mid-July start keeps pricing at base.
39
40
  "enabled": True,
40
41
  "effective_date": "2026-07-15", # UTC; peak surcharge does not apply before this
41
42
  "multiplier": 2.0,
@@ -45,13 +46,14 @@ DEFAULT_PRICING: dict = {
45
46
  ],
46
47
  },
47
48
  "models": {
48
- "deepseek-v4-pro": {
49
- "usd": {"in_hit": 0.003625, "in_miss": 0.435, "out": 0.87},
50
- "cny": {"in_hit": 0.025, "in_miss": 3.0, "out": 6.0},
49
+ # Off-peak base rates; peak windows above bill at multiplier x base.
50
+ "deepseek-v4-pro": { # GA snapshot V4-Pro-0813
51
+ "usd": {"in_hit": 0.022, "in_miss": 0.66, "out": 1.98},
52
+ "cny": {"in_hit": 0.15, "in_miss": 4.5, "out": 13.5},
51
53
  },
52
- "deepseek-v4-flash": {
53
- "usd": {"in_hit": 0.0028, "in_miss": 0.14, "out": 0.28},
54
- "cny": {"in_hit": 0.02, "in_miss": 1.0, "out": 2.0},
54
+ "deepseek-v4-flash": { # GA snapshot V4-Flash-0731
55
+ "usd": {"in_hit": 0.007, "in_miss": 0.22, "out": 0.66},
56
+ "cny": {"in_hit": 0.05, "in_miss": 1.5, "out": 4.5},
55
57
  },
56
58
  },
57
59
  "fallback_model": "deepseek-v4-pro", # unknown model → price as pro (conservative)
@@ -2,7 +2,7 @@
2
2
  "name": "rockycode",
3
3
  "displayName": "rockycode",
4
4
  "description": "AI coding agent — chat, inline tools, diff previews, and in-panel Enter/arrow tool approvals. Powered by the rockycode CLI (DeepSeek).",
5
- "version": "0.1.1",
5
+ "version": "0.1.2",
6
6
  "publisher": "rockycode",
7
7
  "license": "MIT",
8
8
  "icon": "media/icon.png",
@@ -18,10 +18,10 @@ def test_dual_currency():
18
18
  led = UsageLedger() # peak disabled by default
19
19
  led.add("deepseek-v4-pro", _1M, at=OFFPEAK)
20
20
  led.add("deepseek-v4-flash", _1M, at=OFFPEAK)
21
- # USD from the USD table: pro 0.435+0.87, flash 0.14+0.28
22
- assert abs(led.cost("usd") - (0.435 + 0.87 + 0.14 + 0.28)) < 1e-9, led.cost("usd")
23
- # CNY from the CNY table — independent numbers, NOT usd*ratio: pro 3+6, flash 1+2
24
- assert abs(led.cost("cny") - (3.0 + 6.0 + 1.0 + 2.0)) < 1e-9, led.cost("cny")
21
+ # USD from the USD table: pro 0.66+1.98, flash 0.22+0.66
22
+ assert abs(led.cost("usd") - (0.66 + 1.98 + 0.22 + 0.66)) < 1e-9, led.cost("usd")
23
+ # CNY from the CNY table — independent numbers, NOT usd*ratio: pro 4.5+13.5, flash 1.5+4.5
24
+ assert abs(led.cost("cny") - (4.5 + 13.5 + 1.5 + 4.5)) < 1e-9, led.cost("cny")
25
25
  assert led.configured("usd") and led.configured("cny")
26
26
  print(f"dual-currency: ${led.cost('usd'):.3f} / ¥{led.cost('cny'):.1f} (independent tables) ok")
27
27
 
@@ -29,13 +29,13 @@ def test_dual_currency():
29
29
  def test_peak():
30
30
  led = UsageLedger() # ships peak enabled (2x, windows 01–04 & 06–10 UTC, from mid-July)
31
31
  led.add("deepseek-v4-flash", _1M, at=PEAK)
32
- assert abs(led.cost("usd") - (0.14 + 0.28) * 2) < 1e-9, led.cost("usd") # 2x in-window
32
+ assert abs(led.cost("usd") - (0.22 + 0.66) * 2) < 1e-9, led.cost("usd") # 2x in-window
33
33
  off = UsageLedger()
34
34
  off.add("deepseek-v4-flash", _1M, at=OFFPEAK)
35
- assert abs(off.cost("usd") - (0.14 + 0.28)) < 1e-9, off.cost("usd") # off-peak base
35
+ assert abs(off.cost("usd") - (0.22 + 0.66)) < 1e-9, off.cost("usd") # off-peak base
36
36
  pre = UsageLedger()
37
37
  pre.add("deepseek-v4-flash", _1M, at=PRE_EFFECT)
38
- assert abs(pre.cost("usd") - (0.14 + 0.28)) < 1e-9, pre.cost("usd") # in-window but before mid-July
38
+ assert abs(pre.cost("usd") - (0.22 + 0.66)) < 1e-9, pre.cost("usd") # in-window but before mid-July
39
39
  print("peak-hour: 2x in-window after the mid-July start; base before it and off-peak ok")
40
40
 
41
41
 
@@ -45,7 +45,7 @@ def test_override():
45
45
  p.write_text("[models.deepseek-v4-flash.usd]\nout = 9.99\n")
46
46
  pricing = load_pricing(override_path=p)
47
47
  assert pricing["models"]["deepseek-v4-flash"]["usd"]["out"] == 9.99 # overridden
48
- assert pricing["models"]["deepseek-v4-flash"]["usd"]["in_miss"] == 0.14 # untouched keeps default
48
+ assert pricing["models"]["deepseek-v4-flash"]["usd"]["in_miss"] == 0.22 # untouched keeps default
49
49
  print("override: ~/.rockycode/pricing.toml merges over the built-in table ok")
50
50
 
51
51
 
@@ -54,7 +54,7 @@ def test_cache_cheap():
54
54
  led.add("deepseek-v4-pro",
55
55
  {"prompt_tokens": 1_000_000, "prompt_cache_hit_tokens": 1_000_000, "completion_tokens": 0},
56
56
  at=OFFPEAK)
57
- assert led.cost("usd") < 0.02, led.cost("usd")
57
+ assert led.cost("usd") < 0.03, led.cost("usd") # 1M hit tokens at $0.022 vs $0.66 as misses
58
58
  print("cache hits cost far less than misses ok")
59
59
 
60
60
 
@@ -66,7 +66,7 @@ def test_serve_jsonrpc_handshake():
66
66
  proc.stdin.write(_request("initialize"))
67
67
  proc.stdin.flush()
68
68
  resp = _read_line(proc)
69
- assert resp.get("result", {}).get("version") == "0.1.1", \
69
+ assert resp.get("result", {}).get("version") == "0.1.2", \
70
70
  f"unexpected init response: {resp}"
71
71
  sid = resp.get("result", {}).get("session_id")
72
72
  assert sid
@@ -107,7 +107,7 @@ def test_serve_survives_malformed_messages():
107
107
  proc.stdin.write(_request("initialize"))
108
108
  proc.stdin.flush()
109
109
  resp = _read_line(proc)
110
- assert resp.get("result", {}).get("version") == "0.1.1", \
110
+ assert resp.get("result", {}).get("version") == "0.1.2", \
111
111
  f"server did not survive malformed input: {resp}"
112
112
  proc.stdin.write(_request("shutdown", msg_id=2))
113
113
  proc.stdin.flush()
@@ -175,6 +175,17 @@ def test_event_to_notification():
175
175
  assert n["params"]["session_id"] == sid
176
176
 
177
177
 
178
+ def test_cli_version_flag():
179
+ """`rockycode --version` prints the SAME version the serve handshake
180
+ reports — both derive from package metadata, and this literal is part of
181
+ the release bump ritual (matches the handshake asserts above)."""
182
+ from typer.testing import CliRunner
183
+
184
+ from rockycode.cli import app
185
+ result = CliRunner().invoke(app, ["--version"])
186
+ assert result.exit_code == 0 and "rockycode 0.1.2" in result.output, result.output
187
+
188
+
178
189
  if __name__ == "__main__":
179
190
  test_serve_jsonrpc_handshake()
180
191
  print("PASS test_serve_jsonrpc_handshake")
@@ -188,4 +199,7 @@ if __name__ == "__main__":
188
199
  test_event_to_notification()
189
200
  print("PASS test_event_to_notification")
190
201
 
202
+ test_cli_version_flag()
203
+ print("PASS test_cli_version_flag")
204
+
191
205
  print("\nOK — all serve smoke tests passed")
@@ -2239,7 +2239,7 @@ wheels = [
2239
2239
 
2240
2240
  [[package]]
2241
2241
  name = "rockycode"
2242
- version = "0.1.1"
2242
+ version = "0.1.2"
2243
2243
  source = { editable = "." }
2244
2244
  dependencies = [
2245
2245
  { name = "aiohttp" },
@@ -1,73 +0,0 @@
1
- name: Release
2
-
3
- on:
4
- push:
5
- tags: ["v*"]
6
- workflow_dispatch:
7
-
8
- jobs:
9
- release:
10
- runs-on: macos-13 # x86_64 Mac — the only platform missing cbor2 wheels
11
- strategy:
12
- matrix:
13
- python: ["3.11", "3.12", "3.13"]
14
- steps:
15
- - uses: actions/checkout@v4
16
-
17
- - name: Setup uv
18
- uses: astral-sh/setup-uv@v5
19
- with:
20
- enable-cache: true
21
- python-version: ${{ matrix.python }}
22
-
23
- - name: Install Rust (cbor2 needs it on macOS x86_64)
24
- run: rustup update stable
25
-
26
- - name: Build rockycode wheel (only once)
27
- if: matrix.python == '3.11'
28
- run: uv build
29
-
30
- - name: Build cbor2 wheel
31
- run: uv pip wheel cbor2==6.1.2 --no-deps -w dist/
32
-
33
- - name: Upload wheels
34
- uses: actions/upload-artifact@v4
35
- with:
36
- name: wheels-${{ matrix.python }}
37
- path: dist/
38
-
39
- publish:
40
- needs: release
41
- runs-on: ubuntu-latest
42
- steps:
43
- - name: Download all wheels
44
- uses: actions/download-artifact@v4
45
- with:
46
- path: dist/
47
- pattern: wheels-*
48
- merge-multiple: true
49
-
50
- - name: Show artifacts
51
- run: ls -la dist/
52
-
53
- - name: Release
54
- uses: softprops/action-gh-release@v2
55
- with:
56
- files: dist/*
57
- generate_release_notes: true
58
-
59
- # rockycode is pure-Python, so PyPI publishing builds on Ubuntu and does NOT
60
- # depend on the macOS `release` job (which only exists for the cbor2 wheel on
61
- # the GitHub-Release side). This keeps publishing off the slow macOS queue.
62
- pypi:
63
- runs-on: ubuntu-latest
64
- permissions:
65
- id-token: write # OIDC — this is what Trusted Publishing uses
66
- steps:
67
- - uses: actions/checkout@v4
68
- - name: Setup uv
69
- uses: astral-sh/setup-uv@v5
70
- - name: Build rockycode (sdist + wheel — only our project lands in dist/)
71
- run: uv build
72
- - name: Publish to PyPI (Trusted Publishing, no token)
73
- uses: pypa/gh-action-pypi-publish@release/v1
@@ -1 +0,0 @@
1
- __version__ = "0.1.0"
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes