self-evolve-framework 1.5.0 → 1.6.0

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 (149) hide show
  1. package/package.json +1 -1
  2. package/template/skills/skillopt-sleep/SKILL.md +42 -0
  3. package/template/skills/skillopt-sleep/configs/_base_/default.yaml +103 -0
  4. package/template/skills/skillopt-sleep/configs/alfworld/default.yaml +29 -0
  5. package/template/skills/skillopt-sleep/configs/docvqa/default.yaml +28 -0
  6. package/template/skills/skillopt-sleep/configs/features/soft_gate.yaml +47 -0
  7. package/template/skills/skillopt-sleep/configs/livemathematicianbench/default.yaml +22 -0
  8. package/template/skills/skillopt-sleep/configs/officeqa/default.yaml +34 -0
  9. package/template/skills/skillopt-sleep/configs/searchqa/default.yaml +32 -0
  10. package/template/skills/skillopt-sleep/configs/spreadsheetbench/default.yaml +34 -0
  11. package/template/skills/skillopt-sleep/scripts/framework/skillopt/__init__.py +28 -0
  12. package/template/skills/skillopt-sleep/scripts/framework/skillopt/config.py +282 -0
  13. package/template/skills/skillopt-sleep/scripts/framework/skillopt/datasets/__init__.py +7 -0
  14. package/template/skills/skillopt-sleep/scripts/framework/skillopt/datasets/base.py +512 -0
  15. package/template/skills/skillopt-sleep/scripts/framework/skillopt/engine/__init__.py +9 -0
  16. package/template/skills/skillopt-sleep/scripts/framework/skillopt/engine/trainer.py +2379 -0
  17. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/__init__.py +1 -0
  18. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/_template/README.md +43 -0
  19. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/_template/config_template.yaml +55 -0
  20. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/_template/env_template.py +151 -0
  21. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/_template/loader_template.py +87 -0
  22. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/__init__.py +5 -0
  23. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/adapter.py +428 -0
  24. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/dataloader.py +123 -0
  25. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/prompts/analyst_error.md +55 -0
  26. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/prompts/analyst_success.md +33 -0
  27. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/prompts/rollout_no_history.md +8 -0
  28. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/prompts/rollout_with_history.md +9 -0
  29. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/prompts/rollout_with_memory.md +16 -0
  30. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/reflect.py +4 -0
  31. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/rollout.py +366 -0
  32. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/skills/initial.md +45 -0
  33. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/__init__.py +9 -0
  34. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/alfworld_envs.py +221 -0
  35. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/alfworld_projection.py +60 -0
  36. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/alfworld_prompts.py +8 -0
  37. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/config_tw.yaml +145 -0
  38. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/env_base.py +84 -0
  39. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/env_manager.py +139 -0
  40. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/alfworld/vendor/memory.py +87 -0
  41. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/base.py +329 -0
  42. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/__init__.py +1 -0
  43. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/adapter.py +90 -0
  44. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/dataloader.py +61 -0
  45. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/evaluator.py +113 -0
  46. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/prompts/analyst_error.md +35 -0
  47. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/prompts/analyst_success.md +24 -0
  48. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/prompts/rollout_system.md +12 -0
  49. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/rollout.py +391 -0
  50. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/docvqa/skills/initial.md +11 -0
  51. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/__init__.py +1 -0
  52. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/adapter.py +129 -0
  53. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/dataloader.py +308 -0
  54. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/evaluator.py +62 -0
  55. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/prompts/analyst_error.md +37 -0
  56. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/prompts/analyst_success.md +25 -0
  57. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/prompts/rollout_system.md +12 -0
  58. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/reflect.py +4 -0
  59. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/rollout.py +434 -0
  60. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/livemathematicianbench/skills/initial.md +16 -0
  61. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/__init__.py +1 -0
  62. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/adapter.py +112 -0
  63. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/dataloader.py +71 -0
  64. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/evaluator.py +46 -0
  65. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/prompts/analyst_error.md +37 -0
  66. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/prompts/analyst_success.md +25 -0
  67. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/prompts/rollout_system.md +15 -0
  68. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/rollout.py +799 -0
  69. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/skills/initial.md +15 -0
  70. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/officeqa/tool_runtime.py +552 -0
  71. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/__init__.py +1 -0
  72. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/adapter.py +96 -0
  73. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/dataloader.py +42 -0
  74. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/evaluator.py +100 -0
  75. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/prompts/analyst_error.md +46 -0
  76. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/prompts/analyst_success.md +32 -0
  77. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/prompts/rollout_system.md +13 -0
  78. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/reflect.py +4 -0
  79. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/rollout.py +494 -0
  80. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/searchqa/skills/initial.md +3 -0
  81. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/__init__.py +5 -0
  82. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/adapter.py +159 -0
  83. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/codegen_agent.py +731 -0
  84. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/dataloader.py +37 -0
  85. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/evaluator.py +158 -0
  86. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/executor.py +67 -0
  87. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/prompts/analyst_error.md +46 -0
  88. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/prompts/analyst_success.md +32 -0
  89. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/prompts/codegen_system.md +1 -0
  90. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/prompts/critical_rules.md +9 -0
  91. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/prompts/react_system.md +21 -0
  92. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/react_agent.py +395 -0
  93. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/reflect.py +4 -0
  94. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/rollout.py +979 -0
  95. package/template/skills/skillopt-sleep/scripts/framework/skillopt/envs/spreadsheetbench/skills/initial.md +56 -0
  96. package/template/skills/skillopt-sleep/scripts/framework/skillopt/evaluation/__init__.py +13 -0
  97. package/template/skills/skillopt-sleep/scripts/framework/skillopt/evaluation/gate.py +148 -0
  98. package/template/skills/skillopt-sleep/scripts/framework/skillopt/gradient/__init__.py +15 -0
  99. package/template/skills/skillopt-sleep/scripts/framework/skillopt/gradient/aggregate.py +253 -0
  100. package/template/skills/skillopt-sleep/scripts/framework/skillopt/gradient/reflect.py +635 -0
  101. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/__init__.py +514 -0
  102. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/azure_openai.py +915 -0
  103. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/backend_config.py +185 -0
  104. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/claude_backend.py +371 -0
  105. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/codex_backend.py +666 -0
  106. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/codex_harness.py +1057 -0
  107. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/common.py +229 -0
  108. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/minimax_backend.py +277 -0
  109. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/qwen_backend.py +456 -0
  110. package/template/skills/skillopt-sleep/scripts/framework/skillopt/model/router.py +236 -0
  111. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/__init__.py +15 -0
  112. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/appendix.py +156 -0
  113. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/clip.py +109 -0
  114. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/lr_autonomous.py +108 -0
  115. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/meta_skill.py +79 -0
  116. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/rewrite.py +59 -0
  117. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/scheduler.py +127 -0
  118. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/select.py +4 -0
  119. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/skill.py +201 -0
  120. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/skill_aware.py +206 -0
  121. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/slow_update.py +396 -0
  122. package/template/skills/skillopt-sleep/scripts/framework/skillopt/optimizer/update_modes.py +135 -0
  123. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/__init__.py +63 -0
  124. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/analyst_error.md +41 -0
  125. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/analyst_error_full_rewrite.md +32 -0
  126. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/analyst_error_rewrite.md +44 -0
  127. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/analyst_success.md +36 -0
  128. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/analyst_success_full_rewrite.md +30 -0
  129. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/analyst_success_rewrite.md +33 -0
  130. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/lr_autonomous.md +20 -0
  131. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_failure.md +30 -0
  132. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_failure_full_rewrite.md +28 -0
  133. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_failure_rewrite.md +26 -0
  134. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_final.md +33 -0
  135. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_final_full_rewrite.md +28 -0
  136. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_final_rewrite.md +25 -0
  137. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_success.md +28 -0
  138. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_success_full_rewrite.md +28 -0
  139. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/merge_success_rewrite.md +25 -0
  140. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/meta_skill.md +40 -0
  141. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/ranking.md +20 -0
  142. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/ranking_rewrite.md +15 -0
  143. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/rewrite_skill.md +25 -0
  144. package/template/skills/skillopt-sleep/scripts/framework/skillopt/prompts/slow_update.md +60 -0
  145. package/template/skills/skillopt-sleep/scripts/framework/skillopt/scheduler/__init__.py +8 -0
  146. package/template/skills/skillopt-sleep/scripts/framework/skillopt/types.py +306 -0
  147. package/template/skills/skillopt-sleep/scripts/framework/skillopt/utils/__init__.py +4 -0
  148. package/template/skills/skillopt-sleep/scripts/framework/skillopt/utils/json_utils.py +172 -0
  149. package/template/skills/skillopt-sleep/scripts/framework/skillopt/utils/scoring.py +28 -0
