rhylthyme-cli-runner 0.2.8a0__tar.gz → 0.2.9a0__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 (89) hide show
  1. {rhylthyme_cli_runner-0.2.8a0/src/rhylthyme_cli_runner.egg-info → rhylthyme_cli_runner-0.2.9a0}/PKG-INFO +1 -1
  2. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/setup.py +1 -1
  3. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/__init__.py +1 -1
  4. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/program_runner.py +36 -9
  5. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0/src/rhylthyme_cli_runner.egg-info}/PKG-INFO +1 -1
  6. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_instruments.py +2 -2
  7. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/LICENSE +0 -0
  8. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/README.md +0 -0
  9. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/pyproject.toml +0 -0
  10. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/setup.cfg +0 -0
  11. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/cli.py +0 -0
  12. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/environment_icons.py +0 -0
  13. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/environment_loader.py +0 -0
  14. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/environment_schemas.py +0 -0
  15. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/__init__.py +0 -0
  16. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/cli.py +0 -0
  17. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/compare.py +0 -0
  18. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/gold.py +0 -0
  19. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/harness.py +0 -0
  20. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/llm.py +0 -0
  21. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/matcher.py +0 -0
  22. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/metrics.py +0 -0
  23. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/patterns/__init__.py +0 -0
  24. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/patterns/authoring_guide.md +0 -0
  25. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/patterns/baseline.md +0 -0
  26. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/patterns/baseline.py +0 -0
  27. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/patterns/extract.py +0 -0
  28. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/patterns/four_turn.py +0 -0
  29. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/eval/report.py +0 -0
  30. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/expand_replicates.py +0 -0
  31. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/__init__.py +0 -0
  32. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/calibrate.py +0 -0
  33. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/calibrate_cli.py +0 -0
  34. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/cli.py +0 -0
  35. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/evaluate.py +0 -0
  36. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/evaluate_cli.py +0 -0
  37. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/factors.py +0 -0
  38. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/hash.py +0 -0
  39. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/predict.py +0 -0
  40. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/recorder.py +0 -0
  41. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/render.py +0 -0
  42. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/replay.py +0 -0
  43. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/report.py +0 -0
  44. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/report_cli.py +0 -0
  45. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/store.py +0 -0
  46. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/synth.py +0 -0
  47. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/history/usable.py +0 -0
  48. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/import_cli.py +0 -0
  49. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/instance_checks.py +0 -0
  50. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/instruments.py +0 -0
  51. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/program_planner.py +0 -0
  52. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/remote/__init__.py +0 -0
  53. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/remote/auth.py +0 -0
  54. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/remote/checks.py +0 -0
  55. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/remote/cli.py +0 -0
  56. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/remote/mcp_client.py +0 -0
  57. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/render_cli.py +0 -0
  58. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner/validate_program.py +0 -0
  59. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner.egg-info/SOURCES.txt +0 -0
  60. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner.egg-info/dependency_links.txt +0 -0
  61. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner.egg-info/entry_points.txt +0 -0
  62. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner.egg-info/requires.txt +0 -0
  63. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/src/rhylthyme_cli_runner.egg-info/top_level.txt +0 -0
  64. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_calibrate.py +0 -0
  65. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_cli.py +0 -0
  66. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_eval_baseline.py +0 -0
  67. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_eval_harness.py +0 -0
  68. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_eval_providers.py +0 -0
  69. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_eval_scorer.py +0 -0
  70. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_evaluate.py +0 -0
  71. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_example_validation.py +0 -0
  72. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_examples_integration.py +0 -0
  73. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_expand_replicates.py +0 -0
  74. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_hash_parity.py +0 -0
  75. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_history_report.py +0 -0
  76. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_import_cli.py +0 -0
  77. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_mcp_checks.py +0 -0
  78. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_planner_time_strings.py +0 -0
  79. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_predict.py +0 -0
  80. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_program_runner.py +0 -0
  81. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_remote.py +0 -0
  82. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_render_cli.py +0 -0
  83. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_replay.py +0 -0
  84. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_run_recorder.py +0 -0
  85. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_skill.py +0 -0
  86. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_synth.py +0 -0
  87. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_usable.py +0 -0
  88. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_validate_examples_ci.py +0 -0
  89. {rhylthyme_cli_runner-0.2.8a0 → rhylthyme_cli_runner-0.2.9a0}/tests/test_validate_program.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: rhylthyme-cli-runner
3
- Version: 0.2.8a0
3
+ Version: 0.2.9a0
4
4
  Summary: CLI runner for Rhylthyme real-time program schedules
5
5
  Home-page: https://github.com/rhylthyme/rhylthyme-cli-runner
6
6
  Author: Rhylthyme Team
@@ -19,7 +19,7 @@ def read_readme():
19
19
 
