"""Anant Mishra, AM-RP-002. Synthetic offline reference; no sensor validation."""
from datetime import datetime
import json
import math
from pathlib import Path


def instant(text):
    if not isinstance(text, str):
        raise ValueError('timestamp must be a string')
    try:
        value = datetime.fromisoformat(text.replace('Z', '+00:00'))
    except ValueError as exc:
        raise ValueError('invalid timestamp') from exc
    if value.tzinfo is None or value.utcoffset() is None:
        raise ValueError('explicit UTC offset required')
    return value


def classify(record, as_of, max_age_seconds):
    """Classify one already-selected record; never select a history or dispatch work.

    State precedence: absent, after cutoff, unknown time, suspect, stale, current.
    Validate supplied records first. Exactly-at-limit age is accepted. A quality
    flag is an input assertion, not independently established sensor accuracy.
    """
    cutoff = instant(as_of)
    if type(max_age_seconds) not in (int, float) or (type(max_age_seconds) is float and not math.isfinite(max_age_seconds)) or max_age_seconds <= 0:
        raise ValueError('positive finite maximum age required')
    if record is None:
        return dict(state='missing', value=None, age_seconds=None, usable_for_current_decision=False)
    if not isinstance(record, dict) or not isinstance(record.get('asset'), str) or not record['asset']:
        raise ValueError('asset identity required')
    value = record.get('value')
    if type(value) not in (int, float) or (type(value) is float and not math.isfinite(value)) or not 0 <= value <= 100:
        raise ValueError('finite fill percentage in range 0..100 required')
    if record.get('time_origin') not in ('observed', 'unknown') or record.get('quality') not in ('accepted', 'suspect'):
        raise ValueError('declared time origin and quality required')
    receipt = instant(record.get('received_at'))
    observed = None if record.get('observed_at') is None else instant(record['observed_at'])
    if record['time_origin'] == 'observed' and observed is None:
        raise ValueError('observed time required for observed origin')
    if record['time_origin'] == 'observed' and observed > receipt:
        raise ValueError('observation after receipt violates this strict clock contract')
    age = None
    if receipt > cutoff:
        state = 'not_yet_received'
    elif record['time_origin'] == 'unknown':
        state = 'unknown_time'
    else:
        age = (cutoff - observed).total_seconds()
        state = 'suspect' if record['quality'] == 'suspect' else 'stale' if age > max_age_seconds else 'current'
    return dict(state=state, value=value, age_seconds=age, usable_for_current_decision=state == 'current')


if __name__ == '__main__':
    fixture = json.loads(Path(__file__).with_name('synthetic-observations.json').read_text())
    output = {row['case']: classify(row['record'], fixture['as_of'], fixture['max_age_seconds']) for row in fixture['cases']}
    print(json.dumps(output, indent=2))