@@ -0,0 +1 @@
1
+ """ReflACT environment adapters."""
@@ -0,0 +1,43 @@
1
+ # Benchmark Template
2
+
3
+ This directory provides scaffold files for adding a new benchmark to SkillOpt.
4
+
5
+ ## Files
6
+
7
+ - `env_template.py` — Environment adapter template (subclasses
8
+ `EnvAdapter`; implements the 4 abstract methods so the file is
9
+ instantiable out of the box — `reflect` is inherited).
10
+ - `loader_template.py` — Data loader template (subclasses
11
+ `SplitDataLoader`; implements `load_split_items` for `.json`/`.jsonl`).
12
+ - `config_template.yaml` — Config file template.
13
+
14
+ ## Usage
15
+
16
+ 1. **Copy the directory:**
17
+ ```bash
18
+ cp -r skillopt/envs/_template skillopt/envs/your_benchmark
19
+ ```
20
+ 2. **Rename the files** (drop the `_template` suffix):
21
+ ```bash
22
+ cd skillopt/envs/your_benchmark
23
+ mv env_template.py adapter.py
24
+ mv loader_template.py dataloader.py
25
+ ```
26
+ …and inside each file rename the classes
27
+ (`TemplateBenchmarkEnv → YourBenchmarkAdapter`,
28
+ `TemplateBenchmarkLoader → YourBenchmarkLoader`)
29
+ and fix the cross-import in `adapter.py`.
30
+ 3. **Implement the TODO blocks** inside `adapter.py:rollout` and the
31
+ `_normalize_item` helper in `dataloader.py`. (`reflect` is inherited from
32
+ `EnvAdapter`; override it only for custom reflection logic.)
33
+ 4. **Register** the adapter — add a `try / except ImportError` block in
34
+ `scripts/train.py`'s `_register_builtins()` mapping the registry key
35
+ to your `YourBenchmarkAdapter` class. There is no
36
+ `BENCHMARK_REGISTRY` dict in `skillopt/envs/__init__.py`; the live
37
+ registry is `_ENV_REGISTRY` in `scripts/train.py`.
38
+ 5. **Create the config** at `configs/your_benchmark/default.yaml`
39
+ (start from `config_template.yaml`). `_base_` is a **string path**,
40
+ not a list.
41
+
42
+ See the [Add a New Benchmark guide](../../../docs/guide/new-benchmark.md)
43
+ for the full step-by-step with a worked `docfaithful` example.
@@ -0,0 +1,55 @@
1
+ # ──────────────────────────────────────────────────
2
+ # SkillOpt Config Template — <Your Benchmark Name>
3
+ # ──────────────────────────────────────────────────
4
+ # Copy this file to configs/<your_benchmark>/default.yaml
5
+ # and customize the values below.
6
+
7
+ # Inherit global defaults.
8
+ # NOTE: `_base_` is a string path, not a list.
9
+ _base_: ../_base_/default.yaml
10
+
11
+ # ── Environment ──────────────────────────────────
12
+ env:
13
+ name: your_benchmark # Must match the key registered in scripts/train.py
14
+ # Optional: a seed skill document. Create this file yourself before the
15
+ # first run, or omit the key to start from an empty skill.
16
+ # skill_init: skillopt/envs/your_benchmark/skills/initial.md
17
+ data_path: data/your_benchmark # Path to your data (for split_mode: ratio)
18
+ split_dir: "" # Set this and use split_mode: split_dir for pre-split data
19
+ split_mode: ratio # "ratio" or "split_dir"
20
+ split_ratio: "2:1:7" # train:val:test (used when split_mode: ratio)
21
+ workers: 4 # Parallel rollout workers
22
+ max_completion_tokens: 4096 # Cap per target-model call
23
+ limit: 0 # 0 = no limit; small int = debug sample
24
+
25
+ # ── Training ─────────────────────────────────────
26
+ train:
27
+ num_epochs: 4
28
+ batch_size: 40
29
+ accumulation: 1
30
+ seed: 42
31
+
32
+ # ── Gradient (Reflection) ───────────────────────
33
+ gradient:
34
+ analyst_workers: 16 # Parallel reflection workers
35
+ minibatch_size: 8
36
+ merge_batch_size: 8
37
+
38
+ # ── Optimizer ────────────────────────────────────
39
+ optimizer:
40
+ learning_rate: 4 # Max edits per step (edit budget)
41
+ lr_scheduler: cosine # cosine | linear | constant | autonomous
42
+ use_slow_update: true # Epoch-boundary momentum
43
+ use_meta_skill: true # Cross-epoch optimizer memory
44
+
45
+ # ── Evaluation ───────────────────────────────────
46
+ evaluation:
47
+ use_gate: true # Validation gating
48
+ eval_test: true # Run test eval after training
49
+
50
+ # ── Model ────────────────────────────────────────
51
+ # Override only what differs from the inherited defaults.
52
+ model:
53
+ optimizer_backend: openai_chat # openai_chat | claude_chat | qwen_chat | minimax_chat
54
+ target_backend: openai_chat # … plus codex_exec / claude_code_exec for target only
55
+ reasoning_effort: medium
@@ -0,0 +1,151 @@
1
+ """
2
+ Benchmark Environment Template
3
+ ===============================
4
+ Copy this file and implement the TODO sections to add a new benchmark.
5
+
6
+ The EnvAdapter is responsible for:
7
+ 1. Building per-batch environment managers (train and eval splits).
8
+ 2. Running rollouts under the current skill document.
9
+ 3. Reflecting on those rollouts into raw patch dicts.
10
+ 4. Reporting the distinct task types in your data (for stratified
11
+ sampling).
12
+
13
+ For a fully worked example see ``skillopt/envs/officeqa/``.
14
+ """
15
+ from __future__ import annotations
16
+
17
+ from skillopt.datasets.base import BatchSpec
18
+ from skillopt.envs.base import EnvAdapter
19
+ from skillopt.envs._template.loader_template import TemplateBenchmarkLoader
20
+
21
+
22
+ class TemplateBenchmarkEnv(EnvAdapter):
23
+ """
24
+ Environment adapter for <Your Benchmark Name>.
25
+
26
+ Rename this class. Each abstract method below is required by
27
+ :class:`skillopt.envs.base.EnvAdapter`. The template implementations
28
+ are minimal so this file is importable and instantiable; replace the
29
+ TODOs with real logic.
30
+ """
31
+
32
+ def __init__(
33
+ self,
34
+ split_dir: str = "",
35
+ data_path: str = "",
36
+ split_mode: str = "split_dir",
37
+ split_ratio: str = "2:1:7",
38
+ split_seed: int = 42,
39
+ split_output_dir: str = "",
40
+ workers: int = 4,
41
+ analyst_workers: int = 4,
42
+ failure_only: bool = False,
43
+ minibatch_size: int = 8,
44
+ edit_budget: int = 4,
45
+ seed: int = 42,
46
+ limit: int = 0,
47
+ max_completion_tokens: int = 4096,
48
+ ) -> None:
49
+ self.workers = workers
50
+ self.analyst_workers = analyst_workers
51
+ self.failure_only = failure_only
52
+ self.minibatch_size = minibatch_size
53
+ self.edit_budget = edit_budget
54
+ self.max_completion_tokens = int(max_completion_tokens)
55
+ self.dataloader = TemplateBenchmarkLoader(
56
+ split_dir=split_dir,
57
+ data_path=data_path,
58
+ split_mode=split_mode,
59
+ split_ratio=split_ratio,
60
+ split_seed=split_seed,
61
+ split_output_dir=split_output_dir,
62
+ seed=seed,
63
+ limit=limit,
64
+ )
65
+
66
+ # ── Lifecycle hooks ────────────────────────────────────────────────
67
+
68
+ def setup(self, cfg: dict) -> None:
69
+ super().setup(cfg)
70
+ self.dataloader.setup(cfg)
71
+
72
+ def get_dataloader(self):
73
+ return self.dataloader
74
+
75
+ # ── Batch → env manager ────────────────────────────────────────────
76
+
77
+ def build_env_from_batch(self, batch: BatchSpec, **kwargs):
78
+ # Dataset-backed envs typically just pass items straight through.
79
+ return list(batch.payload or [])
80
+
81
+ def build_train_env(self, batch_size: int, seed: int, **kwargs):
82
+ batch = self.dataloader.build_train_batch(
83
+ batch_size=batch_size, seed=seed, **kwargs
84
+ )
85
+ return self.build_env_from_batch(batch, **kwargs)
86
+
87
+ def build_eval_env(self, env_num: int, split: str, seed: int, **kwargs):
88
+ batch = self.dataloader.build_eval_batch(
89
+ env_num=env_num, split=split, seed=seed, **kwargs
90
+ )
91
+ return self.build_env_from_batch(batch, **kwargs)
92
+
93
+ # ── Rollout: run episodes under current skill ──────────────────────
94
+
95
+ def rollout(
96
+ self,
97
+ env_manager,
98
+ skill_content: str,
99
+ out_dir: str,
100
+ **kwargs,
101
+ ) -> list[dict]:
102
+ """
103
+ Run a batch of episodes under the current skill.
104
+
105
+ TODO: replace this loop with your real rollout. For each item:
106
+ 1. Build the prompt using `skill_content` as the system message.
107
+ 2. Call your target model.
108
+ 3. Score the prediction.
109
+ 4. Return a dict with at minimum: ``id`` (str), ``hard`` (0|1),
110
+ ``soft`` (float in [0, 1]). Add any env-specific extras you
111
+ need for reflect() — they will be preserved on
112
+ ``RolloutResult.extras``.
113
+ """
114
+ items: list[dict] = env_manager
115
+ results: list[dict] = []
116
+ for item in items:
117
+ # ── REPLACE THIS BLOCK WITH YOUR REAL ROLLOUT ──
118
+ results.append(
119
+ {
120
+ "id": str(item.get("id", "")),
121
+ "hard": 0,
122
+ "soft": 0.0,
123
+ "predicted_answer": "",
124
+ "question": item.get("question", ""),
125
+ "fail_reason": "template rollout — not implemented",
126
+ }
127
+ )
128
+ return results
129
+
130
+ # ── Reflect (inherited) ─────────────────────────────────────────────
131
+ #
132
+ # ``reflect`` is inherited from ``EnvAdapter``: the default delegates to
133
+ # ``skillopt.gradient.reflect.run_minibatch_reflect`` using your
134
+ # ``analyst_error_*`` / ``analyst_success_*`` prompts. You do NOT need to
135
+ # implement it — override only if your benchmark needs custom reflection.
136
+
137
+ # ── Stratification hint ────────────────────────────────────────────
138
+
139
+ def get_task_types(self) -> list[str]:
140
+ """Distinct task-type strings used for stratified sampling."""
141
+ seen: list[str] = []
142
+ all_items = (
143
+ self.dataloader.train_items
144
+ + self.dataloader.val_items
145
+ + self.dataloader.test_items
146
+ )
147
+ for item in all_items:
148
+ tt = str(item.get("task_type") or "template")
149
+ if tt not in seen:
150
+ seen.append(tt)
151
+ return seen or ["template"]
@@ -0,0 +1,87 @@
1
+ """
2
+ Benchmark Data Loader Template
3
+ ================================
4
+ Copy this file and implement ``load_split_items`` to load your benchmark
5
+ data. The loader is a :class:`skillopt.datasets.base.SplitDataLoader`
6
+ subclass — the base class handles both ``split_mode="split_dir"`` (read
7
+ an existing train/val/test layout) and ``split_mode="ratio"`` (build the
8
+ splits from a single raw file deterministically).
9
+
10
+ For a fully worked example see
11
+ ``skillopt/envs/officeqa/dataloader.py``.
12
+ """
13
+ from __future__ import annotations
14
+
15
+ import json
16
+ from pathlib import Path
17
+
18
+ from skillopt.datasets.base import SplitDataLoader
19
+
20
+
21
+ def _normalize_item(raw: dict) -> dict:
22
+ """
23
+ Normalise one raw entry into the dict shape SkillOpt expects.
24
+
25
+ The only **hard** requirement is ``"id"`` (str). Add whatever extra
26
+ fields your :class:`TemplateBenchmarkEnv.rollout` needs.
27
+ """
28
+ return {
29
+ "id": str(raw.get("uid") or raw.get("id") or ""),
30
+ "question": str(raw.get("question") or raw.get("prompt") or ""),
31
+ "ground_truth": str(raw.get("ground_truth") or raw.get("answer") or ""),
32
+ "task_type": str(raw.get("category") or raw.get("task_type") or "template"),
33
+ # ── add benchmark-specific keys here ──
34
+ }
35
+
36
+
37
+ class TemplateBenchmarkLoader(SplitDataLoader):
38
+ """
39
+ Data loader for <Your Benchmark Name>.
40
+
41
+ Subclass note: you usually only need to implement
42
+ :meth:`load_split_items`. The base class drives ``setup(cfg)``,
43
+ materialises ratio-mode splits, exposes ``train_items``,
44
+ ``val_items``, ``test_items``, and builds ``BatchSpec`` objects on
45
+ demand.
46
+
47
+ If you want to support ``split_mode="ratio"`` (auto-split a single
48
+ file into train/val/test), also implement
49
+ :meth:`load_raw_items(data_path)` returning the full list of items.
50
+ """
51
+
52
+ def load_split_items(self, split_path: str) -> list[dict]:
53
+ """Load all items for one split directory.
54
+
55
+ ``split_path`` is e.g. ``data/your_benchmark/train/``. Return a
56
+ list of dicts, each shaped like :func:`_normalize_item`'s output.
57
+ """
58
+ path = Path(split_path)
59
+
60
+ json_files = sorted(path.glob("*.json"))
61
+ if json_files:
62
+ with json_files[0].open(encoding="utf-8") as f:
63
+ payload = json.load(f)
64
+ if not isinstance(payload, list):
65
+ raise ValueError(
66
+ f"Expected JSON array at top level of {json_files[0]}"
67
+ )
68
+ return [_normalize_item(row) for row in payload]
69
+
70
+ jsonl_files = sorted(path.glob("*.jsonl"))
71
+ if jsonl_files:
72
+ items: list[dict] = []
73
+ with jsonl_files[0].open(encoding="utf-8") as f:
74
+ for line in f:
75
+ line = line.strip()
76
+ if not line:
77
+ continue
78
+ items.append(_normalize_item(json.loads(line)))
79
+ return items
80
+
81
+ raise FileNotFoundError(
82
+ f"No .json or .jsonl file found in {split_path}"
83
+ )
84
+
85
+ # Optional — only needed if you intend to use ``split_mode='ratio'``.
86
+ # def load_raw_items(self, data_path: str) -> list[dict]:
87
+ # ...
@@ -0,0 +1,5 @@
1
+ """ALFWorld environment adapter for ReflACT."""
2
+
3
+ from skillopt.envs.alfworld.adapter import ALFWorldAdapter
4
+
5
+ __all__ = ["ALFWorldAdapter"]