freesolo-flash-dev 1.2.89__tar.gz → 1.2.95__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 (613) hide show
  1. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/PKG-INFO +1 -1
  2. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/__init__.py +14 -19
  3. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/__init__.py +11 -24
  4. freesolo_flash_dev-1.2.95/flash/cli/commands/worker_output.py +67 -0
  5. freesolo_flash_dev-1.2.95/flash/cli/errors.py +277 -0
  6. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/ui/heartbeat.py +27 -0
  7. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/ui/render.py +1 -0
  8. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/plan/kv_sizing.py +20 -8
  9. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/opd_train.py +1 -1
  10. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/opd_train_runner.py +5 -1
  11. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/verl_config.py +17 -8
  12. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/poll.py +3 -0
  13. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/platform/runtime.py +4 -3
  14. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/pyproject.toml +2 -2
  15. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_commands.py +54 -0
  16. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_render_theme.py +254 -1
  17. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_jobs.py +1 -1
  18. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_opd_train.py +32 -0
  19. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_resume_on_retry.py +4 -0
  20. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_rl_train.py +67 -16
  21. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_api.py +49 -0
  22. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/uv.lock +1 -1
  23. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.dockerignore +0 -0
  24. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.env.example +0 -0
  25. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/CODEOWNERS +0 -0
  26. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/ISSUE_TEMPLATE/bug_report.yml +0 -0
  27. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/ISSUE_TEMPLATE/config.yml +0 -0
  28. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/ISSUE_TEMPLATE/feature_request.yml +0 -0
  29. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/PULL_REQUEST_TEMPLATE.md +0 -0
  30. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/dependabot.yml +0 -0
  31. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/auto-rebake.yml +0 -0
  32. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/bake-kernel-cache.yml +0 -0
  33. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/ci.yml +0 -0
  34. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/dev-kernel-cache.yml +0 -0
  35. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/main-source-guard.yml +0 -0
  36. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/notify-tests-repo.yml +0 -0
  37. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/production-kernel-cache-ready.yml +0 -0
  38. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/publish-dev.yml +0 -0
  39. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/publish-image.yml +0 -0
  40. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/publish.yml +0 -0
  41. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/version-parity.yml +0 -0
  42. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.github/workflows/worker-image.yml +0 -0
  43. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/.gitignore +0 -0
  44. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/CHANGELOG.md +0 -0
  45. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/CODE_OF_CONDUCT.md +0 -0
  46. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/CONTRIBUTING.md +0 -0
  47. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/Dockerfile +0 -0
  48. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/Dockerfile.worker +0 -0
  49. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/LICENSE +0 -0
  50. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/NOTICE +0 -0
  51. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/README.md +0 -0
  52. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/SECURITY.md +0 -0
  53. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/SELF_HOSTING.md +0 -0
  54. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/build/kernel_cache/.gitignore +0 -0
  55. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/build/kernel_cache/.keep +0 -0
  56. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/deploy/infisical/README.md +0 -0
  57. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/deploy/infisical/entrypoint.sh +0 -0
  58. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/docker/Dockerfile.kernelcache +0 -0
  59. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/docker/Dockerfile.kernelcache.relayer +0 -0
  60. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/docker/bake_kernel_cache.py +0 -0
  61. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/docker/bake_pod_entry.py +0 -0
  62. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/docker/extract_cudart_fix.py +0 -0
  63. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/docker/kernel_fingerprint.py +0 -0
  64. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/docker/make_rp_handler.py +0 -0
  65. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/__init__.py +0 -0
  66. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/_internal/__init__.py +0 -0
  67. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/_internal/channel.py +0 -0
  68. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/_internal/diagnostics.py +0 -0
  69. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/_internal/fileio.py +0 -0
  70. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/_internal/logging.py +0 -0
  71. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/_internal/paths.py +0 -0
  72. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/adapters/__init__.py +0 -0
  73. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/adapters/artifacts.py +0 -0
  74. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/adapters/fused_experts.py +0 -0
  75. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/adapters/lora_rank.py +0 -0
  76. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/adapters/targets.py +0 -0
  77. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/__main__.py +0 -0
  78. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/deploy.py +0 -0
  79. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/__init__.py +0 -0
  80. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/episode.py +0 -0
  81. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/eval.py +0 -0
  82. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/eval_args.py +0 -0
  83. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/imports.py +0 -0
  84. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/list.py +0 -0
  85. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/push.py +0 -0
  86. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/retained.py +0 -0
  87. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/setup.py +0 -0
  88. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/setup_wandb.py +0 -0
  89. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/test.py +0 -0
  90. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/test_evaluations.py +0 -0
  91. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/test_params.py +0 -0
  92. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/env/test_warnings.py +0 -0
  93. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/prompt_budget.py +0 -0
  94. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/traces.py +0 -0
  95. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/commands/train_cost.py +0 -0
  96. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/scaffold/TRAINING.md +0 -0
  97. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/scaffold/__init__.py +0 -0
  98. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/ui/__init__.py +0 -0
  99. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/ui/cost.py +0 -0
  100. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/ui/env_panels.py +0 -0
  101. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/ui/tables.py +0 -0
  102. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cli/ui/tty.py +0 -0
  103. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/__init__.py +0 -0
  104. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/config.py +0 -0
  105. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/freesolo_api.py +0 -0
  106. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/http.py +0 -0
  107. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/runtime_secrets.py +0 -0
  108. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/shapes.py +0 -0
  109. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/specs.py +0 -0
  110. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/client/streaming.py +0 -0
  111. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/content/__init__.py +0 -0
  112. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/content/image_descriptors.py +0 -0
  113. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/content/multimodal.py +0 -0
  114. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/content/structured_outputs.py +0 -0
  115. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/content/thinking.py +0 -0
  116. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/core/__init__.py +0 -0
  117. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/core/catalog.py +0 -0
  118. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/core/grpo.py +0 -0
  119. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/core/spec.py +0 -0
  120. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/core/spec_persistence.py +0 -0
  121. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cost/__init__.py +0 -0
  122. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cost/analytical.py +0 -0
  123. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cost/facts.py +0 -0
  124. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cost/spec.py +0 -0
  125. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/cost/types.py +0 -0
  126. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/__init__.py +0 -0
  127. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/huggingface.py +0 -0
  128. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/plan/__init__.py +0 -0
  129. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/plan/model_config_probe.py +0 -0
  130. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/plan/prompt_budget.py +0 -0
  131. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/plan/recipe.py +0 -0
  132. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/plan/steps.py +0 -0
  133. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/plan/vram.py +0 -0
  134. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/__init__.py +0 -0
  135. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/dataset_profile.py +0 -0
  136. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/image_tokens.py +0 -0
  137. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/reasoning_render.py +0 -0
  138. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/sft_image_rows.py +0 -0
  139. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/sft_workload.py +0 -0
  140. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/tokenizer.py +0 -0
  141. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/profiling/workload_profile.py +0 -0
  142. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/result/__init__.py +0 -0
  143. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/result/accounting.py +0 -0
  144. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/result/rollout_samples.py +0 -0
  145. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/__init__.py +0 -0
  146. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/__main__.py +0 -0
  147. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/backend_common.py +0 -0
  148. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/entry/__init__.py +0 -0
  149. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/entry/opd.py +0 -0
  150. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/entry/rl.py +0 -0
  151. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/entry/sft.py +0 -0
  152. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/io/__init__.py +0 -0
  153. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/io/heartbeat.py +0 -0
  154. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/io/hf.py +0 -0
  155. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/io/prefetch.py +0 -0
  156. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/io/wandb_log.py +0 -0
  157. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/model/__init__.py +0 -0
  158. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/model/adapter.py +0 -0
  159. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/model/chatml_mask.py +0 -0
  160. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/model/decoding.py +0 -0
  161. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/model/lora.py +0 -0
  162. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/model/packing.py +0 -0
  163. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/perf/__init__.py +0 -0
  164. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/perf/diagnostics.py +0 -0
  165. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/perf/lifecycle.py +0 -0
  166. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/perf/liger.py +0 -0
  167. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/perf/memory.py +0 -0
  168. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/rl_train.py +0 -0
  169. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/rl_train_runner.py +0 -0
  170. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/runtime/__init__.py +0 -0
  171. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/runtime/kernel_warmup.py +0 -0
  172. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/runtime/pkg_proxy.py +0 -0
  173. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/runtime/rng.py +0 -0
  174. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/score_batcher.py +0 -0
  175. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/sft_train.py +0 -0
  176. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/sft_train_runner.py +0 -0
  177. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/teacher/__init__.py +0 -0
  178. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/teacher/client.py +0 -0
  179. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/teacher/encoding.py +0 -0
  180. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/teacher/tokenizer_align.py +0 -0
  181. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/__init__.py +0 -0
  182. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/core/__init__.py +0 -0
  183. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/core/checkpoint_lifecycle.py +0 -0
  184. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/core/child/__init__.py +0 -0
  185. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/core/child/glue.py +0 -0
  186. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/core/child/runtime.py +0 -0
  187. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/core/step_timing.py +0 -0
  188. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/finalize.py +0 -0
  189. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/__init__.py +0 -0
  190. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/batching.py +0 -0
  191. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/bridge.py +0 -0
  192. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/bridge_failures.py +0 -0
  193. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/__init__.py +0 -0
  194. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/bridge.py +0 -0
  195. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/entry.py +0 -0
  196. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/multiturn.py +0 -0
  197. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/plugin.py +0 -0
  198. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/replay_guard.py +0 -0
  199. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/runtime.py +0 -0
  200. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/child/structured.py +0 -0
  201. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/failures.py +0 -0
  202. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/gkd.py +0 -0
  203. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/multiturn_media.py +0 -0
  204. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/multiturn_validation.py +0 -0
  205. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/overrides.py +0 -0
  206. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/prompts.py +0 -0
  207. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/reporting.py +0 -0
  208. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/scoring.py +0 -0
  209. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/state.py +0 -0
  210. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/opd/validation.py +0 -0
  211. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/__init__.py +0 -0
  212. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/checkpoints.py +0 -0
  213. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/child/__init__.py +0 -0
  214. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/child/entry.py +0 -0
  215. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/child/multiturn.py +0 -0
  216. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/child/patches.py +0 -0
  217. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/child/plugin.py +0 -0
  218. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/config.py +0 -0
  219. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/identity.py +0 -0
  220. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/inputs.py +0 -0
  221. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/multi_turn.py +0 -0
  222. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/reward_module.py +0 -0
  223. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/scoring.py +0 -0
  224. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/rl/single_turn.py +0 -0
  225. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/sft/__init__.py +0 -0
  226. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/sft/checkpoints.py +0 -0
  227. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/sft/child/entry.py +0 -0
  228. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/sft/child/plugin.py +0 -0
  229. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/train/sft/config.py +0 -0
  230. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/__init__.py +0 -0
  231. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/capabilities.py +0 -0
  232. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/checkpoints.py +0 -0
  233. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/child_io.py +0 -0
  234. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/diagnostics.py +0 -0
  235. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/parallelism.py +0 -0
  236. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/parent_work.py +0 -0
  237. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker/verl/process_census.py +0 -0
  238. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/engine/worker_entrypoint.py +0 -0
  239. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/__init__.py +0 -0
  240. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/adapter.py +0 -0
  241. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/base.py +0 -0
  242. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/cache_security.py +0 -0
  243. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/dataset_selection.py +0 -0
  244. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/evaluations.py +0 -0
  245. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/identity.py +0 -0
  246. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/loader.py +0 -0
  247. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/namespace_listing.py +0 -0
  248. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/package/__init__.py +0 -0
  249. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/package/direct_tokens.py +0 -0
  250. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/package/limits.py +0 -0
  251. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/package/unpack.py +0 -0
  252. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/pull.py +0 -0
  253. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/envs/staged.py +0 -0
  254. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/__init__.py +0 -0
  255. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/__init__.py +0 -0
  256. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/auth.py +0 -0
  257. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/bootstrap.py +0 -0
  258. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/bootstrap_console.py +0 -0
  259. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/bootstrap_pip.py +0 -0
  260. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/bootstrap_secrets.py +0 -0
  261. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/deadline.py +0 -0
  262. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/host/__init__.py +0 -0
  263. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/host/deadline_sleep.py +0 -0
  264. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/host/failmark.py +0 -0
  265. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/host/hostlog.py +0 -0
  266. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/http.py +0 -0
  267. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/instance.py +0 -0
  268. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/poll_instance.py +0 -0
  269. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/provider.py +0 -0
  270. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/terminal_artifacts.py +0 -0
  271. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/_lifecycle/worker.py +0 -0
  272. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/allocator.py +0 -0
  273. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/artifacts/__init__.py +0 -0
  274. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/artifacts/hf.py +0 -0
  275. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/artifacts/preload_runpod.py +0 -0
  276. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/artifacts/weight_cache.py +0 -0
  277. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/base.py +0 -0
  278. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/fit_errors.py +0 -0
  279. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/__init__.py +0 -0
  280. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/api.py +0 -0
  281. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/auth.py +0 -0
  282. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/gpus.py +0 -0
  283. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/jobs/__init__.py +0 -0
  284. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/jobs/builders.py +0 -0
  285. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/jobs/reap.py +0 -0
  286. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/preflight.py +0 -0
  287. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/lambda_/pricing.py +0 -0
  288. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/preflight.py +0 -0
  289. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/realized.py +0 -0
  290. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/__init__.py +0 -0
  291. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/api.py +0 -0
  292. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/auth.py +0 -0
  293. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/cost.py +0 -0
  294. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/gpus.py +0 -0
  295. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/job_execution.py +0 -0
  296. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/jobs.py +0 -0
  297. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/preflight.py +0 -0
  298. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/pricing.py +0 -0
  299. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/resources.py +0 -0
  300. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/serverless/__init__.py +0 -0
  301. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/runpod/serverless/endpoints.py +0 -0
  302. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/sharding.py +0 -0
  303. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/vast/__init__.py +0 -0
  304. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/vast/api.py +0 -0
  305. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/vast/auth.py +0 -0
  306. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/vast/jobs/__init__.py +0 -0
  307. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/vast/jobs/builders.py +0 -0
  308. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/vast/preflight.py +0 -0
  309. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/providers/vast/pricing.py +0 -0
  310. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/py.typed +0 -0
  311. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/__init__.py +0 -0
  312. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/artifacts.py +0 -0
  313. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/attempts.py +0 -0
  314. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/costs.py +0 -0
  315. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/deadlines.py +0 -0
  316. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/preparation.py +0 -0
  317. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/reconciliation.py +0 -0
  318. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/results/__init__.py +0 -0
  319. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/results/checkpoints.py +0 -0
  320. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/results/verified_revisions.py +0 -0
  321. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/status.py +0 -0
  322. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/submit.py +0 -0
  323. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/__init__.py +0 -0
  324. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/attach.py +0 -0
  325. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/deploy.py +0 -0
  326. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/lifecycle.py +0 -0
  327. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/recovery.py +0 -0
  328. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/retry_decision.py +0 -0
  329. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/seed_submission.py +0 -0
  330. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/supervise/transitions.py +0 -0
  331. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runner/weight_cache.py +0 -0
  332. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runtime_capsule/__init__.py +0 -0
  333. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runtime_capsule/build.py +0 -0
  334. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runtime_capsule/manifest.py +0 -0
  335. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/runtime_capsule/profiles.py +0 -0
  336. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/schema/__init__.py +0 -0
  337. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/schema/fields.py +0 -0
  338. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/__init__.py +0 -0
  339. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/adapter_check.py +0 -0
  340. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/deploy.py +0 -0
  341. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/errors.py +0 -0
  342. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/export.py +0 -0
  343. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/preflight.py +0 -0
  344. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/responses.py +0 -0
  345. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/streaming.py +0 -0
  346. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/thinking.py +0 -0
  347. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/serve/urls.py +0 -0
  348. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/__init__.py +0 -0
  349. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/__main__.py +0 -0
  350. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/app.py +0 -0
  351. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/billing/__init__.py +0 -0
  352. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/billing/charges.py +0 -0
  353. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/billing/retry.py +0 -0
  354. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/__init__.py +0 -0
  355. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/checkpoints.py +0 -0
  356. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/environment_registry.py +0 -0
  357. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/envs.py +0 -0
  358. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/projects.py +0 -0
  359. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/reconcile.py +0 -0
  360. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/repo_cleanup.py +0 -0
  361. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/run_registry.py +0 -0
  362. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/teacher_broker.py +0 -0
  363. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/teacher_errors.py +0 -0
  364. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/domain/teacher_requests.py +0 -0
  365. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/platform/__init__.py +0 -0
  366. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/platform/auth.py +0 -0
  367. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/platform/db.py +0 -0
  368. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/platform/deps.py +0 -0
  369. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/platform/internal_client.py +0 -0
  370. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/platform/locks.py +0 -0
  371. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/__init__.py +0 -0
  372. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/envs.py +0 -0
  373. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/meta.py +0 -0
  374. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/runs.py +0 -0
  375. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/serving.py +0 -0
  376. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/serving_completion.py +0 -0
  377. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/serving_revisions.py +0 -0
  378. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/serving_smoke.py +0 -0
  379. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/server/routes/teacher.py +0 -0
  380. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/source_snapshot.py +0 -0
  381. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/teacher/__init__.py +0 -0
  382. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/teacher/limits.py +0 -0
  383. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/teacher/provider_status.py +0 -0
  384. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/flash/teacher/retry_contract.py +0 -0
  385. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/scripts/build_dev_dist.py +0 -0
  386. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/scripts/check_file_size.py +0 -0
  387. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/scripts/check_function_size.py +0 -0
  388. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/scripts/check_rollout_identity_actor.py +0 -0
  389. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/scripts/check_verl_pin_exists.py +0 -0
  390. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/scripts/scrub_history.sh +0 -0
  391. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/__init__.py +0 -0
  392. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/_helpers/__init__.py +0 -0
  393. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/_helpers/profile.py +0 -0
  394. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/_helpers/runner.py +0 -0
  395. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/_helpers/source_snapshot.py +0 -0
  396. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/_helpers/specs.py +0 -0
  397. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/_helpers/teacher.py +0 -0
  398. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/_helpers/vast.py +0 -0
  399. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/capture_image_sft_processor_oracle.py +0 -0
  400. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/conftest.py +0 -0
  401. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/fixtures/image_sft_processor_oracle.json +0 -0
  402. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/fixtures/qwen35_08b_target_metadata.json +0 -0
  403. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/live/__init__.py +0 -0
  404. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/live/conftest.py +0 -0
  405. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/live/test_lambda_live.py +0 -0
  406. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/live/test_runpod_live.py +0 -0
  407. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/live/test_sft_thinking_render_live.py +0 -0
  408. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/live/test_vast_live.py +0 -0
  409. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_accounting_coverage.py +0 -0
  410. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_adapter_shard_completeness.py +0 -0
  411. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_agent_flash_cli_contract.py +0 -0
  412. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_algorithms.py +0 -0
  413. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_allocator.py +0 -0
  414. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_backend_common.py +0 -0
  415. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_backend_jobspec_contract.py +0 -0
  416. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_bake_kernel_cache.py +0 -0
  417. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_base_model_provenance.py +0 -0
  418. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_billing_retry.py +0 -0
  419. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_build_context_contract.py +0 -0
  420. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cancel_remote.py +0 -0
  421. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_catalog_consistency.py +0 -0
  422. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_catalog_only_models.py +0 -0
  423. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_charge_pricing.py +0 -0
  424. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_checkpoint_lifecycle.py +0 -0
  425. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_checkpoints.py +0 -0
  426. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_commands_coverage.py +0 -0
  427. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_credential_shadowing.py +0 -0
  428. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_errors.py +0 -0
  429. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_estimate.py +0 -0
  430. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_gpus_flag.py +0 -0
  431. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_help.py +0 -0
  432. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_main_coverage.py +0 -0
  433. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_managed.py +0 -0
  434. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_render_coverage.py +0 -0
  435. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_traces.py +0 -0
  436. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cli_wandb_warning.py +0 -0
  437. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_client.py +0 -0
  438. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_client_import_purity.py +0 -0
  439. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_client_server_integration.py +0 -0
  440. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_client_stream_reads.py +0 -0
  441. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_config_env_vars.py +0 -0
  442. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_config_overrides.py +0 -0
  443. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_console_upload.py +0 -0
  444. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_controlled_experiment_repairs.py +0 -0
  445. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cost_analytical.py +0 -0
  446. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cost_equation.py +0 -0
  447. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cost_estimate.py +0 -0
  448. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cost_hardware.py +0 -0
  449. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_cost_models.py +0 -0
  450. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_dataset_profile.py +0 -0
  451. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_deploy_alias_move_warning.py +0 -0
  452. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_deploy_latency.py +0 -0
  453. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_dev_channel.py +0 -0
  454. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_disk_gb.py +0 -0
  455. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_endpoint_name.py +0 -0
  456. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_cache_evict.py +0 -0
  457. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_delete.py +0 -0
  458. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_download.py +0 -0
  459. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_download_api.py +0 -0
  460. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_evaluations.py +0 -0
  461. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_list_api.py +0 -0
  462. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_list_cli.py +0 -0
  463. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_list_hub.py +0 -0
  464. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_no_install.py +0 -0
  465. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_publish.py +0 -0
  466. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_pull.py +0 -0
  467. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_pull_coverage.py +0 -0
  468. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_pull_loader_coverage.py +0 -0
  469. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_pull_managed_control_plane.py +0 -0
  470. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_push.py +0 -0
  471. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_rate_limit_resolve.py +0 -0
  472. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_ref_pinning.py +0 -0
  473. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_env_test.py +0 -0
  474. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_envs_coverage.py +0 -0
  475. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_export.py +0 -0
  476. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_flash_mvp.py +0 -0
  477. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_flash_worker.py +0 -0
  478. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_flashinfer_cache_dirs.py +0 -0
  479. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_freesolo_api_transport.py +0 -0
  480. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_fused_expert_warmstart.py +0 -0
  481. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_github_urlopen_retry.py +0 -0
  482. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_gpu_type_single_field.py +0 -0
  483. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_gpus.py +0 -0
  484. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_grpo_params.py +0 -0
  485. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_grpo_process_census.py +0 -0
  486. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_grpo_resident_sizing.py +0 -0
  487. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_grpo_reward_batching.py +0 -0
  488. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_grpo_rollout_contract.py +0 -0
  489. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_grpo_rollout_identity.py +0 -0
  490. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_health_liveness.py +0 -0
  491. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_hf_retry.py +0 -0
  492. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_idle_endpoint_reaper.py +0 -0
  493. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_image_environment_capability.py +0 -0
  494. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_image_incremental_processor.py +0 -0
  495. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_image_sft_markers.py +0 -0
  496. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_image_sft_processor_parity.py +0 -0
  497. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_image_tokens.py +0 -0
  498. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_infisical_secrets.py +0 -0
  499. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_instance_bootstrap_coverage.py +0 -0
  500. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_internal_client.py +0 -0
  501. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_kernel_cache.py +0 -0
  502. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_kernel_fingerprint.py +0 -0
  503. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_kv_util.py +0 -0
  504. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_lambda_api_coverage.py +0 -0
  505. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_lambda_runner.py +0 -0
  506. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_logging.py +0 -0
  507. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_login_perms.py +0 -0
  508. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_lora_rank_coverage.py +0 -0
  509. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_lora_rank_nested_rung.py +0 -0
  510. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_lora_rank_preflight.py +0 -0
  511. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_lora_targeting.py +0 -0
  512. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_lora_targeting_pinned_verl.py +0 -0
  513. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_managed_config_fields.py +0 -0
  514. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_managed_hf_repo.py +0 -0
  515. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_metrics_schema_agent_contract.py +0 -0
  516. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_mig_guard.py +0 -0
  517. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_multi_gpu_gate.py +0 -0
  518. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_multimodal_training.py +0 -0
  519. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_named_reward_metrics.py +0 -0
  520. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_oom_escalate_gpu.py +0 -0
  521. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_opd.py +0 -0
  522. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_opd_limits.py +0 -0
  523. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_opd_multiturn_eos_boundary.py +0 -0
  524. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_opd_multiturn_failure_exit.py +0 -0
  525. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_opd_replay_guard.py +0 -0
  526. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_opd_resume_safety.py +0 -0
  527. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_orchestrator_flash.py +0 -0
  528. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_packing.py +0 -0
  529. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_packing_coverage.py +0 -0
  530. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_parasail_teacher.py +0 -0
  531. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_persisted_spec_envelope.py +0 -0
  532. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_poll_helpers.py +0 -0
  533. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_preflight.py +0 -0
  534. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_projects.py +0 -0
  535. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_prompt_budget.py +0 -0
  536. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_provider_preflight_coverage.py +0 -0
  537. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_provider_routing.py +0 -0
  538. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_provider_teardown_robustness.py +0 -0
  539. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_providers_symmetry.py +0 -0
  540. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_realized_cost.py +0 -0
  541. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_repo_cleanup.py +0 -0
  542. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_resolve_params_b.py +0 -0
  543. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_rollout_samples.py +0 -0
  544. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_runmgmt.py +0 -0
  545. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_runpod_api_delete.py +0 -0
  546. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_runpod_key_fingerprint.py +0 -0
  547. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_runpod_key_waterfall.py +0 -0
  548. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_runtime_capsule.py +0 -0
  549. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_serve.py +0 -0
  550. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_serve_reasoning_content.py +0 -0
  551. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_app_coverage.py +0 -0
  552. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_auth_singleflight.py +0 -0
  553. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_billing.py +0 -0
  554. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_checkpoints_coverage.py +0 -0
  555. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_db.py +0 -0
  556. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_envs_coverage.py +0 -0
  557. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_locks_coverage.py +0 -0
  558. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_server_standalone.py +0 -0
  559. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_serving_context_preflight.py +0 -0
  560. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_serving_contract.py +0 -0
  561. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_serving_schema_coverage.py +0 -0
  562. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_sft_chunked_nll.py +0 -0
  563. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_sft_example_selection.py +0 -0
  564. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_sft_gc_off.py +0 -0
  565. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_sft_max_context.py +0 -0
  566. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_sft_startup_block.py +0 -0
  567. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_sft_train.py +0 -0
  568. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_sft_workload.py +0 -0
  569. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_source_attestation_flow.py +0 -0
  570. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_source_snapshot.py +0 -0
  571. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_spec_and_validation.py +0 -0
  572. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_spec_contract_bytes.py +0 -0
  573. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_staged_environment.py +0 -0
  574. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_step_floor.py +0 -0
  575. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_step_metrics.py +0 -0
  576. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_step_timing.py +0 -0
  577. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_structured_outputs.py +0 -0
  578. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_teacher_broker.py +0 -0
  579. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_teacher_encoding_contract.py +0 -0
  580. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_terminal_artifacts.py +0 -0
  581. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_thinking_config.py +0 -0
  582. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_train_context_preflight.py +0 -0
  583. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_training_controls.py +0 -0
  584. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_type_comment_prose.py +0 -0
  585. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_vast_api.py +0 -0
  586. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_vast_api_coverage.py +0 -0
  587. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_vast_offers.py +0 -0
  588. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_vast_provider_coverage.py +0 -0
  589. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_vast_runner.py +0 -0
  590. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_verified_revisions.py +0 -0
  591. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_verifiers.py +0 -0
  592. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_verl_checkpoint_export.py +0 -0
  593. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_verl_child_plugins.py +0 -0
  594. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_verl_silence_watchdog.py +0 -0
  595. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_version.py +0 -0
  596. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_vl_warmstart_adapter_keys.py +0 -0
  597. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_vram_architecture.py +0 -0
  598. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_wandb_link.py +0 -0
  599. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_wandb_naming.py +0 -0
  600. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_warmstart_adapter_download.py +0 -0
  601. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_warmstart_cross_repo.py +0 -0
  602. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_warmstart_error_attribution.py +0 -0
  603. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_warmstart_image_adapters.py +0 -0
  604. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_weight_cache.py +0 -0
  605. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_worker_dryrun.py +0 -0
  606. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_worker_hardexit.py +0 -0
  607. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_worker_image.py +0 -0
  608. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_worker_init_heartbeat.py +0 -0
  609. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_worker_stack.py +0 -0
  610. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_worker_thinking.py +0 -0
  611. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_workflow_contracts.py +0 -0
  612. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_workload_profile.py +0 -0
  613. {freesolo_flash_dev-1.2.89 → freesolo_flash_dev-1.2.95}/tests/test_zero2_sharding_gate.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.5
