nabla-cli 0.5.0__tar.gz → 0.5.2__tar.gz
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.
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/PKG-INFO +1 -1
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/__init__.py +1 -1
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/cli.py +46 -19
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/ui.py +15 -3
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla_cli.egg-info/PKG-INFO +1 -1
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/pyproject.toml +1 -1
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/README.md +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/__main__.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/branding.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/config.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/contract.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/induce.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/profile.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/prompt_recon.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/recorder.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/samplegen.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/scanner.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/schema_resolver.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/schemas/site_profile.schema.json +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla/term.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla_cli.egg-info/SOURCES.txt +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla_cli.egg-info/dependency_links.txt +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla_cli.egg-info/entry_points.txt +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla_cli.egg-info/requires.txt +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/nabla_cli.egg-info/top_level.txt +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/setup.cfg +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_cli_ux.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_config.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_e2e_profile.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_induce.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_prompt_recon.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_recorder.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_samplegen.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_scanner.py +0 -0
- {nabla_cli-0.5.0 → nabla_cli-0.5.2}/tests/test_schema_resolver.py +0 -0
|
@@ -488,10 +488,9 @@ def _cmd_record(args) -> int:
|
|
|
488
488
|
rail(_out, f"using {conventional} (found by convention; pass --inputs to override)")
|
|
489
489
|
source = RecordSource(kind="samples", samples_file=str(conventional))
|
|
490
490
|
else:
|
|
491
|
-
source, err =
|
|
491
|
+
source, source_kind, err = _resolve_inputs_interactively(args, site)
|
|
492
492
|
if err is not None:
|
|
493
493
|
return err
|
|
494
|
-
source_kind = "generated_samples"
|
|
495
494
|
|
|
496
495
|
on_progress = None
|
|
497
496
|
progress = None
|
|
@@ -538,26 +537,54 @@ def _cmd_record(args) -> int:
|
|
|
538
537
|
return 0
|
|
539
538
|
|
|
540
539
|
|
|
541
|
-
def
|
|
542
|
-
"""No
|
|
543
|
-
inputs
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
from .
|
|
547
|
-
from .samplegen import SampleGenError, generate_samples
|
|
540
|
+
def _resolve_inputs_interactively(args, site):
|
|
541
|
+
"""No --inputs given and no conventional file found. Interactively, ask
|
|
542
|
+
where inputs come from (generate N / custom count / own file); otherwise
|
|
543
|
+
generate the default quietly. Returns (source, source_kind, exit_code)
|
|
544
|
+
with exit_code None on success."""
|
|
545
|
+
from .ui import prompt_text, select
|
|
548
546
|
|
|
549
547
|
n = args.num_samples
|
|
550
|
-
if n is None:
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
548
|
+
if n is None and _out.is_terminal and sys.stdin.isatty():
|
|
549
|
+
options = [
|
|
550
|
+
("generate 5", "synthetic inputs — quick look, fewest credits"),
|
|
551
|
+
("generate 10", "synthetic inputs — balanced"),
|
|
552
|
+
("generate 20", "synthetic inputs — handoff floor, most credits"),
|
|
553
|
+
("custom count", "type how many synthetic inputs to generate"),
|
|
554
|
+
("my own file", "type a path to your JSONL of inputs"),
|
|
555
|
+
]
|
|
556
|
+
choice = select(_out, "Inputs", options)
|
|
557
|
+
if choice == 3:
|
|
558
|
+
while True:
|
|
559
|
+
typed = prompt_text(_out, "How many", default="5")
|
|
560
|
+
if typed.isdigit() and int(typed) > 0:
|
|
561
|
+
n = int(typed)
|
|
562
|
+
break
|
|
563
|
+
_warn("enter a positive number")
|
|
564
|
+
elif choice == 4:
|
|
565
|
+
while True:
|
|
566
|
+
typed = prompt_text(_out, "Path to JSONL")
|
|
567
|
+
if typed and Path(typed).exists():
|
|
568
|
+
return RecordSource(kind="samples", samples_file=typed), None, None
|
|
569
|
+
_warn(f"{typed or '(empty)'} not found — try again, or Ctrl+C to abort")
|
|
559
570
|
else:
|
|
560
|
-
n = 5
|
|
571
|
+
n = (5, 10, 20)[choice]
|
|
572
|
+
elif n is None:
|
|
573
|
+
n = 5
|
|
574
|
+
|
|
575
|
+
source, err = _generate_samples_source(args, site, Path(f"{site.symbol}.inputs.jsonl"), n)
|
|
576
|
+
if err is not None:
|
|
577
|
+
return None, None, err
|
|
578
|
+
return source, "generated_samples", None
|
|
579
|
+
|
|
580
|
+
|
|
581
|
+
def _generate_samples_source(args, site, out_path: Path, n: int):
|
|
582
|
+
"""Generate synthetic inputs with the configured provider, persist them
|
|
583
|
+
for inspection, and record through them. Returns (RecordSource, None)
|
|
584
|
+
or (None, exit_code)."""
|
|
585
|
+
from .induce import InduceError
|
|
586
|
+
from .prompt_recon import reconstruct
|
|
587
|
+
from .samplegen import SampleGenError, generate_samples
|
|
561
588
|
|
|
562
589
|
template = reconstruct(site, args.repo)
|
|
563
590
|
schema, _ = resolve_schema(site, args.repo)
|
|
@@ -23,8 +23,8 @@ from rich.text import Text
|
|
|
23
23
|
|
|
24
24
|
RAIL = "│"
|
|
25
25
|
_POINTER = "❯"
|
|
26
|
-
_ON = "
|
|
27
|
-
_OFF = "
|
|
26
|
+
_ON = "[∇]" # selected: the brand mark, filled in
|
|
27
|
+
_OFF = "[ ]"
|
|
28
28
|
|
|
29
29
|
|
|
30
30
|
# ---------------------------------------------------------------------------
|
|
@@ -111,7 +111,7 @@ def select(console: Console, label: str, options: list[tuple[str, str]],
|
|
|
111
111
|
row.append(f"{name:<{name_width}}", style="bold cyan")
|
|
112
112
|
else:
|
|
113
113
|
# Unselected is quieter, never grey — grey reads as disabled.
|
|
114
|
-
row.append(f" {_OFF} ", style="
|
|
114
|
+
row.append(f" {_OFF} ", style="")
|
|
115
115
|
row.append(f"{name:<{name_width}}")
|
|
116
116
|
row.append(f" {desc}", style="dim")
|
|
117
117
|
console.print(row)
|
|
@@ -141,6 +141,18 @@ def select(console: Console, label: str, options: list[tuple[str, str]],
|
|
|
141
141
|
return idx
|
|
142
142
|
|
|
143
143
|
|
|
144
|
+
def prompt_text(console: Console, label: str, default: str = "") -> str:
|
|
145
|
+
"""Typed input on the rail: styled label, plain typing, default on enter."""
|
|
146
|
+
prompt = Text(f"{RAIL} ", style="dim")
|
|
147
|
+
prompt.append(label, style="bold")
|
|
148
|
+
if default:
|
|
149
|
+
prompt.append(f" [{default}]", style="dim")
|
|
150
|
+
prompt.append(" ")
|
|
151
|
+
console.print(prompt, end="")
|
|
152
|
+
value = input().strip()
|
|
153
|
+
return value or default
|
|
154
|
+
|
|
155
|
+
|
|
144
156
|
# ---------------------------------------------------------------------------
|
|
145
157
|
# Progress
|
|
146
158
|
# ---------------------------------------------------------------------------
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|