chunker and ui
This commit is contained in:
98
tests/chunker/test_processor.py
Normal file
98
tests/chunker/test_processor.py
Normal file
@@ -0,0 +1,98 @@
|
||||
"""
|
||||
Tests for Processor implementations — ChecksumProcessor, SimulatedDecodeProcessor, CompositeProcessor.
|
||||
|
||||
Demonstrates: TDD (Interview Topic 8) — ABC contract, parametrized tests.
|
||||
"""
|
||||
|
||||
import pytest
|
||||
|
||||
from core.chunker.exceptions import ChunkChecksumError
|
||||
from core.chunker.models import Chunk
|
||||
from core.chunker.processor import (
|
||||
ChecksumProcessor,
|
||||
CompositeProcessor,
|
||||
Processor,
|
||||
SimulatedDecodeProcessor,
|
||||
)
|
||||
|
||||
|
||||
class TestChecksumProcessor:
|
||||
def test_valid_time_range(self, sample_chunk):
|
||||
"""Valid time range passes."""
|
||||
proc = ChecksumProcessor()
|
||||
result = proc.process(sample_chunk)
|
||||
assert result.success is True
|
||||
assert result.checksum_valid is True
|
||||
assert result.processing_time > 0
|
||||
|
||||
def test_invalid_time_range(self):
|
||||
"""Invalid time range raises ChunkChecksumError."""
|
||||
chunk = Chunk(
|
||||
sequence=0,
|
||||
start_time=10.0,
|
||||
end_time=10.0, # zero duration
|
||||
source_path="/fake.mp4",
|
||||
duration=0.0,
|
||||
)
|
||||
proc = ChecksumProcessor()
|
||||
with pytest.raises(ChunkChecksumError) as exc_info:
|
||||
proc.process(chunk)
|
||||
assert exc_info.value.sequence == 0
|
||||
|
||||
def test_sequence_preserved(self, make_chunk):
|
||||
"""Result carries the chunk's sequence number."""
|
||||
chunk = make_chunk(42)
|
||||
proc = ChecksumProcessor()
|
||||
result = proc.process(chunk)
|
||||
assert result.sequence == 42
|
||||
|
||||
|
||||
class TestSimulatedDecodeProcessor:
|
||||
def test_processes_successfully(self, sample_chunk):
|
||||
"""Simulated decode always succeeds."""
|
||||
proc = SimulatedDecodeProcessor(ms_per_second=1.0)
|
||||
result = proc.process(sample_chunk)
|
||||
assert result.success is True
|
||||
assert result.processing_time > 0
|
||||
|
||||
def test_time_proportional_to_duration(self):
|
||||
"""Longer chunks take longer."""
|
||||
short = Chunk(0, 0.0, 1.0, "/fake.mp4", 1.0)
|
||||
long = Chunk(1, 0.0, 10.0, "/fake.mp4", 10.0)
|
||||
|
||||
proc = SimulatedDecodeProcessor(ms_per_second=50.0)
|
||||
r_short = proc.process(short)
|
||||
r_long = proc.process(long)
|
||||
|
||||
assert r_long.processing_time > r_short.processing_time
|
||||
|
||||
|
||||
class TestCompositeProcessor:
|
||||
def test_chains_processors(self, sample_chunk):
|
||||
"""Composite runs all processors in sequence."""
|
||||
proc = CompositeProcessor([
|
||||
ChecksumProcessor(),
|
||||
SimulatedDecodeProcessor(ms_per_second=1.0),
|
||||
])
|
||||
result = proc.process(sample_chunk)
|
||||
assert result.success is True
|
||||
|
||||
def test_stops_on_failure(self):
|
||||
"""If first processor raises, composite propagates the error."""
|
||||
bad_chunk = Chunk(0, 10.0, 10.0, "/fake.mp4", 0.0) # invalid range
|
||||
proc = CompositeProcessor([
|
||||
ChecksumProcessor(),
|
||||
SimulatedDecodeProcessor(ms_per_second=1.0),
|
||||
])
|
||||
with pytest.raises(ChunkChecksumError):
|
||||
proc.process(bad_chunk)
|
||||
|
||||
def test_requires_at_least_one(self):
|
||||
"""Empty processor list raises ValueError."""
|
||||
with pytest.raises(ValueError, match="at least one"):
|
||||
CompositeProcessor([])
|
||||
|
||||
def test_is_processor(self):
|
||||
"""CompositeProcessor is a Processor."""
|
||||
proc = CompositeProcessor([ChecksumProcessor()])
|
||||
assert isinstance(proc, Processor)
|
||||
Reference in New Issue
Block a user