2
2
  Name: freesolo-flash-dev
3
- Version: 1.2.89
3
+ Version: 1.2.95
4
4
  Summary: Flash — managed LoRA post-training (SFT/GRPO/OPD) for Freesolo environments, driven by the `flash` CLI
5
5
  Project-URL: Homepage, https://github.com/freesolo-co/flash
6
6
  Project-URL: Repository, https://github.com/freesolo-co/flash
@@ -3,9 +3,7 @@
3
3
  from __future__ import annotations
4
4
 
5
5
  import argparse
6
- import difflib
7
6
  import math
8
- import re
9
7
  import shlex
10
8
  import sys
11
9
  from typing import NoReturn
@@ -57,6 +55,7 @@ from flash.cli.commands.traces import (
57
55
  RECORDS_FORMAT,
58
56
  cmd_traces_export,
59
57
  )
58
+ from flash.cli.errors import friendly_error
60
59
  from flash.cli.ui import render
61
60
  from flash.client.config import shadowed_login_warning
62
61
  from flash.core.catalog import ALGORITHMS
@@ -170,20 +169,6 @@ def _gpu_count_override(value: str) -> str:
170
169
  raise argparse.ArgumentTypeError(f"expected a number of gpus, got {value!r}") from None
171
170
 
172
171
 
