Coverage for / home / jenkins / .local / lib / python3.10 / site-packages / hyper_parallel / codegen / cli.py: 96%
47 statements
« prev ^ index » next coverage.py v7.13.1, created at 2026-11-15 07:18 +0800
« prev ^ index » next coverage.py v7.13.1, created at 2026-11-15 07:18 +0800
1# Copyright 2026 Huawei Technologies Co., Ltd
2#
3# Licensed under the Apache License, Version 2.0 (the "License");
4# you may not use this file except in compliance with the License.
5# You may obtain a copy of the License at
6#
7# http://www.apache.org/licenses/LICENSE-2.0
8#
9# Unless required by applicable law or agreed to in writing, software
10# distributed under the License is distributed on an "AS IS" BASIS,
11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12# See the License for the specific language governing permissions and
13# limitations under the License.
14# ============================================================================
15"""Thin command-line interface for native-build codegen workflows."""
17from __future__ import annotations
19import argparse
20import logging
21import os
22import sys
23from typing import Optional
25from hyper_parallel.codegen.build import generate_from_native_build
26from hyper_parallel.trainer.config import parser as config_parser
28logger = logging.getLogger(__name__)
31def main(argv: Optional[list[str]] = None) -> int:
32 """Run the CLI and return its process exit code."""
33 parser = _build_parser()
34 args, config_overrides = parser.parse_known_args(argv)
35 setattr(args, "_config_overrides", config_overrides)
36 if not getattr(args, "command", None):
37 parser.print_usage(sys.stderr)
38 return 2
39 _configure_logging(getattr(args, "verbose", False))
40 try:
41 return args.func(args)
42 except Exception as exc: # A CLI reports failures without a traceback by default.
43 if getattr(args, "verbose", False):
44 logger.exception("codegen: %s", exc)
45 else:
46 logger.error("codegen: %s", exc)
47 return 1
50def cmd_generate(args: argparse.Namespace) -> int:
51 """Observe a meta model and generate a fresh bundle."""
52 if int(os.environ.get("WORLD_SIZE", "1")) > 1:
53 raise RuntimeError(
54 "codegen generate is a single-process CPU/meta command; "
55 "run it with python instead of torchrun"
56 )
57 config = _load_config(args.config, _cli_overrides(args))
58 layout = generate_from_native_build(config, artifact_dir=args.output)
59 logger.info("codegen: artifact %s", layout.artifact_dir)
60 return 0
63def _load_config(yaml_path: str, overrides: Optional[list[str]] = None):
64 """Load a resolved TrainerConfig without building trainer runtime components."""
65 return config_parser.load_training_config(yaml_path, overrides or [])
68def _cli_overrides(args: argparse.Namespace) -> list[str]:
69 """Return typed config overrides left after argparse processing."""
70 return list(getattr(args, "_config_overrides", None) or [])
73def _configure_logging(verbose: bool) -> None:
74 logging.basicConfig(
75 level=logging.INFO if verbose else logging.WARNING,
76 format="%(levelname)s:%(name)s:%(message)s",
77 )
80def _build_parser() -> argparse.ArgumentParser:
81 """Build the codegen command-line parser."""
82 parser = argparse.ArgumentParser(
83 prog="hyper_parallel.codegen",
84 description="Generate a model bundle from a training YAML.",
85 )
86 parser.add_argument("--verbose", action="store_true", help="verbose logging")
87 subparsers = parser.add_subparsers(dest="command")
89 generate = subparsers.add_parser(
90 "generate",
91 help="observe the model on meta and generate its bundle",
92 )
93 generate.add_argument("--config", required=True, help="path to the training YAML")
94 generate.add_argument("--output", help="explicit artifact output directory")
95 generate.set_defaults(func=cmd_generate)
97 return parser
100__all__ = ["cmd_generate", "main"]