(args: argparse.Namespace)
| 677 | |
| 678 | |
| 679 | def run_profile(args: argparse.Namespace) -> dict: |
| 680 | import os |
| 681 | |
| 682 | os.environ["DB_PATH"] = args.db |
| 683 | from explainshell.store import Store |
| 684 | from explainshell.web.views import explain_cmd |
| 685 | |
| 686 | store = Store(args.db) |
| 687 | |
| 688 | rng = random.Random(args.seed) |
| 689 | cmds = [gen_bot_cmd(rng) for _ in range(args.n)] |
| 690 | distro_preference = [("ubuntu", "26.04"), ("arch", "rolling")] |
| 691 | |
| 692 | for c in cmds[:3]: |
| 693 | try: |
| 694 | explain_cmd(c, store, distro_preference=distro_preference) |
| 695 | except Exception as e: |
| 696 | print(f"warmup error: {type(e).__name__}: {e}") |
| 697 | |
| 698 | pr = cProfile.Profile() |
| 699 | per_call: list[float] = [] |
| 700 | errors = 0 |
| 701 | pr.enable() |
| 702 | for c in cmds: |
| 703 | t0 = time.perf_counter() |
| 704 | try: |
| 705 | explain_cmd(c, store, distro_preference=distro_preference) |
| 706 | per_call.append((time.perf_counter() - t0) * 1000.0) |
| 707 | except Exception: |
| 708 | errors += 1 |
| 709 | pr.disable() |
| 710 | |
| 711 | st = pcts(per_call) |
| 712 | print(f"explain_cmd calls: n={len(per_call)} errors={errors}") |
| 713 | if st: |
| 714 | print( |
| 715 | f"wall ms: p50={st['p50']:.1f} p95={st['p95']:.1f} " |
| 716 | f"p99={st['p99']:.1f} max={st['max']:.1f} mean={st['mean']:.1f}" |
| 717 | ) |
| 718 | |
| 719 | s = io.StringIO() |
| 720 | pstats.Stats(pr, stream=s).sort_stats("cumulative").print_stats(40) |
| 721 | print("\n=== cProfile top (cumulative) ===\n") |
| 722 | print(s.getvalue()) |
| 723 | |
| 724 | s = io.StringIO() |
| 725 | pstats.Stats(pr, stream=s).sort_stats("tottime").print_stats(30) |
| 726 | print("\n=== cProfile top (self time) ===\n") |
| 727 | print(s.getvalue()) |
| 728 | |
| 729 | return {"n": len(per_call), "errors": errors, "latency_ms": st} |
| 730 | |
| 731 | |
| 732 | # --- CLI -------------------------------------------------------------------- |
no test coverage detected