173
- def _friendly_message(message: str) -> str:
174
- """Shorten argparse's verbose ``invalid choice: 'x' (choose from a, b, c, ...)`` into a concise
175
- ``unknown command 'x' (did you mean 'y'?)`` — the single closest match instead of dumping the
176
- whole list. Other messages pass through untouched. Styled path only; the machine path keeps
177
- argparse's exact text (scripts and the error tests match on the literal `invalid choice`)."""
178
- m = re.search(r"invalid choice: '([^']*)'(?: \(choose from (.*)\))?", message)
179
- if not m:
180
- return message
181
- bad, raw_choices = m.group(1), m.group(2) or ""
182
- choices = [c.strip().strip("'\"") for c in raw_choices.split(",") if c.strip()]
183
- near = difflib.get_close_matches(bad, choices, n=1)
184
- return f"unknown command '{bad}'" + (f" (did you mean '{near[0]}'?)" if near else "")
185
-
186
-
187
172
  class _ThemedParser(argparse.ArgumentParser):
188
173
  """Base parser whose usage errors match the rest of the themed CLI.
189
174
 
@@ -201,9 +186,13 @@ class _ThemedParser(argparse.ArgumentParser):
201
186
  if not render.styled():
202
187
  super().error(message) # argparse's raw usage + `prog: error: msg`, then exit 2
203
188
  # themed twin: the red ✗ error line (same idiom as main()'s catch-all and `flash login`),
204
- # then a dimmed pointer at this parser's own --help instead of the raw usage block. An
205
- # "invalid choice" becomes a short "did you mean" suggestion (see _friendly_message).
206
- print(render.error(_friendly_message(message)), file=sys.stderr)
189
+ # then a dimmed pointer at this parser's own --help instead of the raw usage block. unknown
190
+ # commands and flags get a short "did you mean" suggestion (see `friendly_error`). the argv
191
+ # stash is what tells it which subcommand was selected; only the root parser carries one.
192
+ print(
193
+ render.error(friendly_error(message, self, getattr(self, "_flash_argv", None))),
194
+ file=sys.stderr,
195
+ )
207
196
  # dimmed pointer at THIS parser's own --help (argparse sets prog per parser: `flash --help`
208
197
  # for the root, `flash <cmd> --help` for a subcommand) instead of the raw usage block.
209
198
  print(render.arrow(f"run `{self.prog} --help` for usage"), file=sys.stderr)
@@ -902,6 +891,12 @@ def _redacted_args(raw_args: list[str]) -> list[str]:
902
891
  def main(argv: list[str] | None = None) -> int:
903
892
  raw_args = list(argv) if argv is not None else sys.argv[1:]
904
893
  parser = _build_parser()
894
+ # the tokens this invocation was actually given, for the error hook: argparse reports a
895
+ # subcommand's unknown flags from the ROOT parser, so scoping the suggestion to the selected
896
+ # command needs the argv `main` was called with. reading sys.argv there instead would be right
897
+ # only for the console-script path and wrong for every embedded caller -- including the tests,
898
+ # where it silently reads pytest's own argv and restores the whole-tree pool.
899
+ parser._flash_argv = raw_args
905
900
  args = parser.parse_args(argv)
906
901
  configure_logging(verbosity=getattr(args, "verbose", 0))
907
902
  debug = getattr(args, "debug", False)
@@ -470,16 +470,10 @@ def _log_follow_progress(status: dict | None, fallback_state: str) -> tuple[str,
470
470
  parts = [state]
471
471
  heartbeat = status.get("last_heartbeat") if isinstance(status, dict) else None
472
472
  # retries rewind steps while state remains running, so surface the 0-based attempt identity.
473
- # prefer live `remote.attempt`; the heartbeat may belong to the superseded worker. fall back only
474
- # when `remote` is absent, not explicitly null: null marks the allocation window after teardown,
475
- # when the new attempt is unknown and the attached heartbeat is stale.
476
- from flash.providers._lifecycle.poll import _attempt_int
477
-
478
- remote = status.get("remote")
479
- remote_cleared = "remote" in status and remote is None
480
- attempt = _attempt_int(remote.get("attempt")) if isinstance(remote, dict) else None
481
- if attempt is None and not remote_cleared and isinstance(heartbeat, dict):
482
- attempt = _attempt_int(heartbeat.get("attempt"))
473
+ # `live_attempt` owns the provenance order (live `remote.attempt` first, heartbeat only when
474
+ # `remote` is absent rather than cleared at teardown) and is shared with the worker-artifact
475
+ # labelling below, so the spinner and the appended sections name the same current attempt.
476
+ attempt = render.live_attempt(status)
483
477
  if isinstance(heartbeat, dict):
484
478
  heartbeat_age_seconds = render._heartbeat_age_seconds(heartbeat.get("ts"))
485
479
  # stage and step come from the heartbeat, attempt from `remote` below. during the relaunch
@@ -712,20 +706,6 @@ def _follow_status(
712
706
  return 130
713
707
 
714
708
 
715
- def _print_worker_output(client: ApiClient, run_id: str, *, printed_any: bool = False) -> bool:
716
- for name, text in (client.get_worker_output(run_id) or {}).items():
717
- if not text:
718
- continue
719
- sep = "\n" if printed_any else ""
720
- if render.styled():
721
- print(f"{sep}{render.log_section(name)}")
722
- else:
723
- print(f"{sep}----- {name} -----")
724
- print(text, end="" if text.endswith("\n") else "\n")
725
- printed_any = True
726
- return printed_any
727
-
728
-
729
709
  def cmd_log(args) -> int:
730
710
  client = client_from_config()
731
711
  if getattr(args, "follow", False):
@@ -980,3 +960,10 @@ from flash.cli.commands.train_cost import ( # noqa: E402,F401
980
960
  _sft_cost_rows,
981
961
  _warn_if_wandb_requested_without_key,
982
962
  )
963
+
964
+ # re-exported so `commands._print_worker_output(...)` keeps resolving for `cmd_log` and the CLI tests.
965
+ from flash.cli.commands.worker_output import ( # noqa: E402,F401
966
+ _artifact_attempt,
967
+ _print_worker_output,
968
+ _worker_section_name,
969
+ )
@@ -0,0 +1,67 @@
1
+ """Printing the worker-uploaded text artifacts that `flash runs log` appends to a run log.
2
+
3
+ These sections are NOT part of the chronological log. `cmd_log` prints the control-plane log first
4
+ and appends these afterwards, so they always land at the tail no matter how old they are -- and the
5
+ plane returns the highest UPLOADED attempt, which during a retry is the attempt that just died, not
6
+ the one now running. Read without a label, the last thing on screen is a traceback from a worker
7
+ that has already been replaced.
8
+
9
+ So the job here is provenance: say which attempt produced each section, and say when that attempt is
10
+ not the live one. The old output is kept rather than hidden because it carries the failure that
11
+ explains why a retry exists at all.
12
+ """
13
+
14
+ from __future__ import annotations
15
+
16
+ import re
17
+ from typing import TYPE_CHECKING
18
+
19
+ from flash.cli.ui import render
20
+
21
+ if TYPE_CHECKING:
22
+ from flash.client import ApiClient
23
+
24
+
25
+ def _artifact_attempt(name: str) -> int | None:
26
+ """Return the bounded attempt encoded by a worker artifact name."""
27
+ from flash.providers._lifecycle.poll import _attempt_int
28
+
29
+ match = re.search(r"_attempt(\d+)\.txt$", name)
30
+ return _attempt_int(int(match.group(1))) if match else None
31
+
32
+
33
+ def _worker_section_name(name: str, current_attempt: int | None) -> str:
34
+ """Label an attempt-scoped artifact and identify superseded output."""
35
+ attempt = _artifact_attempt(name)
36
+ if attempt is None:
37
+ return name
38
+ if current_attempt is None:
39
+ return f"{name} (attempt={attempt})"
40
+ if attempt != current_attempt:
41
+ return f"{name} (attempt={attempt}, previous attempt; current attempt={current_attempt})"
42
+ return f"{name} (attempt={attempt}, current attempt)"
43
+
44
+
45
+ def _print_worker_output(client: ApiClient, run_id: str, *, printed_any: bool = False) -> bool:
46
+ worker_output = client.get_worker_output(run_id) or {}
47
+ if not worker_output:
48
+ return printed_any
49
+ try:
50
+ current_attempt = render.live_attempt(client.get_run(run_id) or {})
51
+ except Exception:
52
+ # artifact text is best-effort diagnostic output; a status refresh failure must not hide it.
53
+ current_attempt = None
54
+ for name, text in worker_output.items():
55
+ if not text:
56
+ continue
57
+ # label provenance from the filename rather than letting the final section, which is merely
58
+ # the last one appended, read as the live attempt's output.
59
+ section_name = _worker_section_name(name, current_attempt)
60
+ sep = "\n" if printed_any else ""
61
+ if render.styled():
62
+ print(f"{sep}{render.log_section(section_name)}")
63
+ else:
64
+ print(f"{sep}----- {section_name} -----")
65
+ print(text, end="" if text.endswith("\n") else "\n")
66
+ printed_any = True
67
+ return printed_any
@@ -0,0 +1,277 @@
1
+ """Turning argparse's usage errors into the themed CLI's short suggestions.
2
+
3
+ argparse reports a mistyped flag by printing the whole usage block, which buries the one token that
4
+ was actually wrong. These helpers reduce that to a single line naming the token and, where one
5
+ exists, the closest real alternative.
6
+
7
+ The hard part is making the suggestion one the user can actually follow. A subcommand's unknown
8
+ tokens are handed back to the root parser to report, so candidate options must be recovered from the
9
+ parser in effect at the rejected token's argv position. Looking only at the final selected command
10
+ crosses nested command boundaries, while looking through the whole tree offers unrelated flags.
11
+
12
+ Root flags are also positional here (`flash --debug login`, never `flash login --debug`), and `--`
13
+ stops option parsing. The suggestion context therefore carries both boundaries, plus the original
14
+ spelling of a repeated short root flag that must be moved without changing its count.
15
+ """
16
+
17
+ from __future__ import annotations
18
+
19
+ import argparse
20
+ import difflib
21
+ import re
22
+ from collections.abc import Iterable
23
+ from dataclasses import dataclass
24
+
25
+ from flash._internal.channel import CLI_NAME
26
+
27
+
28
+ @dataclass(frozen=True)
29
+ class _SuggestionContext:
30
+ options: tuple[str, ...]
31
+ root_only: frozenset[str]
32
+ reposition: str | None = None
33
+ after_terminator: bool = False
34
+
35
+
36
+ def friendly_error(
37
+ message: str, parser: argparse.ArgumentParser, argv: Iterable[str] | None
38
+ ) -> str:
39
+ """Rewrite one argparse usage error for the themed CLI.
40
+
41
+ The whole suggestion policy lives behind this call: which parser's flags are candidates, which
42
+ of them need repositioning, and how the message reads. The caller is an ``error()`` override on
43
+ every parser in the tree and should stay a two-liner -- deciding a candidate pool inline there
44
+ would put policy in a hook that exists to print.
45
+ """
46
+ if argv is None:
47
+ # a subparser raising its own error is already the parser in effect at the rejected token.
48
+ context = _SuggestionContext(tuple(sorted(_direct_options(parser))), frozenset())
49
+ else:
50
+ context = _suggestion_context(message, parser, tuple(argv))
51
+ return _friendly_message(message, context)
52
+
53
+
54
+ def _friendly_message(message: str, context: _SuggestionContext) -> str:
55
+ """Shorten argparse's verbose errors into concise suggestions on the styled path.
56
+
57
+ An ``invalid choice: 'x' (choose from a, b, c, ...)`` becomes ``unknown command 'x' (did you
58
+ mean 'y'?)`` instead of dumping the whole list. An ``unrecognized arguments: --flag value``
59
+ suggests the closest option registered on the parser that rejected it. Other messages pass
60
+ through untouched. The machine path keeps argparse's exact text for scripts and error tests.
61
+ """
62
+ m = re.search(r"invalid choice: '([^']*)'(?: \(choose from (.*)\))?", message)
63
+ if m:
64
+ bad, raw_choices = m.group(1), m.group(2) or ""
65
+ choices = [c.strip().strip("'\"") for c in raw_choices.split(",") if c.strip()]
66
+ near = difflib.get_close_matches(bad, choices, n=1)
67
+ return f"unknown command '{bad}'" + (f" (did you mean '{near[0]}'?)" if near else "")
68
+
69
+ prefix = "unrecognized arguments: "
70
+ if not message.startswith(prefix):
71
+ return message
72
+ # a bare `-` starts with a dash but names no option, so it is an ordinary positional argparse
73
+ # could not place. requiring a character after the dash keeps it out of the typo machinery,
74
+ # which would otherwise answer it with the nearest short flag.
75
+ bad = next(
76
+ (
77
+ token.split("=", 1)[0]
78
+ for token in message[len(prefix) :].split()
79
+ if token.startswith("-") and len(token.split("=", 1)[0]) > 1
80
+ ),
81
+ None,
82
+ )
83
+ if bad is None:
84
+ return message
85
+ if context.after_terminator:
86
+ return message
87
+ # a root flag in the wrong position is a placement error, not a typo. repeatable short flags
88
+ # retain the complete spelling so moving `-vv` never downgrades it to one `-v`.
89
+ if context.reposition is not None:
90
+ return _reposition_message(context.reposition)
91
+ if bad in context.root_only:
92
+ return _reposition_message(bad)
93
+ # the position-scoped pool can still include an exact spelling shared with the root. dropping it
94
+ # keeps a rejected token from being echoed back as its own correction.
95
+ candidates = [option for option in context.options if option != bad]
96
+ near = difflib.get_close_matches(bad, candidates, n=1)
97
+ if not near:
98
+ return message
99
+ suggestion = near[0]
100
+ if suggestion in context.root_only:
101
+ # a root flag only parses before the subcommand, so naming it alone hands back a correction
102
+ # that fails the same way. say where it goes, or the second attempt is the first error again.
103
+ return f"unrecognized argument '{bad}' (did you mean '{suggestion}'? {_placement_hint(suggestion)})"
104
+ return f"unrecognized argument '{bad}' (did you mean '{suggestion}'?)"
105
+
106
+
107
+ def _placement_hint(flag: str) -> str:
108
+ """Say where a root flag belongs, and claim nothing about the rest of the line.
109
+
110
+ This hint knows one thing: the flag parses only ahead of the subcommand. It does not know what
111
+ removing the flag from where it sat exposes. `--wait` takes an optional value, so a flag lifted
112
+ from between `--wait` and a run id leaves the run id to be swallowed as the timeout -- which
113
+ `_wait_seconds` then catches and explains precisely. Stating the destination and stopping there
114
+ keeps this hint true for every line; the one case it cannot see already answers itself.
115
+
116
+ Both the repositioning message and the respelling-plus-repositioning message end in this same
117
+ advice, so they share it rather than each spelling it out and drifting apart.
118
+ """
119
+ return f"it goes before the command, as `{CLI_NAME} {flag} ...`"
120
+
121
+
122
+ def _reposition_message(flag: str) -> str:
123
+ """Answer a correctly spelled root flag that landed after the subcommand."""
124
+ return f"unrecognized argument '{flag}' ({_placement_hint(flag)})"
125
+
126
+
127
+ def _suggestion_context(
128
+ message: str, root: argparse.ArgumentParser, argv: tuple[str, ...]
129
+ ) -> _SuggestionContext:
130
+ root_only = _root_only_options(root)
131
+ bad = _unrecognized_option(message)
132
+ if bad is None:
133
+ return _SuggestionContext((), root_only)
134
+ location = _option_location(root, argv, bad)
135
+ if location is None:
136
+ return _SuggestionContext((), root_only)
137
+ current, after_terminator = location
138
+ reposition = bad if _is_repeated_root_short_option(root, bad, root_only) else None
139
+ options = tuple(sorted({*_direct_options(current), *root_only}))
140
+ return _SuggestionContext(options, root_only, reposition, after_terminator)
141
+
142
+
143
+ def _unrecognized_option(message: str) -> str | None:
144
+ prefix = "unrecognized arguments: "
145
+ if not message.startswith(prefix):
146
+ return None
147
+ return next(
148
+ (
149
+ token.split("=", 1)[0]
150
+ for token in message[len(prefix) :].split()
151
+ if token.startswith("-")
152
+ ),
153
+ None,
154
+ )
155
+
156
+
157
+ def _option_location(
158
+ root: argparse.ArgumentParser, argv: tuple[str, ...], bad: str
159
+ ) -> tuple[argparse.ArgumentParser, bool] | None:
160
+ """Return the parser and terminator state at the rejected token's argv position."""
161
+ current = root
162
+ path_open = True
163
+ after_terminator = False
164
+ fallback: tuple[argparse.ArgumentParser, bool] | None = None
165
+
166
+ for token in argv:
167
+ if token == "--":
168
+ after_terminator = True
169
+ path_open = False
170
+ continue
171
+ if token.split("=", 1)[0] == bad:
172
+ location = (current, after_terminator)
173
+ fallback = location
174
+ # repeated spellings can include one accepted root occurrence and one rejected
175
+ # subcommand occurrence. choose the occurrence argparse could not consume here.
176
+ if after_terminator or len(_option_tuples(current, token)) != 1:
177
+ return location
178
+ if after_terminator or token.startswith("-") or not path_open:
179
+ continue
180
+ subparsers = next(
181
+ (a for a in current._actions if isinstance(a, argparse._SubParsersAction)), None
182
+ )
183
+ if subparsers is None:
184
+ path_open = False
185
+ continue
186
+ nxt = subparsers.choices.get(token)
187
+ if nxt is None:
188
+ path_open = False
189
+ continue
190
+ current = nxt
191
+
192
+ return fallback
193
+
194
+
195
+ def _option_tuples(parser: argparse.ArgumentParser, token: str) -> list:
196
+ """The prefix matches for a token, for tokens argparse's own helper cannot be asked about.
197
+
198
+ `_get_option_tuples` indexes the token's second character, so a bare ``-`` raises IndexError
199
+ there. A lone dash is an ordinary unrecognized positional and must reach argparse's own message
200
+ rather than crash the code that was trying to improve it.
201
+ """
202
+ if len(token) < 2:
203
+ return []
204
+ return parser._get_option_tuples(token)
205
+
206
+
207
+ def _parse_optional_fields(
208
+ parser: argparse.ArgumentParser, token: str
209
+ ) -> tuple[object, str | None, str | None] | None:
210
+ """The action, option spelling and explicit remainder argparse reads out of a token.
211
+
212
+ `_parse_optional` has three shapes across the interpreters `requires-python` admits: a 3-tuple
213
+ before 3.11.9/3.12.3, a 4-tuple once a separator was inserted, and from 3.12.11 a LIST of those
214
+ tuples, one per prefix match. Normalizing here keeps that churn in one place, and keeps the
215
+ separator out of the caller: the exact-spelling reconstruction the caller does already settles
216
+ what the separator would have told it. An unfamiliar shape returns None rather than raising,
217
+ because this runs inside the handler whose whole job is to render someone else's error.
218
+ """
219
+ parsed = parser._parse_optional(token)
220
+ if isinstance(parsed, list):
221
+ # several prefix matches means the spelling is ambiguous, so it is not one repeated flag.
222
+ parsed = parsed[0] if len(parsed) == 1 else None
223
+ if not isinstance(parsed, tuple) or len(parsed) not in (3, 4):
224
+ return None
225
+ return parsed[0], parsed[1], parsed[-1]
226
+
227
+
228
+ def _is_repeated_root_short_option(
229
+ root: argparse.ArgumentParser, token: str, root_only: frozenset[str]
230
+ ) -> bool:
231
+ """Whether token is a compact repeat of a count-style root option, such as ``-vv``."""
232
+ if not token.startswith("-") or token.startswith("--"):
233
+ return False
234
+ fields = _parse_optional_fields(root, token)
235
+ if fields is None:
236
+ return False
237
+ action, option, explicit = fields
238
+ return (
239
+ isinstance(action, argparse._CountAction)
240
+ and option in root_only
241
+ and isinstance(explicit, str)
242
+ and bool(explicit)
243
+ # the whole token must be that one short flag repeated, so `-vx` and `-v=2` are not repeats.
244
+ and token == option + option[-1] * len(explicit)
245
+ )
246
+
247
+
248
+ def _direct_options(parser: argparse.ArgumentParser) -> Iterable[str]:
249
+ for action in parser._actions:
250
+ yield from action.option_strings
251
+
252
+
253
+ def _parser_options(parser: argparse.ArgumentParser) -> Iterable[str]:
254
+ """Yield option strings registered on a parser and its subparsers."""
255
+ yield from _direct_options(parser)
256
+ for action in parser._actions:
257
+ if isinstance(action, argparse._SubParsersAction):
258
+ for subparser in action.choices.values():
259
+ yield from _parser_options(subparser)
260
+
261
+
262
+ def _root_only_options(parser: argparse.ArgumentParser) -> frozenset[str]:
263
+ """Option strings accepted only BEFORE the subcommand.
264
+
265
+ This CLI's root flags are positional: `flash --debug login` parses, `flash login --debug` does
266
+ not. A suggestion drawn from the whole option pool can therefore name a real flag that still
267
+ fails in the position the user typed it, so the caller needs to know which ones to reposition.
268
+ """
269
+ root: set[str] = set()
270
+ sub: set[str] = set()
271
+ for action in parser._actions:
272
+ if isinstance(action, argparse._SubParsersAction):
273
+ for subparser in action.choices.values():
274
+ sub.update(_parser_options(subparser))
275
+ else:
276
+ root.update(action.option_strings)
277
+ return frozenset(root - sub)
@@ -43,6 +43,33 @@ _WARMUP_HEARTBEAT_FRESH_FOR_S = 1200.0
43
43
  _WARMUP_STAGES = frozenset({"rl_train_start", "rl_initializing"})
