|
2 | 2 | # All rights reserved. |
3 | 3 | # SPDX-License-Identifier: Apache-2.0 |
4 | 4 |
|
| 5 | +from contextlib import contextmanager |
5 | 6 | import json |
6 | 7 |
|
7 | 8 | import pytest |
8 | 9 |
|
9 | | -from nemo_retriever.harness.artifact_writer import artifact_paths, ArtifactWriter, capture_output_to_log, redact |
| 10 | +from nemo_retriever.harness.artifact_writer import ( |
| 11 | + append_text, |
| 12 | + artifact_paths, |
| 13 | + ArtifactWriter, |
| 14 | + capture_output_to_log, |
| 15 | + redact, |
| 16 | +) |
| 17 | +from nemo_retriever.harness.beir_runner import _write_trec_run |
10 | 18 | from nemo_retriever.harness.contracts import ( |
11 | 19 | EXIT_ARTIFACT_WRITE_FAILURE, |
12 | 20 | EXIT_INGEST_FAILURE, |
@@ -91,6 +99,42 @@ def test_redact_recurses_into_structured_override_values(): |
91 | 99 | assert redact(override) == 'query={"reranker_api_key": "<redacted>", "top_k": 10}' |
92 | 100 |
|
93 | 101 |
|
| 102 | +def test_redact_preserves_token_limits(): |
| 103 | + payload = { |
| 104 | + "reranker_api_key": "secret-value", |
| 105 | + "webhookUrl": "https://hooks.example.invalid/secret", |
| 106 | + "webhooks": ["https://hooks.example.invalid/one"], |
| 107 | + "passwords": ["password-value"], |
| 108 | + "client_secrets": ["client-secret"], |
| 109 | + "access_tokens": ["access-token"], |
| 110 | + "caption_max_tokens": 77, |
| 111 | + "text_chunk_overlap_tokens": 12, |
| 112 | + "tokenizer_model": "model-name", |
| 113 | + } |
| 114 | + |
| 115 | + assert redact(payload) == { |
| 116 | + "reranker_api_key": "<redacted>", |
| 117 | + "webhookUrl": "<redacted>", |
| 118 | + "webhooks": "<redacted>", |
| 119 | + "passwords": "<redacted>", |
| 120 | + "client_secrets": "<redacted>", |
| 121 | + "access_tokens": "<redacted>", |
| 122 | + "caption_max_tokens": 77, |
| 123 | + "text_chunk_overlap_tokens": 12, |
| 124 | + "tokenizer_model": "model-name", |
| 125 | + } |
| 126 | + |
| 127 | + |
| 128 | +def test_text_artifact_writes_are_classified(tmp_path): |
| 129 | + with pytest.raises(HarnessRunError) as log_error: |
| 130 | + append_text(tmp_path, "log line") |
| 131 | + with pytest.raises(HarnessRunError) as trec_error: |
| 132 | + _write_trec_run(tmp_path, {"query": {"document": 1.0}}) |
| 133 | + |
| 134 | + assert log_error.value.exit_code == EXIT_ARTIFACT_WRITE_FAILURE |
| 135 | + assert trec_error.value.exit_code == EXIT_ARTIFACT_WRITE_FAILURE |
| 136 | + |
| 137 | + |
94 | 138 | def test_invalid_run_config_preserves_existing_artifacts(tmp_path): |
95 | 139 | (tmp_path / "results.json").write_text('{"old": true}', encoding="utf-8") |
96 | 140 | (tmp_path / "lancedb").mkdir() |
@@ -222,6 +266,35 @@ def fail_writer(**kwargs): |
222 | 266 | assert error.value.failure.message == "OSError: artifact directory unavailable" |
223 | 267 |
|
224 | 268 |
|
| 269 | +def test_run_benchmark_preserves_run_log_write_failure(monkeypatch, tmp_path): |
| 270 | + import nemo_retriever.harness.execution as execution |
| 271 | + from nemo_retriever.harness.json_io import artifact_write_error |
| 272 | + |
| 273 | + class FakeIngestPlan: |
| 274 | + documents = () |
| 275 | + |
| 276 | + @contextmanager |
| 277 | + def fail_log_capture(*args, **kwargs): |
| 278 | + raise artifact_write_error(OSError("run log unavailable")) |
| 279 | + yield |
| 280 | + |
| 281 | + monkeypatch.setattr(execution, "resolve_ingest_plan", lambda request: FakeIngestPlan()) |
| 282 | + monkeypatch.setattr(execution, "run_ingest_workflow", lambda plan, dry_run: {}) |
| 283 | + monkeypatch.setattr(execution, "resolve_query_plan", lambda request: object()) |
| 284 | + monkeypatch.setattr(execution, "query_plan_payload", lambda plan: {}) |
| 285 | + monkeypatch.setattr(execution, "capture_output_to_log", fail_log_capture) |
| 286 | + |
| 287 | + outcome = run_benchmark( |
| 288 | + "jp20_smoke", |
| 289 | + output_dir=str(tmp_path / "run"), |
| 290 | + overrides=(f'dataset.path="{tmp_path}"',), |
| 291 | + ) |
| 292 | + |
| 293 | + assert outcome.exit_code == EXIT_ARTIFACT_WRITE_FAILURE |
| 294 | + assert outcome.results["failure"]["failure_reason"] == "artifact_write_failed" |
| 295 | + assert outcome.results["failure"]["message"] == "OSError: run log unavailable" |
| 296 | + |
| 297 | + |
225 | 298 | def test_run_benchmark_keeps_non_write_failures_internal(monkeypatch, tmp_path): |
226 | 299 | import nemo_retriever.harness.execution as execution |
227 | 300 |
|
|
0 commit comments