Skip to content

Commit e658633

Browse files
authored
feat: CWL Executor and hint design for input data (#94)
* feat: dirac executor on top of cwltool
1 parent 734ac71 commit e658633

20 files changed

Lines changed: 4515 additions & 903 deletions

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -176,3 +176,6 @@ generated_schemas/*
176176
!test/workflows/test_meta/schemas/dirac-metadata.json
177177

178178
.DS_Store
179+
180+
*.sim
181+
task.cwl
Lines changed: 189 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,189 @@
1+
# Production Plugin System Design
2+
3+
## Overview
4+
5+
This document describes the design for a pluggable Production configuration system that makes the CWL executor (`__main__.py`) completely generic by extracting experiment-specific code (e.g., LHCb Bookkeeping integration) into plugins.
6+
7+
## Three-Level CWL Submission Model
8+
9+
```mermaid
10+
flowchart TB
11+
subgraph "Level A: Production"
12+
P[dirac:Production hint]
13+
P --> IDP[Input Dataset Plugin]
14+
P --> |future| OC[Output Config]
15+
P --> |future| TD[Transformation Defaults]
16+
end
17+
18+
subgraph "Level B: Transformation"
19+
T[dirac:Transformation hint]
20+
T --> TT[Transformation Type]
21+
T --> GS[Group Size]
22+
T --> TP[Plugin/Priority]
23+
end
24+
25+
subgraph "Level C: Job"
26+
S[dirac:Scheduling hint]
27+
S --> Platform
28+
S --> Sites
29+
30+
EH[dirac:ExecutionHooks hint]
31+
EH --> PreProcess
32+
EH --> PostProcess
33+
EH --> OutputStorage
34+
end
35+
36+
P -.->|"configures input for"| T
37+
T -.->|"creates many"| J[Jobs]
38+
S -.->|"configures"| J
39+
EH -.->|"hooks into"| J
40+
```
41+
42+
| Level | DIRAC Concept | CWL Scope | Hint |
43+
|-------|---------------|-----------|------|
44+
| **(a) Production** | Production/Request | Orchestrates transformations, configures input data | `dirac:Production` |
45+
| **(b) Transformation** | Transformation | Job template - defines steps that run in each job | `dirac:Transformation` |
46+
| **(c) Job** | Job | Single execution with specific inputs | `dirac:Scheduling`, `dirac:ExecutionHooks` |
47+
48+
**Key insight:** A Transformation workflow is a **job template**. DIRAC creates many jobs from it, each with different input files.
49+
50+
## Plugin Architecture
51+
52+
```mermaid
53+
classDiagram
54+
class ProductionHint {
55+
+str input_dataset_plugin
56+
+dict input_dataset_config
57+
+from_cwl(cwl_content) ProductionHint
58+
+to_runtime() InputDatasetPluginBase
59+
}
60+
61+
class InputDatasetPluginBase {
62+
<<abstract>>
63+
+ClassVar[str] vo
64+
+ClassVar[str] version
65+
+ClassVar[str] description
66+
+generate_inputs(workflow_path, config, ...) tuple[Path, Path]
67+
+format_hint_display(config) list[tuple]
68+
}
69+
70+
class NoOpInputDatasetPlugin {
71+
+generate_inputs() tuple[None, None]
72+
}
73+
74+
class LHCbBookkeepingPlugin {
75+
+ClassVar[str] vo = "lhcb"
76+
+generate_inputs() tuple[Path, Path]
77+
+format_hint_display() list[tuple]
78+
}
79+
80+
class InputDatasetPluginRegistry {
81+
-dict _plugins
82+
+register_plugin(plugin_class)
83+
+discover_plugins() int
84+
+get_plugin(name) type
85+
+instantiate_plugin(hint) InputDatasetPluginBase
86+
}
87+
88+
InputDatasetPluginBase <|-- NoOpInputDatasetPlugin
89+
InputDatasetPluginBase <|-- LHCbBookkeepingPlugin
90+
ProductionHint --> InputDatasetPluginRegistry : uses
91+
InputDatasetPluginRegistry --> InputDatasetPluginBase : manages
92+
```
93+
94+
## CWL Hint Formats
95+
96+
### New Format: `dirac:Production`
97+
98+
```yaml
99+
cwlVersion: v1.2
100+
class: Workflow
101+
102+
hints:
103+
- class: dirac:Production
104+
input_dataset_plugin: "LHCbBookkeepingPlugin"
105+
input_dataset_config:
106+
event_type: "27165175"
107+
conditions_description: "Beam6800GeV-VeloClosed-MagUp-Excl-UT"
108+
conditions_dict:
109+
configName: "Collision24"
110+
configVersion: "Beam6800GeV-VeloClosed-MagUp-Excl-UT"
111+
inFileType: "BRUNELHLT2.DST"
112+
inProPass: "Sprucing24c5/DaVinciRestripping25r0"
113+
```
114+
115+
## Data Flow
116+
117+
```mermaid
118+
sequenceDiagram
119+
participant User
120+
participant CLI as __main__.py
121+
participant Registry as PluginRegistry
122+
participant Plugin as InputDatasetPlugin
123+
participant External as External System<br/>(e.g., LHCb Bookkeeping)
124+
participant CWLTool
125+
126+
User->>CLI: dirac-cwl-run workflow.cwl
127+
CLI->>CLI: Parse CWL, extract hints
128+
CLI->>Registry: find_applicable_plugin(cwl_content)
129+
Registry->>Registry: Check dirac:Production
130+
Registry-->>CLI: LHCbBookkeepingPlugin instance
131+
132+
CLI->>Plugin: generate_inputs(workflow_path, config, ...)
133+
Plugin->>External: Query for LFNs
134+
External-->>Plugin: LFN list
135+
Plugin->>External: Resolve replicas
136+
External-->>Plugin: Replica catalog data
137+
Plugin->>Plugin: Write inputs.yml
138+
Plugin->>Plugin: Write catalog.json
139+
Plugin-->>CLI: (inputs_path, catalog_path)
140+
141+
Plugin-->>CLI: ["CMAKE_PREFIX_PATH", ...]
142+
143+
CLI->>CWLTool: Execute with inputs + catalog
144+
CWLTool-->>CLI: Results
145+
CLI-->>User: Output
146+
```
147+
148+
## File Structure
149+
150+
```
151+
dirac-cwl/src/dirac_cwl/
152+
├── production/
153+
│ ├── __init__.py # Package init + auto-discovery
154+
│ ├── core.py # ProductionHint + InputDatasetPluginBase
155+
│ ├── registry.py # InputDatasetPluginRegistry
156+
│ └── plugins/
157+
│ ├── __init__.py # Plugin exports
158+
│ ├── core.py # NoOpInputDatasetPlugin
159+
│ └── lhcb.py # LHCbBookkeepingPlugin (temporary)
160+
├── job/
161+
│ └── executor/
162+
│ └── __main__.py # Modified to use plugin system
163+
└── ...
164+
```
165+
166+
## Entry Points Configuration
167+
168+
In `pyproject.toml`:
169+
170+
```toml
171+
[project.entry-points."dirac_cwl.input_dataset_plugins"]
172+
NoOpInputDatasetPlugin = "dirac_cwl.production.plugins:NoOpInputDatasetPlugin"
173+
LHCbBookkeepingPlugin = "dirac_cwl.production.plugins.lhcb:LHCbBookkeepingPlugin"
174+
```
175+
176+
**Done so far (DIRACGrid/dirac-cwl#94):**
177+
- `dirac:Production` hint with `input_dataset_plugin` for querying external catalogs
178+
- Plugin generates `inputs.yml` + `catalog.json` for local CWL execution
179+
180+
**Future work (CWL submission tools):**
181+
The following will be **configured via CWL hints** when we build the submission CLI, but are **executed by DIRAC agents** at runtime:
182+
183+
| Feature | CWL Hint | DIRAC Agent | Notes |
184+
|---------|----------|-------------|-------|
185+
| Transformation grouping | `dirac:Transformation` (plugin, groupSize) | TransformationAgent | Groups files into tasks |
186+
| Input Meta Queries | `dirac:Transformation` (inputQuery) | InputDataAgent | Finds input files from upstream |
187+
| Output registration | `dirac:ExecutionHooks` or similar | Job wrapper | Registers outputs to catalog |
188+
189+
The hints define **what** should happen; DIRAC agents execute **when** and **how**.

0 commit comments

Comments
 (0)