44
44
 
45
45
 
46
+ def live_attempt(obj: dict) -> int | None:
47
+ """The attempt a status payload says is live, or None when it cannot be established.
48
+
49
+ `remote.attempt` is the plane's live attempt. It is preferred over `last_heartbeat.attempt`,
50
+ which is whichever worker produced the ping and may already be superseded. The heartbeat is a
51
+ fallback only when `remote` is ABSENT: an explicitly null `remote` is the teardown window, where
52
+ the attached ping belongs to a worker that is already gone, so falling back there would report a
53
+ dead attempt as the live one.
54
+
55
+ Shared so the status line, the log-follow spinner, and worker-artifact labelling cannot disagree
56
+ about which attempt is current -- three surfaces that a user reads within one screen of each
57
+ other, where a disagreement reads as a run that is on two attempts at once.
58
+ """
59
+ from flash.providers._lifecycle.poll import _attempt_int
60
+
61
+ remote = obj.get("remote")
62
+ if isinstance(remote, dict):
63
+ attempt = _attempt_int(remote.get("attempt"))
64
+ if attempt is not None:
65
+ return attempt
66
+ elif "remote" in obj:
67
+ # explicitly null: the teardown window. the ping is the dead worker's, so there is no answer.
68
+ return None
69
+ heartbeat = obj.get("last_heartbeat")
70
+ return _attempt_int(heartbeat.get("attempt")) if isinstance(heartbeat, dict) else None
71
+
72
+
46
73
  def heartbeat_is_current_attempt(obj: dict, heartbeat: dict) -> bool:
