27def _add_run_parser(subparsers):
28 """!
29 @brief Attach `run` parser with staged execution and dry-run support.
30 @param[in] subparsers Argument passed to `_add_run_parser()`.
31 @return Value returned by `_add_run_parser()`.
32 """
33 p_run = subparsers.add_parser(
34 "run",
35 help="Execute a simulation workflow (solve and/or post-process).",
36 formatter_class=argparse.RawTextHelpFormatter,
37 description=(
38 "Execute solver and/or post-processing stages.\n\n"
39 "Notes:\n"
40 " - --num-procs applies to solver and post-processing stage launches.\n"
41 " - With --solve, --continue resumes the existing run directory in-place.\n"
42 " - With --post-process, --continue resumes the same recipe from the first unfinished step\n"
43 " and caps the launch to the highest fully available contiguous source frontier.\n\n"
44 "Diagnostics:\n"
45 " - PETSc and runtime memory diagnostics live under monitor.yml -> diagnostics.\n"
46 " - Use --dry-run to inspect resolved PETSc flags and expected log destinations.\n\n"
47 "Examples:\n"
48 " picurv run --solve -n 8 --case case.yml --solver solver.yml --monitor monitor.yml\n"
49 " picurv run --solve --restart-from runs/old_run --case case.yml --solver solver.yml --monitor monitor.yml\n"
50 " picurv run --solve --continue --run-dir runs/my_run --case case.yml --solver solver.yml --monitor monitor.yml\n"
51 " picurv run --post-process --run-dir runs/my_run --post post.yml\n"
52 " picurv run --post-process --continue --run-dir runs/my_run --post post.yml\n"
53 " picurv run --solve --case case.yml --solver solver.yml --monitor monitor.yml --dry-run"
54 ),
55 epilog="Next: run `picurv validate ...` first for config-only checks.",
56 )
57 run_group = p_run.add_argument_group("stages")
58 run_group.add_argument("--solve", action="store_true", help="Execute the solver stage (creates a new run directory).")
59 run_group.add_argument("--post-process", action="store_true", help="Execute the post-processing stage on a run directory.")
60
61 solver_group = p_run.add_argument_group("solver inputs (required for --solve)")
62 solver_group.add_argument("--case", help="Path to the case definition file (e.g., case.yml).")
63 solver_group.add_argument("--solver", help="Path to the solver settings profile (e.g., solver.yml).")
64 solver_group.add_argument("--monitor", help="Path to the monitoring, diagnostics, and I/O profile (e.g., monitor.yml).")
65 solver_group.add_argument(
66 "--restart-from", "--from",
67 dest="restart_from",
68 help="Path to an existing run directory to restart from.\n"
69 "Use 'latest' to select the newest compatible local workspace run.",
70 )
71 solver_group.add_argument(
72 "--statistics-state",
73 choices=RESTART_STATISTICS_MODES,
74 default=None,
75 help="For a branched restart with field statistics enabled, this is required:\n"
76 "'reset' discards the parent's accumulated windows, 'carry' resumes compatible\n"
77 "saved window state. Ignored when field statistics are disabled.",
78 )
79 solver_group.add_argument(
80 "--require-precomputed",
81 action="store_true",
82 help="Refuse to build missing or stale deterministic assets while staging the run.",
83 )
84 solver_group.add_argument(
85 "--fetch-missing",
86 action="store_true",
87 help="Try the configured storage profile before rebuilding a missing workspace asset.",
88 )
89 run_group.add_argument(
90 "--continue",
91 action="store_true",
92 dest="continue_run",
93 help="Resume an existing run directory in-place. Requires --run-dir.\n"
94 "With --solve, requires start_step > 0 and appends to existing solver output/logs.\n"
95 "With --post-process, resumes the same recipe from the first unfinished step\n"
96 "and skips already-complete work inside the current live source frontier.",
97 )
98
99 post_group = p_run.add_argument_group("post-processor inputs (required for --post-process)")
100 post_group.add_argument("--run-dir", help="Path to an existing run directory.\n(Used with --post-process or --continue).")
101 post_group.add_argument("--post", help="Path to the post-processing recipe file (e.g., post.yml).")
102 post_group.add_argument(
103 "--only",
104 help="Comma-separated post stages to run: 'fields' (the field post-processor)\n"
105 "and/or 'spectra'. Defaults to every stage.\n"
106 "Use --only spectra to re-measure spectra without rebuilding field output.",
107 )
108
109 p_run.add_argument(
110 "-n",
111 "--num-procs",
112 type=int,
113 default=1,
114 help="Number of MPI processes for solver and post-processing stages.",
115 )
116 p_run.add_argument("--cluster", help="Path to cluster.yml for Slurm execution mode.")
117 p_run.add_argument("--scheduler", help="Explicit scheduler selector (currently 'slurm').")
118 p_run.add_argument("--no-submit", action="store_true", help="Stage run artifacts without starting local execution or Slurm submission.")
119 p_run.add_argument(
120 "--dry-run",
121 action="store_true",
122 help="Resolve and print planned commands/artifacts, including diagnostic flags and log paths, without writing files.",
123 )
124 p_run.add_argument(
125 "--format",
126 dest="output_format",
127 choices=
list(CLI_OUTPUT_FORMATS),
128 default="text",
129 help="Output format for --dry-run (default: text).",
130 )
131 return p_run
132
133
Head of a generic C-style linked list.