Files
signal-platform/tests/unit/test_ingestion_service.py
T
dennisthiessen 20a1c143f3
Deploy / lint (push) Successful in 8s
Deploy / test (push) Successful in 1m25s
Deploy / deploy (push) Successful in 46s
fix: surface empty OHLCV fetch as a warning, not success
Fetching a symbol the provider doesn't cover (e.g. RHM/Rheinmetall — Alpaca
serves US listings only) returned 0 bars but reported "complete · Successfully
ingested 0 records", which the UI showed as green success.

fetch_and_ingest now returns a distinct `no_data` status when the provider
returns nothing AND the ticker has no history (vs. "already up to date" when bars
exist). The fetch endpoint maps it to a `warning` source status, and the fetch
toast renders it as ⚠ with the provider message instead of success.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-28 19:27:41 +02:00

63 lines
2.1 KiB
Python

"""Tests for the ingestion service — honest reporting of empty provider fetches."""
from __future__ import annotations
from datetime import date, timedelta
import pytest
from app.models.ticker import Ticker
from app.providers.protocol import OHLCVData
from app.services import ingestion_service as svc
from tests.conftest import MockMarketDataProvider, _test_session_factory # type: ignore
@pytest.fixture
async def session():
async with _test_session_factory() as s:
yield s
async def _add_ticker(session, symbol: str) -> None:
session.add(Ticker(symbol=symbol))
await session.commit()
def _bars(symbol: str, n: int) -> list[OHLCVData]:
today = date.today()
return [
OHLCVData(ticker=symbol, date=today - timedelta(days=i),
open=100.0, high=101.0, low=99.0, close=100.0, volume=1000)
for i in range(n)
]
async def test_empty_fetch_on_new_ticker_reports_no_data(session):
# A non-US symbol (e.g. RHM/Rheinmetall) Alpaca doesn't cover → empty bars.
# This must NOT report success; it surfaces as no_data.
await _add_ticker(session, "RHM")
result = await svc.fetch_and_ingest(session, MockMarketDataProvider(ohlcv_data=[]), "RHM")
assert result.status == "no_data"
assert result.records_ingested == 0
assert "provider" in (result.message or "").lower()
async def test_happy_path_ingests_bars(session):
await _add_ticker(session, "AAA")
result = await svc.fetch_and_ingest(session, MockMarketDataProvider(ohlcv_data=_bars("AAA", 3)), "AAA")
assert result.status == "complete"
assert result.records_ingested == 3
async def test_empty_fetch_with_existing_history_is_up_to_date(session):
# Covered ticker, just no new bars in the window → complete, not no_data.
await _add_ticker(session, "BBB")
await svc.fetch_and_ingest(session, MockMarketDataProvider(ohlcv_data=_bars("BBB", 2)), "BBB")
result = await svc.fetch_and_ingest(session, MockMarketDataProvider(ohlcv_data=[]), "BBB")
assert result.status == "complete"
assert result.records_ingested == 0