47
74
  """False only when the heartbeat provably belongs to a superseded retry attempt.
48
75
 
@@ -808,6 +808,7 @@ from flash.cli.ui.heartbeat import ( # noqa: E402,F401
808
808
  _superseded_hint,
809
809
  heartbeat_is_current_attempt,
810
810
  heartbeat_is_superseded,
811
+ live_attempt,
811
812
  warmup_message,
812
813
  )
813
814
  from flash.cli.ui.tables import ( # noqa: E402,F401
@@ -19,6 +19,10 @@ _KV_BLOCK_TOKENS = 16
19
19
  # floor remains authoritative at short context; longer contexts retain 1.5 gb plus 25% fragmentation.
20
20
  _KV_PROFILE_OVERHEAD_GB = 1.5
21
21
  _KV_FRAGMENTATION_MARGIN = 1.25
22
+ # the smallest share of a card vllm is given. below this the engine has no room for its own runtime
23
+ # once the kv pool is carved out, so a budget that prices under it is not a smaller engine but a
24
+ # broken one. the legacy equation and the multi-rank shard path both bottom out here.
25
+ _MIN_ENGINE_UTIL = 0.10
22
26
 
23
27
 
24
28
  def _round_up(value: int, multiple: int) -> int:
@@ -138,15 +142,18 @@ def colocate_kv_util(
138
142
  fp8_kv: bool = False,
139
143
  model_info=None,
140
144
  preserve_legacy_floor: bool = False,
145
+ tensor_parallel: int = 1,
141
146
  ) -> float:
142
- """vllm_gpu_memory_utilization for the colocated GRPO rollout engine.
147
+ """vllm_gpu_memory_utilization for one colocated rollout tensor-parallel rank.
143
148
 
144
- Budget vLLM's weight copy plus KV cache. Catalog models use geometry with measured overhead
145
- and an 8 GB floor; uncataloged models retain the conservative legacy equation.
149
+ Budget the rank's weight shard plus a conservative full KV cache. Catalog models use geometry
150
+ with measured overhead and an 8 GB floor; uncataloged models retain the legacy KV equation.
146
151
  """
