feat: Nicht-Optimierungsaufgaben ablehnen statt modellieren

Bisher erzeugte is_optimization_task=False nur eine Log-Warnung; eine
reine Gleichung wurde trotzdem in ein Optimierungsmodell gepresst.
Jetzt bricht run_pipeline direkt nach dem Verstehen ab: kein
Nachfassen, keine Extraktion, kein Solver. PipelineResult.rejected,
reliable=False, specification/review optional; Report "Aufgabe
abgelehnt", CLI-Exit-Code 3, Benchmark-Status "abgelehnt" (auch die
Ergebnistabelle verkraftet die Zeile), --von verweigert.

Der Verstehens-Prompt nennt reine Gleichungen/Rechenaufgaben als
Nicht-Aufgaben und Zulaessigkeitsfragen sowie moeglicherweise
unloesbare Planungen ausdruecklich als Aufgaben. Unvermessen;
Prompt-Kennung jetzt 0333bfd5f9fe.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Dieter Schlüter 2026-09-17 12:54:54 +02:00
commit 8697400dc2

View file

@ -543,3 +543,42 @@ def test_persistently_undeclared_data_is_unreliable():
result = run_pipeline("Aufgabe", session=session, max_revisions=0, max_restarts=0, solver_retries=1)
assert not result.reliable
assert any(p.startswith("Datenherkunft") for p in result.reliability_issues)
# Beobachtet: eine reine Gleichung (x! - 2x^2 + 1337 = 3629937) wurde nur mit Log-Warnung weiter modelliert
KEINE_AUFGABE = TaskUnderstanding(
is_optimization_task=False, reason="Eine Gleichung soll gelöst werden; es gibt nichts zu entscheiden.",
facts=[], ignored_numbers=[],
sub_questions=[SubQuestion(id="1", quote="x! - 2x**2 + 1337 = 3629937", kind="rechnen", needs_solver=True)])
def test_non_optimization_task_is_rejected_without_modeling(tmp_path):
from reporting.report import write_report
session = FakeSession(specs=[], reviews=[], understandings=[KEINE_AUFGABE])
result = run_pipeline("x! - 2x**2 + 1337 = 3629937", session=session)
assert result.rejected and not result.reliable
assert result.specification is None and result.solver_run is None
assert session.steps == ["Verstehen"] # kein Nachfassen, keine Extraktion, kein Solver
assert "Keine Optimierungsaufgabe" in result.reliability_issues[0]
for endung in ("md", "html"):
ziel = tmp_path / f"abgelehnt.{endung}"
write_report(result, str(ziel))
text = ziel.read_text(encoding="utf-8")
assert "Aufgabe abgelehnt" in text and "nichts zu entscheiden" in text
def test_rejected_result_cannot_be_continued_and_counts_as_failure(tmp_path, monkeypatch):
import pytest
from benchmark import benchmark
from TextToModel import continue_pipeline
session = FakeSession(specs=[], reviews=[], understandings=[KEINE_AUFGABE])
result = run_pipeline("x! = 120", session=session)
gespeichert = tmp_path / "abgelehnt.json"
gespeichert.write_text(result.model_dump_json())
with pytest.raises(ValueError, match="abgelehnt"):
continue_pipeline(str(gespeichert), "solver", session=session)
monkeypatch.setattr(benchmark, "run_pipeline", lambda *a, **k: result)
zeile = benchmark.run_case({"name": "gleichung", "task": "x! = 120", "expected": {}}, "fake", 1)
assert zeile["solver_status"] == "abgelehnt" and zeile["task_ok"] is False
benchmark.print_table([zeile]) # die Ergebnistabelle verkraftet die Zeile