cjm-transcript-decomp-core 0.0.1__tar.gz → 0.0.4__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.
- {cjm_transcript_decomp_core-0.0.1/cjm_transcript_decomp_core.egg-info → cjm_transcript_decomp_core-0.0.4}/PKG-INFO +9 -49
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/README.md +5 -45
- cjm_transcript_decomp_core-0.0.4/cjm_transcript_decomp_core/__init__.py +1 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core/cli.py +60 -18
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core/models.py +9 -2
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core/pipeline.py +32 -4
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4/cjm_transcript_decomp_core.egg-info}/PKG-INFO +9 -49
- cjm_transcript_decomp_core-0.0.4/cjm_transcript_decomp_core.egg-info/entry_points.txt +5 -0
- cjm_transcript_decomp_core-0.0.4/cjm_transcript_decomp_core.egg-info/requires.txt +5 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/pyproject.toml +4 -1
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/tests/test_cli.py +14 -1
- cjm_transcript_decomp_core-0.0.1/cjm_transcript_decomp_core/__init__.py +0 -1
- cjm_transcript_decomp_core-0.0.1/cjm_transcript_decomp_core.egg-info/entry_points.txt +0 -2
- cjm_transcript_decomp_core-0.0.1/cjm_transcript_decomp_core.egg-info/requires.txt +0 -5
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/LICENSE +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/MANIFEST.in +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core/alignment.py +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core/graph.py +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core.egg-info/SOURCES.txt +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core.egg-info/dependency_links.txt +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/cjm_transcript_decomp_core.egg-info/top_level.txt +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/setup.cfg +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/tests/test_alignment.py +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/tests/test_graph.py +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/tests/test_models.py +0 -0
- {cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/tests/test_pipeline.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: cjm-transcript-decomp-core
|
|
3
|
-
Version: 0.0.
|
|
3
|
+
Version: 0.0.4
|
|
4
4
|
Summary: A frontend-agnostic core for the transcript decomposition workflow — composes isolated capability workers (forced alignment, VAD, graph storage) into a headless pipeline that decomposes transcription run manifests into a VAD-aligned context-graph spine with traceable provenance, and a CLI as its first driver.
|
|
5
5
|
Author-email: "Christian J. Mills" <9126128+cj-mills@users.noreply.github.com>
|
|
6
6
|
License: Apache-2.0
|
|
@@ -10,10 +10,10 @@ Classifier: Programming Language :: Python :: 3 :: Only
|
|
|
10
10
|
Requires-Python: >=3.12
|
|
11
11
|
Description-Content-Type: text/markdown
|
|
12
12
|
License-File: LICENSE
|
|
13
|
-
Requires-Dist: cjm_substrate>=0.0.
|
|
14
|
-
Requires-Dist: cjm_context_graph_primitives>=0.0.
|
|
13
|
+
Requires-Dist: cjm_substrate>=0.0.57
|
|
14
|
+
Requires-Dist: cjm_context_graph_primitives>=0.0.15
|
|
15
15
|
Requires-Dist: cjm_capability_primitives>=0.0.10
|
|
16
|
-
Requires-Dist: cjm-context-graph-layer>=0.0.
|
|
16
|
+
Requires-Dist: cjm-context-graph-layer>=0.0.11
|
|
17
17
|
Requires-Dist: cjm-transcript-graph-schema>=0.0.7
|
|
18
18
|
Dynamic: license-file
|
|
19
19
|
|
|
@@ -26,15 +26,10 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
26
26
|
## Modules
|
|
27
27
|
|
|
28
28
|
- **`cjm_transcript_decomp_core.alignment`** — Pure forced-alignment logic (no capability calls): map FA words back to character spans in the original text, assign words to VAD chunks by timestamp, and build one text segment per VAD chunk. Extracted from the page-centric ForcedAlignmentService (Tier-1 logic).
|
|
29
|
-
- **`cjm_transcript_decomp_core.cli`** — The CLI driver — the decomposition core's first (and currently only) frontend.
|
|
29
|
+
- **`cjm_transcript_decomp_core.cli`** — The CLI driver — the decomposition core's first (and currently only) frontend.
|
|
30
30
|
- **`cjm_transcript_decomp_core.graph`** — Graph-spine EXTENSION + skeptical-lens verification (stage 5, CR-18 revolution 2). Decomp no longer creates a Document: it RECOMPUTES the transcription-emitted root's deterministic node ids from the consumed manifest (no search), verifies the root exists, and attaches the fine Segment spine under the existing AudioSegment nodes — PART_OF to the owning rendition, STARTS_WITH per rendition (the coarse-seam jump anchor), source-wide NEXT. Each Segment carries the audio TimeSlice ref plus per-transcriber CharSlice refs into the Transcript nodes (the D4/P10 framing, finally expressible). Commit goes through the layer's idempotent extend_graph.
|
|
31
31
|
- **`cjm_transcript_decomp_core.models`** — Lean data shapes for the transcript-decomposition pipeline: in-core mirrors of the forced-alignment / VAD / text DTOs (no FastHTML deps), run configuration, the committed graph-segment carrier, and the decomposition run manifest (proto-bundle).
|
|
32
32
|
- **`cjm_transcript_decomp_core.pipeline`** — The headless decomposition pipeline (stage 5: decomp is an EXTENDER). Load a transcription run manifest, verify the transcription-emitted graph root exists (the graph begins at transcription), then per source per pipeline-segment run VAD + per-transcriber forced alignment, build one aligned segment per VAD chunk with per-transcriber text variants, and attach the fine spine under the existing AudioSegment nodes via the layer's idempotent extend_graph — with HITL approval seams between alignment, commit, and the next source.
|
|
33
|
-
- **`tests.test_alignment`** — Tests for cjm_transcript_decomp_core.alignment — pure forced-alignment logic.
|
|
34
|
-
- **`tests.test_graph`** — Tests for cjm_transcript_decomp_core.graph — fine-spine extension payload.
|
|
35
|
-
- **`tests.test_models`** — Tests for cjm_transcript_decomp_core.models — decomposition data shapes.
|
|
36
|
-
- **`tests_manual.measure_cold_fanout_overlap_e2e`** — Cold-run M×(VAD ∥ T×FA) fan-out overlap measurement (stage-5 closeout;
|
|
37
|
-
- **`tests_manual.validate_stage7_volume_journal_e2e`** — Stage-7 stress part 6 — volume regression on the REAL corpus.
|
|
38
33
|
|
|
39
34
|
## API
|
|
40
35
|
|
|
@@ -50,7 +45,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
50
45
|
- `build_parser` _function_ — Build the CLI parser (subcommands: run).
|
|
51
46
|
- `load_capabilities` _function_ — Discover manifests + load each requested capability (default instance).
|
|
52
47
|
- `main` _function_ — CLI entry point (console script: `cjm-transcript-decomp-core`).
|
|
53
|
-
- `run_command` _function_ — Execute the `run` subcommand: extend
|
|
48
|
+
- `run_command` _function_ — Execute the `run` subcommand: extend transcription-run manifest(s) with the fine spine.
|
|
54
49
|
|
|
55
50
|
### `cjm_transcript_decomp_core.graph`
|
|
56
51
|
|
|
@@ -76,6 +71,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
76
71
|
- `build_alignment_composition` _function_ — Build the whole-source M×(VAD ∥ T×FA) composition (D8 fan-in, stage-5 variants).
|
|
77
72
|
- `collect_capability_info` _function_ — Record capability identity + data-DB pointers for the run manifest (provenance).
|
|
78
73
|
- `confirm_seam` _function_ — HITL approval seam in its cheapest viable form (log + optional CLI prompt).
|
|
74
|
+
- `decomp_replay_handlers` _function_ — The decomp core's replay vocabulary (DEC 426658f1, replay stays DOMAIN-OWNED).
|
|
79
75
|
- `decompose_source` _function_ — Decompose one source into aligned fine segments with per-transcriber variants.
|
|
80
76
|
- `fa_words_from_result` _function_ — Normalize a typed forced-alignment result into FA words (pure; stage 3).
|
|
81
77
|
- `load_source_manifest` _function_ — Load + lightly validate a transcription-core run manifest.
|
|
@@ -83,43 +79,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
83
79
|
- `submit_and_wait` _function_ — Submit one capability job, wait for it, and return its result (raise on failure).
|
|
84
80
|
- `vad_chunks_from_result` _function_ — Normalize a typed VAD result into segment-local VAD chunks.
|
|
85
81
|
|
|
86
|
-
### `tests.test_alignment`
|
|
87
|
-
|
|
88
|
-
- `test_assign_words_to_chunks_by_timestamp` _function_
|
|
89
|
-
- `test_build_segments_per_chunk` _function_
|
|
90
|
-
- `test_empty_chunk_yields_empty_segment_warning` _function_
|
|
91
|
-
- `test_map_fa_words_to_text_spans` _function_
|
|
92
|
-
|
|
93
|
-
### `tests.test_graph`
|
|
94
|
-
|
|
95
|
-
- `test_edge_topology_spans_coarse_boundary` _function_
|
|
96
|
-
- `test_extension_payload_deterministic_ids` _function_
|
|
97
|
-
- `test_preprocessed_manifest_distinct_renditions_same_boundaries` _function_
|
|
98
|
-
- `test_provenance_refs_and_text_from` _function_
|
|
99
|
-
- `test_resolve_root_ids_recomputation` _function_
|
|
100
|
-
|
|
101
|
-
### `tests.test_models`
|
|
102
|
-
|
|
103
|
-
- `test_faword_from_wire_tolerates_extra_keys` _function_
|
|
104
|
-
- `test_manifest_save_round_trip` _function_
|
|
105
|
-
- `test_manifest_shape_and_run_id` _function_
|
|
106
|
-
- `test_stage5_segment_shape` _function_
|
|
107
|
-
- `test_vad_chunk_duration` _function_
|
|
108
|
-
|
|
109
|
-
### `tests_manual.measure_cold_fanout_overlap_e2e`
|
|
110
|
-
|
|
111
|
-
- `lane_intervals` _function_ — (start, end) UTC intervals for completed jobs of one instance.
|
|
112
|
-
- `main` _function_
|
|
113
|
-
- `merge` _function_ — Merge overlapping intervals so a side can't double-count itself.
|
|
114
|
-
- `overlap_seconds` _function_ — Total seconds where any interval of A overlaps any interval of B.
|
|
115
|
-
- `self_overlap_max` _function_ — Max simultaneously in-flight jobs within one lane + seconds at depth >= 2.
|
|
116
|
-
|
|
117
|
-
### `tests_manual.validate_stage7_volume_journal_e2e`
|
|
118
|
-
|
|
119
|
-
- `checkpoint_copy` _function_ — Checkpoint-then-copy (the stage-3 G3 backup discipline — never copy
|
|
120
|
-
- `journal_rows` _function_
|
|
121
|
-
- `main` _function_
|
|
122
|
-
|
|
123
82
|
## Dependencies
|
|
124
83
|
|
|
125
|
-
**Depends on:** `cjm-substrate`
|
|
84
|
+
**Depends on:** `cjm-capability-primitives`, `cjm-context-graph-layer`, `cjm-context-graph-primitives`, `cjm-substrate`, `cjm-transcript-graph-schema`
|
|
85
|
+
**Used by:** `cjm-transcript-decomp-tui`
|
|
@@ -7,15 +7,10 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
7
7
|
## Modules
|
|
8
8
|
|
|
9
9
|
- **`cjm_transcript_decomp_core.alignment`** — Pure forced-alignment logic (no capability calls): map FA words back to character spans in the original text, assign words to VAD chunks by timestamp, and build one text segment per VAD chunk. Extracted from the page-centric ForcedAlignmentService (Tier-1 logic).
|
|
10
|
-
- **`cjm_transcript_decomp_core.cli`** — The CLI driver — the decomposition core's first (and currently only) frontend.
|
|
10
|
+
- **`cjm_transcript_decomp_core.cli`** — The CLI driver — the decomposition core's first (and currently only) frontend.
|
|
11
11
|
- **`cjm_transcript_decomp_core.graph`** — Graph-spine EXTENSION + skeptical-lens verification (stage 5, CR-18 revolution 2). Decomp no longer creates a Document: it RECOMPUTES the transcription-emitted root's deterministic node ids from the consumed manifest (no search), verifies the root exists, and attaches the fine Segment spine under the existing AudioSegment nodes — PART_OF to the owning rendition, STARTS_WITH per rendition (the coarse-seam jump anchor), source-wide NEXT. Each Segment carries the audio TimeSlice ref plus per-transcriber CharSlice refs into the Transcript nodes (the D4/P10 framing, finally expressible). Commit goes through the layer's idempotent extend_graph.
|
|
12
12
|
- **`cjm_transcript_decomp_core.models`** — Lean data shapes for the transcript-decomposition pipeline: in-core mirrors of the forced-alignment / VAD / text DTOs (no FastHTML deps), run configuration, the committed graph-segment carrier, and the decomposition run manifest (proto-bundle).
|
|
13
13
|
- **`cjm_transcript_decomp_core.pipeline`** — The headless decomposition pipeline (stage 5: decomp is an EXTENDER). Load a transcription run manifest, verify the transcription-emitted graph root exists (the graph begins at transcription), then per source per pipeline-segment run VAD + per-transcriber forced alignment, build one aligned segment per VAD chunk with per-transcriber text variants, and attach the fine spine under the existing AudioSegment nodes via the layer's idempotent extend_graph — with HITL approval seams between alignment, commit, and the next source.
|
|
14
|
-
- **`tests.test_alignment`** — Tests for cjm_transcript_decomp_core.alignment — pure forced-alignment logic.
|
|
15
|
-
- **`tests.test_graph`** — Tests for cjm_transcript_decomp_core.graph — fine-spine extension payload.
|
|
16
|
-
- **`tests.test_models`** — Tests for cjm_transcript_decomp_core.models — decomposition data shapes.
|
|
17
|
-
- **`tests_manual.measure_cold_fanout_overlap_e2e`** — Cold-run M×(VAD ∥ T×FA) fan-out overlap measurement (stage-5 closeout;
|
|
18
|
-
- **`tests_manual.validate_stage7_volume_journal_e2e`** — Stage-7 stress part 6 — volume regression on the REAL corpus.
|
|
19
14
|
|
|
20
15
|
## API
|
|
21
16
|
|
|
@@ -31,7 +26,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
31
26
|
- `build_parser` _function_ — Build the CLI parser (subcommands: run).
|
|
32
27
|
- `load_capabilities` _function_ — Discover manifests + load each requested capability (default instance).
|
|
33
28
|
- `main` _function_ — CLI entry point (console script: `cjm-transcript-decomp-core`).
|
|
34
|
-
- `run_command` _function_ — Execute the `run` subcommand: extend
|
|
29
|
+
- `run_command` _function_ — Execute the `run` subcommand: extend transcription-run manifest(s) with the fine spine.
|
|
35
30
|
|
|
36
31
|
### `cjm_transcript_decomp_core.graph`
|
|
37
32
|
|
|
@@ -57,6 +52,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
57
52
|
- `build_alignment_composition` _function_ — Build the whole-source M×(VAD ∥ T×FA) composition (D8 fan-in, stage-5 variants).
|
|
58
53
|
- `collect_capability_info` _function_ — Record capability identity + data-DB pointers for the run manifest (provenance).
|
|
59
54
|
- `confirm_seam` _function_ — HITL approval seam in its cheapest viable form (log + optional CLI prompt).
|
|
55
|
+
- `decomp_replay_handlers` _function_ — The decomp core's replay vocabulary (DEC 426658f1, replay stays DOMAIN-OWNED).
|
|
60
56
|
- `decompose_source` _function_ — Decompose one source into aligned fine segments with per-transcriber variants.
|
|
61
57
|
- `fa_words_from_result` _function_ — Normalize a typed forced-alignment result into FA words (pure; stage 3).
|
|
62
58
|
- `load_source_manifest` _function_ — Load + lightly validate a transcription-core run manifest.
|
|
@@ -64,43 +60,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
64
60
|
- `submit_and_wait` _function_ — Submit one capability job, wait for it, and return its result (raise on failure).
|
|
65
61
|
- `vad_chunks_from_result` _function_ — Normalize a typed VAD result into segment-local VAD chunks.
|
|
66
62
|
|
|
67
|
-
### `tests.test_alignment`
|
|
68
|
-
|
|
69
|
-
- `test_assign_words_to_chunks_by_timestamp` _function_
|
|
70
|
-
- `test_build_segments_per_chunk` _function_
|
|
71
|
-
- `test_empty_chunk_yields_empty_segment_warning` _function_
|
|
72
|
-
- `test_map_fa_words_to_text_spans` _function_
|
|
73
|
-
|
|
74
|
-
### `tests.test_graph`
|
|
75
|
-
|
|
76
|
-
- `test_edge_topology_spans_coarse_boundary` _function_
|
|
77
|
-
- `test_extension_payload_deterministic_ids` _function_
|
|
78
|
-
- `test_preprocessed_manifest_distinct_renditions_same_boundaries` _function_
|
|
79
|
-
- `test_provenance_refs_and_text_from` _function_
|
|
80
|
-
- `test_resolve_root_ids_recomputation` _function_
|
|
81
|
-
|
|
82
|
-
### `tests.test_models`
|
|
83
|
-
|
|
84
|
-
- `test_faword_from_wire_tolerates_extra_keys` _function_
|
|
85
|
-
- `test_manifest_save_round_trip` _function_
|
|
86
|
-
- `test_manifest_shape_and_run_id` _function_
|
|
87
|
-
- `test_stage5_segment_shape` _function_
|
|
88
|
-
- `test_vad_chunk_duration` _function_
|
|
89
|
-
|
|
90
|
-
### `tests_manual.measure_cold_fanout_overlap_e2e`
|
|
91
|
-
|
|
92
|
-
- `lane_intervals` _function_ — (start, end) UTC intervals for completed jobs of one instance.
|
|
93
|
-
- `main` _function_
|
|
94
|
-
- `merge` _function_ — Merge overlapping intervals so a side can't double-count itself.
|
|
95
|
-
- `overlap_seconds` _function_ — Total seconds where any interval of A overlaps any interval of B.
|
|
96
|
-
- `self_overlap_max` _function_ — Max simultaneously in-flight jobs within one lane + seconds at depth >= 2.
|
|
97
|
-
|
|
98
|
-
### `tests_manual.validate_stage7_volume_journal_e2e`
|
|
99
|
-
|
|
100
|
-
- `checkpoint_copy` _function_ — Checkpoint-then-copy (the stage-3 G3 backup discipline — never copy
|
|
101
|
-
- `journal_rows` _function_
|
|
102
|
-
- `main` _function_
|
|
103
|
-
|
|
104
63
|
## Dependencies
|
|
105
64
|
|
|
106
|
-
**Depends on:** `cjm-substrate`
|
|
65
|
+
**Depends on:** `cjm-capability-primitives`, `cjm-context-graph-layer`, `cjm-context-graph-primitives`, `cjm-substrate`, `cjm-transcript-graph-schema`
|
|
66
|
+
**Used by:** `cjm-transcript-decomp-tui`
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "0.0.4"
|
|
@@ -10,9 +10,11 @@ Prerequisite runtime (once, from the repo root):
|
|
|
10
10
|
cjm-ctl --cjm-config cjm.yaml setup-runtime
|
|
11
11
|
cjm-ctl --cjm-config cjm.yaml install-all --capabilities capabilities_test.yaml --force
|
|
12
12
|
|
|
13
|
-
Then decompose
|
|
13
|
+
Then decompose transcription-core run manifest(s) — a multi-manifest batch
|
|
14
|
+
shares ONE loaded capability stack (models load once, per-manifest runs):
|
|
14
15
|
|
|
15
16
|
cjm-transcript-decomp-core run path/to/transcription-run.json --yes
|
|
17
|
+
cjm-transcript-decomp-core run runs/run_a.json runs/run_b.json --yes
|
|
16
18
|
# GPU runs: opt into CR-7 GPU subtree attribution
|
|
17
19
|
cjm-transcript-decomp-core run run.json --yes --sysmon-capability cjm-capability-monitor-nvidia
|
|
18
20
|
"""
|
|
@@ -21,11 +23,13 @@ import argparse
|
|
|
21
23
|
import asyncio
|
|
22
24
|
import getpass
|
|
23
25
|
import logging
|
|
26
|
+
import os
|
|
24
27
|
from pathlib import Path
|
|
25
28
|
from typing import Any, Dict, List, Optional
|
|
26
29
|
|
|
27
30
|
from cjm_substrate.core.manager import CapabilityManager
|
|
28
31
|
from cjm_substrate.core.queue import JobQueue
|
|
32
|
+
from cjm_substrate.core.workspace import resolve_workspace
|
|
29
33
|
from cjm_transcript_decomp_core.models import DecompConfig
|
|
30
34
|
from cjm_transcript_decomp_core.pipeline import load_source_manifest, run_decomp
|
|
31
35
|
|
|
@@ -41,7 +45,8 @@ def build_parser() -> argparse.ArgumentParser: # Configured CLI parser
|
|
|
41
45
|
sub = parser.add_subparsers(dest="command", required=True)
|
|
42
46
|
|
|
43
47
|
run = sub.add_parser("run", help="Extend a transcription-emitted graph root with the fine spine")
|
|
44
|
-
run.add_argument("
|
|
48
|
+
run.add_argument("manifests", nargs="+",
|
|
49
|
+
help="Transcription-core run manifest JSON(s) — a batch shares ONE loaded capability stack")
|
|
45
50
|
run.add_argument("--manifests-dir", default=".cjm/manifests", help="Capability manifests directory")
|
|
46
51
|
run.add_argument("--vad-capability", default="cjm-capability-silero-vad", help="VAD capability name")
|
|
47
52
|
run.add_argument("--fa-capability", default="cjm-capability-qwen3-forced-aligner", help="Forced-alignment capability name")
|
|
@@ -56,7 +61,15 @@ def build_parser() -> argparse.ArgumentParser: # Configured CLI parser
|
|
|
56
61
|
run.add_argument("--language", default="English", help="Forced-alignment language")
|
|
57
62
|
run.add_argument("--force", action="store_true", help="Bypass capability-side caches (VAD + FA)")
|
|
58
63
|
run.add_argument("-y", "--yes", action="store_true", help="Auto-accept HITL seams (headless mode)")
|
|
59
|
-
run.add_argument("--output", default=None, help="Decomp-manifest output path (default:
|
|
64
|
+
run.add_argument("--output", default=None, help="Decomp-manifest output path (single-manifest runs only; default: <output-dir>/<run_id>.json)")
|
|
65
|
+
run.add_argument("--output-dir", default=None,
|
|
66
|
+
help="Decomp-manifest output directory (callers with a shared runs dir "
|
|
67
|
+
"pass it so manifests land beside their sources; default: the "
|
|
68
|
+
"workspace's runs/ when one is active, else runs/ under the cwd)")
|
|
69
|
+
run.add_argument("--workspace", default=None,
|
|
70
|
+
help="Workspace root (5daadfc4; default: CJM_WORKSPACE env, else upward walk "
|
|
71
|
+
"from cwd). Supplies the --output-dir default and is exported so "
|
|
72
|
+
"substrate config + capability workers resolve workspace-scoped paths")
|
|
60
73
|
run.add_argument("--actor", default=None,
|
|
61
74
|
help="Journal attribution for who/what initiated this run (default: cli:<username>)")
|
|
62
75
|
run.add_argument("-v", "--verbose", action="store_true", help="DEBUG-level logging")
|
|
@@ -85,11 +98,31 @@ def load_capabilities(
|
|
|
85
98
|
|
|
86
99
|
async def run_command(
|
|
87
100
|
args: argparse.Namespace, # Parsed CLI arguments for the `run` subcommand
|
|
88
|
-
) -> int: # Process exit code (0 =
|
|
89
|
-
"""Execute the `run` subcommand: extend
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
101
|
+
) -> int: # Process exit code (0 = every manifest fully extended + verified)
|
|
102
|
+
"""Execute the `run` subcommand: extend transcription-run manifest(s) with the fine spine.
|
|
103
|
+
|
|
104
|
+
Batch shape (decomp-TUI demand, work item 0ff6bf0f): N manifests ride ONE
|
|
105
|
+
capability stack — the models load once and every manifest reuses them,
|
|
106
|
+
where N CLI invocations would pay N model loads. Each manifest keeps its
|
|
107
|
+
own run_id, decomp manifest, and RUN_STARTED/RUN_FINISHED journal bracket,
|
|
108
|
+
so a batch member is indistinguishable from a solo run downstream. A failed
|
|
109
|
+
member records and the batch continues (unattended queueing must not sink
|
|
110
|
+
the rest); the exit code aggregates across members.
|
|
111
|
+
"""
|
|
112
|
+
# 5daadfc4 workspace: resolve BEFORE any substrate config loads; export so
|
|
113
|
+
# the process tree (substrate config, capability workers) is workspace-scoped.
|
|
114
|
+
ws = resolve_workspace(explicit=getattr(args, "workspace", None))
|
|
115
|
+
if ws is not None:
|
|
116
|
+
os.environ["CJM_WORKSPACE"] = str(ws.root)
|
|
117
|
+
output_dir = (Path(args.output_dir) if args.output_dir
|
|
118
|
+
else (ws.runs_dir if ws is not None else Path("runs")))
|
|
119
|
+
manifest_paths = [str(Path(m).resolve()) for m in args.manifests]
|
|
120
|
+
missing = [m for m in manifest_paths if not Path(m).exists()]
|
|
121
|
+
if missing:
|
|
122
|
+
raise SystemExit(f"source manifest(s) not found: {', '.join(missing)}")
|
|
123
|
+
if args.output and len(manifest_paths) > 1:
|
|
124
|
+
raise SystemExit("--output names ONE decomp manifest — omit it for batch runs "
|
|
125
|
+
"(each lands at runs/<run_id>.json)")
|
|
93
126
|
|
|
94
127
|
cfg = DecompConfig(
|
|
95
128
|
vad_capability=args.vad_capability,
|
|
@@ -118,11 +151,28 @@ async def run_command(
|
|
|
118
151
|
|
|
119
152
|
queue = JobQueue(deps=manager, sysmon_capability_name=args.sysmon_capability)
|
|
120
153
|
await queue.start()
|
|
154
|
+
all_ok = True
|
|
121
155
|
try:
|
|
122
156
|
# CR-14 follow-up: actor attribution (operator identity by default;
|
|
123
157
|
# agents/services pass --actor explicitly).
|
|
124
158
|
actor = args.actor or f"cli:{getpass.getuser()}"
|
|
125
|
-
|
|
159
|
+
for mp in manifest_paths:
|
|
160
|
+
try:
|
|
161
|
+
manifest = await run_decomp(manager, queue, cfg, mp, actor=actor)
|
|
162
|
+
except Exception as e: # One member's failure must not sink the batch
|
|
163
|
+
logger.error(f"decomp failed for {mp}: {e}")
|
|
164
|
+
print(f"FAILED {mp}: {e}")
|
|
165
|
+
all_ok = False
|
|
166
|
+
continue
|
|
167
|
+
out = (Path(args.output) if args.output
|
|
168
|
+
else output_dir / f"{manifest.run_id}.json")
|
|
169
|
+
manifest.save(out, workspace=ws)
|
|
170
|
+
n_manifest_sources = len(load_source_manifest(mp).get("sources", []) or [])
|
|
171
|
+
n_sources = len(manifest.sources)
|
|
172
|
+
n_segs = sum(s.segment_count for s in manifest.sources)
|
|
173
|
+
print(f"decomp manifest: {out}")
|
|
174
|
+
print(f"sources extended: {n_sources}/{n_manifest_sources} segment nodes: {n_segs}")
|
|
175
|
+
all_ok = all_ok and (n_sources == n_manifest_sources)
|
|
126
176
|
finally:
|
|
127
177
|
await queue.stop()
|
|
128
178
|
for iid in reversed(load_order): # Reverse load order; the monitor unloads last
|
|
@@ -130,15 +180,7 @@ async def run_command(
|
|
|
130
180
|
manager.unload_capability(iid)
|
|
131
181
|
except Exception as e: # Best-effort teardown; never mask the run's outcome
|
|
132
182
|
logger.warning(f"unload {iid} failed: {e}")
|
|
133
|
-
|
|
134
|
-
out = Path(args.output) if args.output else Path("runs") / f"{manifest.run_id}.json"
|
|
135
|
-
manifest.save(out)
|
|
136
|
-
n_manifest_sources = len(load_source_manifest(manifest_path).get("sources", []) or [])
|
|
137
|
-
n_sources = len(manifest.sources)
|
|
138
|
-
n_segs = sum(s.segment_count for s in manifest.sources)
|
|
139
|
-
print(f"decomp manifest: {out}")
|
|
140
|
-
print(f"sources extended: {n_sources}/{n_manifest_sources} segment nodes: {n_segs}")
|
|
141
|
-
return 0 if n_sources == n_manifest_sources else 1
|
|
183
|
+
return 0 if all_ok else 1
|
|
142
184
|
|
|
143
185
|
|
|
144
186
|
def main(
|
|
@@ -7,6 +7,8 @@ from dataclasses import asdict, dataclass, field
|
|
|
7
7
|
from pathlib import Path
|
|
8
8
|
from typing import Any, Dict, List, Optional, Union
|
|
9
9
|
|
|
10
|
+
from cjm_substrate.core.workspace import relativize_recorded
|
|
11
|
+
|
|
10
12
|
|
|
11
13
|
@dataclass
|
|
12
14
|
class FAWord:
|
|
@@ -173,11 +175,16 @@ class DecompManifest:
|
|
|
173
175
|
def save(
|
|
174
176
|
self,
|
|
175
177
|
path: Union[str, Path], # Destination JSON file (parent dirs created)
|
|
178
|
+
workspace=None, # Active Workspace; owned paths record as ${WS}/<rel> (5daadfc4 rung f)
|
|
176
179
|
) -> Path: # The written path
|
|
177
|
-
"""Write the manifest as pretty-printed JSON.
|
|
180
|
+
"""Write the manifest as pretty-printed JSON.
|
|
181
|
+
|
|
182
|
+
With `workspace`, recorded paths under its root take the ${WS}/ token
|
|
183
|
+
form (relativize_recorded), so the manifest relocates with the
|
|
184
|
+
workspace; readers resolve via resolve_recorded_tree at load."""
|
|
178
185
|
out = Path(path)
|
|
179
186
|
out.parent.mkdir(parents=True, exist_ok=True)
|
|
180
|
-
out.write_text(json.dumps(self.to_dict(), indent=2))
|
|
187
|
+
out.write_text(json.dumps(relativize_recorded(self.to_dict(), workspace), indent=2))
|
|
181
188
|
return out
|
|
182
189
|
|
|
183
190
|
|
|
@@ -10,12 +10,14 @@ from typing import Any, Dict, List, Optional, Tuple
|
|
|
10
10
|
from cjm_capability_primitives.forced_alignment import ForcedAlignResult
|
|
11
11
|
from cjm_capability_primitives.vad import VADResult
|
|
12
12
|
from cjm_context_graph_layer.declare import Derivation, derivation_to_graph
|
|
13
|
-
from cjm_context_graph_layer.
|
|
13
|
+
from cjm_context_graph_layer.journal import journal_extend, sidecar_journal_path, wires_handlers
|
|
14
|
+
from cjm_context_graph_layer.ops import graph_task
|
|
14
15
|
from cjm_substrate.core.empirical_store import compute_config_hash
|
|
15
16
|
from cjm_substrate.core.journal_store import JournalEvent, SubstrateEventType
|
|
16
17
|
from cjm_substrate.core.manager import CapabilityManager
|
|
17
18
|
from cjm_substrate.core.ports import Composition, CompositionNode, NodeState
|
|
18
19
|
from cjm_substrate.core.queue import JobQueue, JobStatus
|
|
20
|
+
from cjm_substrate.core.workspace import resolve_recorded_tree
|
|
19
21
|
from cjm_transcript_decomp_core.alignment import (assign_words_to_chunks,
|
|
20
22
|
build_segments_from_alignment,
|
|
21
23
|
map_fa_words_to_text, tier1_alignment_checks)
|
|
@@ -58,8 +60,11 @@ def load_source_manifest(
|
|
|
58
60
|
|
|
59
61
|
Consumed as untyped JSON — the format/version tags are the only interchange
|
|
60
62
|
contract (no shared schema type across cores; manifest-as-interchange, CR-20).
|
|
63
|
+
${WS}/ recorded paths (5daadfc4 rung f) resolve to absolute here, anchored
|
|
64
|
+
at the manifest's own location (active workspace as fallback), so all
|
|
65
|
+
downstream consumers keep seeing absolute paths.
|
|
61
66
|
"""
|
|
62
|
-
data = json.loads(Path(path).read_text())
|
|
67
|
+
data = resolve_recorded_tree(json.loads(Path(path).read_text()), Path(path))
|
|
63
68
|
fmt = data.get("format", "")
|
|
64
69
|
if "transcription-core" not in fmt:
|
|
65
70
|
logger.warning(f"unexpected source manifest format: {fmt!r} (continuing)")
|
|
@@ -380,6 +385,10 @@ async def run_decomp(
|
|
|
380
385
|
capabilities=collect_capability_info(manager, [cfg.vad_capability, cfg.fa_capability, cfg.graph_capability]),
|
|
381
386
|
)
|
|
382
387
|
vad_config_hash = str((manifest.capabilities.get(cfg.vad_capability) or {}).get("config_hash") or "")
|
|
388
|
+
# Pipeline writes append through to the graph db's SIDECAR journal (DEC ccbab9f5 /
|
|
389
|
+
# finding 4219da27): unjournaled ingestion would erode db-rebuildability.
|
|
390
|
+
graph_db_path = (manifest.capabilities.get(cfg.graph_capability) or {}).get("db_path")
|
|
391
|
+
graph_journal_path = sidecar_journal_path(str(graph_db_path)) if graph_db_path else None
|
|
383
392
|
|
|
384
393
|
sources = src.get("sources", []) or []
|
|
385
394
|
status = "completed"
|
|
@@ -419,7 +428,12 @@ async def run_decomp(
|
|
|
419
428
|
status = "aborted"
|
|
420
429
|
break
|
|
421
430
|
|
|
422
|
-
res = await
|
|
431
|
+
res = await journal_extend(queue, cfg.graph_capability, nodes, edges,
|
|
432
|
+
journal_path=graph_journal_path, verb="spine-extension",
|
|
433
|
+
actor="pipeline:cjm-transcript-decomp-core", run=run_id,
|
|
434
|
+
args={"source_id": ids["source"],
|
|
435
|
+
"segments": len(ids["segments"]),
|
|
436
|
+
"text_from": text_from})
|
|
423
437
|
logger.info(f"[src {i}] extension: +{res.nodes_added} node(s) "
|
|
424
438
|
f"({res.nodes_verified} verified present), +{res.edges_added} edge(s) "
|
|
425
439
|
f"({res.edges_existing} existing)")
|
|
@@ -431,7 +445,10 @@ async def run_decomp(
|
|
|
431
445
|
"text_from": text_from},
|
|
432
446
|
)
|
|
433
447
|
dn, de = derivation_to_graph(d)
|
|
434
|
-
await
|
|
448
|
+
await journal_extend(queue, cfg.graph_capability, [dn], de,
|
|
449
|
+
journal_path=graph_journal_path, verb="derivation",
|
|
450
|
+
actor="pipeline:cjm-transcript-decomp-core", run=run_id,
|
|
451
|
+
args={"method": "alignment-fold/v1"})
|
|
435
452
|
|
|
436
453
|
# Fine spine hangs under the run's renditions — verify scopes there.
|
|
437
454
|
vr = await verify_source(queue, cfg.graph_capability, ids["source"], ids["renditions"])
|
|
@@ -473,3 +490,14 @@ async def run_decomp(
|
|
|
473
490
|
"segments": sum(s.segment_count for s in manifest.sources),
|
|
474
491
|
})
|
|
475
492
|
return manifest
|
|
493
|
+
|
|
494
|
+
|
|
495
|
+
def decomp_replay_handlers() -> Dict[str, Any]: # verb -> async handler(queue, graph_id, op)
|
|
496
|
+
"""The decomp core's replay vocabulary (DEC 426658f1, replay stays DOMAIN-OWNED).
|
|
497
|
+
|
|
498
|
+
Exported through the `cjm_context_graph_layer.replay` entry-point group and
|
|
499
|
+
unioned by `composed_replay_handlers`. Both verbs are `journal_extend` ops —
|
|
500
|
+
wire-carrying by construction — so they register the layer's shared
|
|
501
|
+
`apply_wires` (identity-comparable across cores: transcription also emits
|
|
502
|
+
`derivation`, and the shared handler keeps that collision legal)."""
|
|
503
|
+
return wires_handlers("spine-extension", "derivation")
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: cjm-transcript-decomp-core
|
|
3
|
-
Version: 0.0.
|
|
3
|
+
Version: 0.0.4
|
|
4
4
|
Summary: A frontend-agnostic core for the transcript decomposition workflow — composes isolated capability workers (forced alignment, VAD, graph storage) into a headless pipeline that decomposes transcription run manifests into a VAD-aligned context-graph spine with traceable provenance, and a CLI as its first driver.
|
|
5
5
|
Author-email: "Christian J. Mills" <9126128+cj-mills@users.noreply.github.com>
|
|
6
6
|
License: Apache-2.0
|
|
@@ -10,10 +10,10 @@ Classifier: Programming Language :: Python :: 3 :: Only
|
|
|
10
10
|
Requires-Python: >=3.12
|
|
11
11
|
Description-Content-Type: text/markdown
|
|
12
12
|
License-File: LICENSE
|
|
13
|
-
Requires-Dist: cjm_substrate>=0.0.
|
|
14
|
-
Requires-Dist: cjm_context_graph_primitives>=0.0.
|
|
13
|
+
Requires-Dist: cjm_substrate>=0.0.57
|
|
14
|
+
Requires-Dist: cjm_context_graph_primitives>=0.0.15
|
|
15
15
|
Requires-Dist: cjm_capability_primitives>=0.0.10
|
|
16
|
-
Requires-Dist: cjm-context-graph-layer>=0.0.
|
|
16
|
+
Requires-Dist: cjm-context-graph-layer>=0.0.11
|
|
17
17
|
Requires-Dist: cjm-transcript-graph-schema>=0.0.7
|
|
18
18
|
Dynamic: license-file
|
|
19
19
|
|
|
@@ -26,15 +26,10 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
26
26
|
## Modules
|
|
27
27
|
|
|
28
28
|
- **`cjm_transcript_decomp_core.alignment`** — Pure forced-alignment logic (no capability calls): map FA words back to character spans in the original text, assign words to VAD chunks by timestamp, and build one text segment per VAD chunk. Extracted from the page-centric ForcedAlignmentService (Tier-1 logic).
|
|
29
|
-
- **`cjm_transcript_decomp_core.cli`** — The CLI driver — the decomposition core's first (and currently only) frontend.
|
|
29
|
+
- **`cjm_transcript_decomp_core.cli`** — The CLI driver — the decomposition core's first (and currently only) frontend.
|
|
30
30
|
- **`cjm_transcript_decomp_core.graph`** — Graph-spine EXTENSION + skeptical-lens verification (stage 5, CR-18 revolution 2). Decomp no longer creates a Document: it RECOMPUTES the transcription-emitted root's deterministic node ids from the consumed manifest (no search), verifies the root exists, and attaches the fine Segment spine under the existing AudioSegment nodes — PART_OF to the owning rendition, STARTS_WITH per rendition (the coarse-seam jump anchor), source-wide NEXT. Each Segment carries the audio TimeSlice ref plus per-transcriber CharSlice refs into the Transcript nodes (the D4/P10 framing, finally expressible). Commit goes through the layer's idempotent extend_graph.
|
|
31
31
|
- **`cjm_transcript_decomp_core.models`** — Lean data shapes for the transcript-decomposition pipeline: in-core mirrors of the forced-alignment / VAD / text DTOs (no FastHTML deps), run configuration, the committed graph-segment carrier, and the decomposition run manifest (proto-bundle).
|
|
32
32
|
- **`cjm_transcript_decomp_core.pipeline`** — The headless decomposition pipeline (stage 5: decomp is an EXTENDER). Load a transcription run manifest, verify the transcription-emitted graph root exists (the graph begins at transcription), then per source per pipeline-segment run VAD + per-transcriber forced alignment, build one aligned segment per VAD chunk with per-transcriber text variants, and attach the fine spine under the existing AudioSegment nodes via the layer's idempotent extend_graph — with HITL approval seams between alignment, commit, and the next source.
|
|
33
|
-
- **`tests.test_alignment`** — Tests for cjm_transcript_decomp_core.alignment — pure forced-alignment logic.
|
|
34
|
-
- **`tests.test_graph`** — Tests for cjm_transcript_decomp_core.graph — fine-spine extension payload.
|
|
35
|
-
- **`tests.test_models`** — Tests for cjm_transcript_decomp_core.models — decomposition data shapes.
|
|
36
|
-
- **`tests_manual.measure_cold_fanout_overlap_e2e`** — Cold-run M×(VAD ∥ T×FA) fan-out overlap measurement (stage-5 closeout;
|
|
37
|
-
- **`tests_manual.validate_stage7_volume_journal_e2e`** — Stage-7 stress part 6 — volume regression on the REAL corpus.
|
|
38
33
|
|
|
39
34
|
## API
|
|
40
35
|
|
|
@@ -50,7 +45,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
50
45
|
- `build_parser` _function_ — Build the CLI parser (subcommands: run).
|
|
51
46
|
- `load_capabilities` _function_ — Discover manifests + load each requested capability (default instance).
|
|
52
47
|
- `main` _function_ — CLI entry point (console script: `cjm-transcript-decomp-core`).
|
|
53
|
-
- `run_command` _function_ — Execute the `run` subcommand: extend
|
|
48
|
+
- `run_command` _function_ — Execute the `run` subcommand: extend transcription-run manifest(s) with the fine spine.
|
|
54
49
|
|
|
55
50
|
### `cjm_transcript_decomp_core.graph`
|
|
56
51
|
|
|
@@ -76,6 +71,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
76
71
|
- `build_alignment_composition` _function_ — Build the whole-source M×(VAD ∥ T×FA) composition (D8 fan-in, stage-5 variants).
|
|
77
72
|
- `collect_capability_info` _function_ — Record capability identity + data-DB pointers for the run manifest (provenance).
|
|
78
73
|
- `confirm_seam` _function_ — HITL approval seam in its cheapest viable form (log + optional CLI prompt).
|
|
74
|
+
- `decomp_replay_handlers` _function_ — The decomp core's replay vocabulary (DEC 426658f1, replay stays DOMAIN-OWNED).
|
|
79
75
|
- `decompose_source` _function_ — Decompose one source into aligned fine segments with per-transcriber variants.
|
|
80
76
|
- `fa_words_from_result` _function_ — Normalize a typed forced-alignment result into FA words (pure; stage 3).
|
|
81
77
|
- `load_source_manifest` _function_ — Load + lightly validate a transcription-core run manifest.
|
|
@@ -83,43 +79,7 @@ A frontend-agnostic core for the transcript decomposition workflow — composes
|
|
|
83
79
|
- `submit_and_wait` _function_ — Submit one capability job, wait for it, and return its result (raise on failure).
|
|
84
80
|
- `vad_chunks_from_result` _function_ — Normalize a typed VAD result into segment-local VAD chunks.
|
|
85
81
|
|
|
86
|
-
### `tests.test_alignment`
|
|
87
|
-
|
|
88
|
-
- `test_assign_words_to_chunks_by_timestamp` _function_
|
|
89
|
-
- `test_build_segments_per_chunk` _function_
|
|
90
|
-
- `test_empty_chunk_yields_empty_segment_warning` _function_
|
|
91
|
-
- `test_map_fa_words_to_text_spans` _function_
|
|
92
|
-
|
|
93
|
-
### `tests.test_graph`
|
|
94
|
-
|
|
95
|
-
- `test_edge_topology_spans_coarse_boundary` _function_
|
|
96
|
-
- `test_extension_payload_deterministic_ids` _function_
|
|
97
|
-
- `test_preprocessed_manifest_distinct_renditions_same_boundaries` _function_
|
|
98
|
-
- `test_provenance_refs_and_text_from` _function_
|
|
99
|
-
- `test_resolve_root_ids_recomputation` _function_
|
|
100
|
-
|
|
101
|
-
### `tests.test_models`
|
|
102
|
-
|
|
103
|
-
- `test_faword_from_wire_tolerates_extra_keys` _function_
|
|
104
|
-
- `test_manifest_save_round_trip` _function_
|
|
105
|
-
- `test_manifest_shape_and_run_id` _function_
|
|
106
|
-
- `test_stage5_segment_shape` _function_
|
|
107
|
-
- `test_vad_chunk_duration` _function_
|
|
108
|
-
|
|
109
|
-
### `tests_manual.measure_cold_fanout_overlap_e2e`
|
|
110
|
-
|
|
111
|
-
- `lane_intervals` _function_ — (start, end) UTC intervals for completed jobs of one instance.
|
|
112
|
-
- `main` _function_
|
|
113
|
-
- `merge` _function_ — Merge overlapping intervals so a side can't double-count itself.
|
|
114
|
-
- `overlap_seconds` _function_ — Total seconds where any interval of A overlaps any interval of B.
|
|
115
|
-
- `self_overlap_max` _function_ — Max simultaneously in-flight jobs within one lane + seconds at depth >= 2.
|
|
116
|
-
|
|
117
|
-
### `tests_manual.validate_stage7_volume_journal_e2e`
|
|
118
|
-
|
|
119
|
-
- `checkpoint_copy` _function_ — Checkpoint-then-copy (the stage-3 G3 backup discipline — never copy
|
|
120
|
-
- `journal_rows` _function_
|
|
121
|
-
- `main` _function_
|
|
122
|
-
|
|
123
82
|
## Dependencies
|
|
124
83
|
|
|
125
|
-
**Depends on:** `cjm-substrate`
|
|
84
|
+
**Depends on:** `cjm-capability-primitives`, `cjm-context-graph-layer`, `cjm-context-graph-primitives`, `cjm-substrate`, `cjm-transcript-graph-schema`
|
|
85
|
+
**Used by:** `cjm-transcript-decomp-tui`
|
|
@@ -14,7 +14,7 @@ classifiers = [
|
|
|
14
14
|
"Programming Language :: Python :: 3",
|
|
15
15
|
"Programming Language :: Python :: 3 :: Only",
|
|
16
16
|
]
|
|
17
|
-
dependencies = ['cjm_substrate>=0.0.
|
|
17
|
+
dependencies = ['cjm_substrate>=0.0.57', 'cjm_context_graph_primitives>=0.0.15', 'cjm_capability_primitives>=0.0.10', 'cjm-context-graph-layer>=0.0.11', 'cjm-transcript-graph-schema>=0.0.7']
|
|
18
18
|
|
|
19
19
|
[project.urls]
|
|
20
20
|
Repository = "https://github.com/cj-mills/cjm-transcript-decomp-core"
|
|
@@ -22,6 +22,9 @@ Repository = "https://github.com/cj-mills/cjm-transcript-decomp-core"
|
|
|
22
22
|
[project.scripts]
|
|
23
23
|
cjm-transcript-decomp-core = "cjm_transcript_decomp_core.cli:main"
|
|
24
24
|
|
|
25
|
+
[project.entry-points."cjm_context_graph_layer.replay"]
|
|
26
|
+
decomp = "cjm_transcript_decomp_core.pipeline:decomp_replay_handlers"
|
|
27
|
+
|
|
25
28
|
[tool.setuptools.dynamic]
|
|
26
29
|
version = {attr = "cjm_transcript_decomp_core.__version__"}
|
|
27
30
|
|
|
@@ -8,12 +8,16 @@ def test_run_defaults():
|
|
|
8
8
|
p = build_parser()
|
|
9
9
|
args = p.parse_args(["run", "m.json", "--yes", "--language", "English"])
|
|
10
10
|
assert args.command == "run"
|
|
11
|
-
assert args.
|
|
11
|
+
assert args.manifests == ["m.json"] # single manifest = a batch of one
|
|
12
12
|
assert args.yes is True
|
|
13
13
|
assert args.fa_capability == "cjm-capability-qwen3-forced-aligner"
|
|
14
14
|
assert args.graph_capability == "cjm-capability-graph-sqlite"
|
|
15
15
|
assert args.text_from is None # authority defaults to the manifest's sole transcriber
|
|
16
16
|
assert args.sysmon_capability is None
|
|
17
|
+
# 5daadfc4: None sentinel — run_command resolves the workspace's runs/ when
|
|
18
|
+
# one is active, else the legacy cwd-relative runs/; TUIs pin their browsed dir
|
|
19
|
+
assert args.output_dir is None
|
|
20
|
+
assert args.workspace is None
|
|
17
21
|
|
|
18
22
|
|
|
19
23
|
def test_text_from_and_sysmon_flags():
|
|
@@ -22,3 +26,12 @@ def test_text_from_and_sysmon_flags():
|
|
|
22
26
|
"--sysmon-capability", "cjm-capability-monitor-nvidia"])
|
|
23
27
|
assert args.text_from == "cjm-capability-voxtral-hf"
|
|
24
28
|
assert args.sysmon_capability == "cjm-capability-monitor-nvidia"
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
def test_batch_manifests():
|
|
32
|
+
# Batch shape (work item 0ff6bf0f): N manifests, one invocation, one stack.
|
|
33
|
+
p = build_parser()
|
|
34
|
+
args = p.parse_args(["run", "a.json", "b.json", "c.json", "--yes",
|
|
35
|
+
"--text-from", "cjm-capability-voxtral-hf"])
|
|
36
|
+
assert args.manifests == ["a.json", "b.json", "c.json"]
|
|
37
|
+
assert args.text_from == "cjm-capability-voxtral-hf"
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
__version__ = "0.0.1"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/tests/test_alignment.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{cjm_transcript_decomp_core-0.0.1 → cjm_transcript_decomp_core-0.0.4}/tests/test_pipeline.py
RENAMED
|
File without changes
|