147
- weights_gb = (
148
- max(0.5, float(params_b or 1.0)) * 2.0
149
- ) # vLLM's bf16 weight copy lives in the budget
152
+ total_weights_gb = max(0.5, float(params_b or 1.0)) * 2.0
153
+ tp_size = max(1, int(tensor_parallel))
154
+ # tensor parallelism shards vllm's bf16 weights, but kv heads can replicate when tp is wider than
155
+ # the model's kv-head count. shard only the weight term and keep the full kv budget on every rank.
156
+ weights_gb = total_weights_gb if tp_size == 1 else total_weights_gb / tp_size
150
157
  # catalog geometry is authoritative. active params remain only for the uncataloged fallback, while
151
158
  # the weight copy always uses total parameters.
152
159
  kv_params_b = float(active_params_b) if active_params_b else params_b
@@ -169,7 +176,7 @@ def colocate_kv_util(
169
176
  preserve_legacy_floor=preserve_legacy_floor,
170
177
  ),
171
178
  )
172
- return max(0.10, min(_util_cap, (weights_gb + kv_gb) / max(1.0, total_vram_gb)))
179
+ return max(_MIN_ENGINE_UTIL, min(_util_cap, (weights_gb + kv_gb) / max(1.0, total_vram_gb)))
173
180
  # Sleep mode keeps a larger pool (1.5x margin): the engine is offloaded during the backward, so a
