ouroboros/tests/test_background_model_wait.py
Ouroboros c7cd252f2a Pin the alarm clock, the wake message and retarget the retired-loop harnesses
tests/test_consciousness.py is rewritten for tick(now): every branch
(disabled, live wake, live owner turn, not due, allowance unknown/exhausted,
no owner chat, launch with the envelope and rendered message, refusal,
finish -> chosen interval / pending reason / doubling backoff, notify
debounce, the same-instant admission race, self-trigger exclusion, boot floor,
the one-time inbox archive, graceful stop of a live wake, the snapshot keys).
tests/test_consciousness_wake.py pins the renderer (placeholders, event
truncation, fail-soft readers), the template's hints and the server status
projection.

Retired with the loop: test_consciousness_observations.py,
test_observation_fold.py, test_background_model_wait_browser.py, the
background twins in test_openai_chat_dispatch*.py, test_anthropic_native_custody.py,
test_transport_death_retry.py, the background-role pins in
test_owner_live_delivery.py / test_quiz_answer.py, the BG budget pins and the
consciousness max_tokens row. The context harnesses (test_repo_read_limits,
test_context, test_durable_learning_completeness) now assert the same
governance and gap facts on the wake's Main context through build_llm_messages;
test_background_model_wait.py keeps only the generic model-wait facts. The
docs-sync identifier audit resolves the wake template against the full
registry plus its render placeholders; the people/identity prompt pins follow
the new wording; test_settings_honesty pins that the wake-up bounds apply
without a restart; the persistence scan and the smoke tool inventory absorb
the retired fold segments and the registered set_next_wakeup.

Co-authored-by: Ouroboros <311266734+ouroboros-agent@users.noreply.github.com>
2026-09-16 06:03:21 +03:00

57 lines
3.3 KiB
Python

"""Model-wait facts that survive the Background Consciousness redesign: an owner
without a task ceiling keeps lexical deadlines, an image window is not a cycle
deadline, and an auth wait preserves the profile intent. (A wake-up is an ordinary
Main turn now; its model waits are the direct turn's own — see test_model_wait.)"""
import json
import pytest
from ouroboros import config, model_wait
from ouroboros import llm_claudexor as transport
from tests.test_llm_claudexor import MODEL
def test_image_window_fallback_does_not_create_a_ceilingless_owner_deadline(tmp_path, monkeypatch):
from ouroboros.tools.vision import _vision_execution_window
monkeypatch.setattr(config, "get_task_abs_ceiling_sec", lambda: 900)
with model_wait.task_model_wait_scope(task={"id": "ceilingless"}, drive_root=tmp_path,
event_queue=None, worker_slot_held=False, owner_control=lambda: None) as owner:
owner.started_monotonic = 0
assert owner.execution_window_remaining() is None
assert _vision_execution_window() == 900
assert owner.control_reason() is None
def test_ceilingless_owner_retains_lexical_deadlines_without_task_ceiling(tmp_path, monkeypatch):
owner = model_wait.TaskModelWait(task={"id": "ceilingless"}, drive_root=tmp_path,
event_queue=None, worker_slot_held=False, owner_control=lambda: None)
owner.started_monotonic = 0
monkeypatch.setattr(config, "get_task_abs_ceiling_sec", lambda: 0)
assert owner.control_reason() is None and owner.execution_window_remaining() is None
with model_wait.task_model_wait_scope(task={"id": "ceilingless"}, drive_root=tmp_path,
event_queue=None, worker_slot_held=False, owner_control=lambda: None) as bound:
with model_wait.execution_deadline_scope(model_wait.monotonic_now() - 1):
assert bound.control_reason() == "execution_deadline"
with model_wait.calendar_scope("2000-01-01T00:00:00Z"):
assert bound.control_reason() == "deadline"
@pytest.mark.parametrize("override,problem_context,expected", [
(None, {}, "configured-pin"), ("", {}, ""),
(None, {"credentialProfileId": "proved-profile"}, "proved-profile"),
])
def test_auth_wait_profile_hint_preserves_intent_without_inventing_route(tmp_path, monkeypatch, override, problem_context, expected):
monkeypatch.setenv("OUROBOROS_MODEL_ACCOUNTS", json.dumps({"main": "configured-pin"}))
waiter = model_wait.TaskModelWait(task={"id": "actor"}, drive_root=tmp_path,
event_queue=None, worker_slot_held=False,
row_mutator=lambda key, fn: model_wait.mutate_live_wait(waiter, key, fn),
owner_control=lambda: "stopped")
error = transport.ClaudexorModelError({"code": "auth_required", "context": problem_context},
model_role="main", route={})
with pytest.raises(model_wait.ModelWaitInterrupted):
waiter.wait(None, error, {"model": MODEL, "model_role": "main", "model_account_override": override})
row, = waiter.waits.values()
assert row["credential_profile_id"] == expected
assert error.route == {} # The UI hint is not claimed as an actual provider route.