20
20
  setup(
21
21
  name="rhylthyme-cli-runner",
22
- version="0.2.8a0",
22
+ version="0.2.9a0",
23
23
  description="CLI runner for Rhylthyme real-time program schedules",
24
24
  long_description=read_readme(),
25
25
  long_description_content_type="text/markdown",
@@ -6,7 +6,7 @@ This package provides the command-line interface for running and validating
6
6
  Rhylthyme real-time program schedules.
7
7
  """
8
8
 
9
- __version__ = "0.2.8a0"
9
+ __version__ = "0.2.9a0"
10
10
  __author__ = "Rhylthyme Team"
11
11
  __description__ = "CLI runner for Rhylthyme real-time program schedules"
12
12
 
@@ -128,6 +128,30 @@ except ImportError: # pragma: no cover - validator not importable
128
128
  return sign * parse_time_string(text.lstrip("+-"))
129
129
 
130
130
 
131
+ INSTRUMENT_DURATION_PARAMS = (
132
+ "duration",
133
+ "duration_seconds",
134
+ "seconds",
135
+ "run_time",
136
+ "time",
137
+ "timeout",
138
+ )
139
+
140
+
141
+ def _instrument_estimate_seconds(instrument: Dict[str, Any]) -> float:
142
+ """rhylthyme_galago.fill_durations' offline estimate: params, else 60 s."""
143
+ params = instrument.get("params") or {}
144
+ for key in INSTRUMENT_DURATION_PARAMS:
145
+ value = params.get(key)
146
+ if (
147
+ isinstance(value, (int, float))
148
+ and not isinstance(value, bool)
149
+ and value > 0
150
+ ):
151
+ return float(value)
152
+ return 60.0
153
+
154
+
131
155
  class StepStatus(Enum):
132
156
  """Enum representing the status of a step."""
133
157
 
@@ -241,7 +265,9 @@ class Step:
241
265
  if self.instrument and self.duration_type is None:
242
266
  self.duration_type = DurationType.INDEFINITE
243
267
  self.min_seconds = 0.0
244
- self.default_seconds = 60.0
268
+ # For display and upcoming events only: the same estimate as
269
+ # planning and the timeline (a duration-like param, else 60 s)
270
+ self.default_seconds = _instrument_estimate_seconds(self.instrument)
245
271
 
246
272
  # Extract start trigger information
247
273
  start_trigger_data = step_data["startTrigger"]
@@ -984,10 +1010,9 @@ class ProgramRunner:
984
1010
 
985
1011
  # If auto_start is False, set the program to wait for manual start
986
1012
  if not self.auto_start:
987
- self.status_message = (
988
- "Program waiting for manual start. Press 's' to start."
989
- )
990
- # The clock is running from here (is_running stays True)
1013
+ # The clock is running from here (is_running stays True), so say
1014
+ # so: instrument steps may already be sending commands.
1015
+ self.status_message = "Program running. Press 'p' to pause, 'q' to quit."
991
1016
  self.emit_event(
992
1017
  "program_started",
993
1018
  {"time": self.program_start_time, "wall_time": time.time()},
@@ -1100,7 +1125,8 @@ class ProgramRunner:
1100
1125
  if step.step_id not in self.failed_steps:
1101
1126
  self.failed_steps.append(step.step_id)
1102
1127
  self.status_message = (
1103
- f"FAILED {self.failure_text(step)} | r: retry x: skip A: abort program"
1128
+ "Paused new steps: an instrument command failed. "
1129
+ "r retries it, x marks it done, A (twice) aborts the program."
1104
1130
  )
1105
1131
  logging.error(f"Step {step.step_id} failed: {self.failure_text(step)}")
1106
1132
  self.emit_event(
@@ -2981,9 +3007,10 @@ def draw_ui(stdscr, runner: ProgramRunner) -> None:
2981
3007
  events_y + 1, events_col_x + 2, "No upcoming events", curses.color_pair(5)
2982
3008
  )
2983
3009
 
2984
- # Draw available triggers
3010
+ # Draw available triggers (while a failed step holds the program, its
3011
+ # banner takes this place instead)
2985
3012
  triggers_y = height - 4
2986
- available_triggers = runner.get_available_triggers()
3013
+ available_triggers = [] if runner.failed_steps else runner.get_available_triggers()
2987
3014
  if available_triggers:
2988
3015
  safe_addstr(triggers_y, 2, "Available Triggers:", curses.A_BOLD)
2989
3016
  trigger_names = [trigger["name"] for trigger in available_triggers]
@@ -2999,7 +3026,7 @@ def draw_ui(stdscr, runner: ProgramRunner) -> None:
2999
3026
  )
3000
3027
  banner += " | r: retry x: skip (mark done) A: abort program "
3001
3028
  safe_addstr(
3002
- height - 3, 2, banner[: width - 4], curses.A_BOLD | curses.A_REVERSE
3029
+ height - 4, 2, banner[: width - 4], curses.A_BOLD | curses.A_REVERSE
3003
3030
  )
3004
3031
 
3005
3032
  # Draw status message
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: rhylthyme-cli-runner
3
- Version: 0.2.8a0
3
+ Version: 0.2.9a0
4
4
  Summary: CLI runner for Rhylthyme real-time program schedules
5
5
  Home-page: https://github.com/rhylthyme/rhylthyme-cli-runner
6
6
  Author: Rhylthyme Team
@@ -504,8 +504,8 @@ def test_error_replies_fail_the_step(code):
504
504
  "errorMessage": "boom",
505
505
  }
506
506
  assert runner.failed_steps == ["shake"]
507
- assert f"FAILED shake: shaker.start_shake {code} (boom)" in runner.status_message
508
- assert "r: retry x: skip A: abort program" in runner.status_message
507
+ assert runner.failure_text(shake) == f"shake: shaker.start_shake {code} (boom)"
508
+ assert "r retries it, x marks it done, A (twice) aborts" in runner.status_message
509
509
  failed = [d for k, d in events if k == "step_failed"]
510
510
  assert failed[0]["code"] == code
511
511