174
181
  # bigger rollout-phase KV does not compete with the training peak.
175
182
  kv_pool_gb = max(
@@ -184,4 +191,9 @@ def colocate_kv_util(
184
191
  preserve_legacy_floor=preserve_legacy_floor,
185
192
  ),
186
193
  )
187
- return min(_util_cap, (weights_gb + kv_pool_gb) / max(1.0, total_vram_gb))
194
+ sized = min(_util_cap, (weights_gb + kv_pool_gb) / max(1.0, total_vram_gb))
195
+ # sharding the weight term can drive a small model's rank budget low enough that vllm has no
196
+ # room left for its own runtime once the kv pool is carved out -- a 4B model on 2 cards prices
197
+ # under this floor. single-rank sizing carries the whole weight copy and never gets that small,
198
+ # so the floor exists only where sharding created the problem.
199
+ return max(_MIN_ENGINE_UTIL, sized) if tp_size > 1 else sized
@@ -374,7 +374,7 @@ def run_opd_train(spec=None) -> None:
374
374
  # and on an image run that fan-out exhausted the grpo worker container's threads.
375
375
  "multimodal": bool(multimodal),
376
376
  "gpu_mem_util": _resolve_opd_gpu_mem_util(
377
- request, prompt_state, runtime, model_id, fp8_kv
377
+ request, prompt_state, workload, runtime, model_id, fp8_kv
378
378
  ),
379
379
  "loggers": runtime.loggers,
380
380
  # resolved from the out-of-process capability probe, never by opening cuda in this parent -- see fused_ce_backend.
@@ -535,6 +535,7 @@ def _spec_gpu_type(spec: Any) -> str:
535
535
  def _resolve_opd_gpu_mem_util(
536
536
  request: _OpdRequest,
537
537
  prompt_state: _PromptState,
538
+ workload: _WorkloadState,
538
539
  runtime: _RuntimeState,
539
540
  model_id: str,
540
541
  fp8_kv: bool,
@@ -559,12 +560,15 @@ def _resolve_opd_gpu_mem_util(
559
560
  "model_id": model_id,
560
561
  "model_revision": str(getattr(request, "model_revision", "") or ""),
561
562
  "engine_len": int(prompt_state.max_model_len),
562
- "group_size": int(request.knobs.group_size),
563
+ # opd submits prompts_per_step * group_size generations to the rollout engine together.
564
+ # grpo's concurrency is group_size because its resolver receives one prompt group here.
565
+ "group_size": int(workload.prompts_per_step) * int(request.knobs.group_size),
563
566
  },
564
567
  gpu_type=_spec_gpu_type(getattr(request, "spec", None)),
565
568
  n_gpus=int(runtime.gpu_count),
566
569
  fp8_kv=bool(fp8_kv),
567
570
  sleep_unsupported=rollout_sleep_unsupported(model_id),
571
+ preserve_legacy_floor=True,
568
572
  )
569
573
 
570
574