from molid.pubchemproc import pubchem_client as pc
from molid.pubchemproc.fetch import fetch_molecule_data

class _Resp:
    def __init__(self, ok=True, status=200, payload=None, url="http://x", reason="OK"):
        self.ok = ok
        self.status_code = status
        self._payload = payload or {}
        self.url = url
        self.reason = reason
    def json(self): return self._payload
    def raise_for_status(self):
        if not (200 <= self.status_code < 300):
            from requests import HTTPError
            raise HTTPError(f"{self.status_code} {self.reason}", response=self)

def _mk_session(queue):
    # queue is list of _Resp that will be returned on successive .get calls
    class _S:
        def get(self, *a, **k):
            return queue.pop(0)
    return _S()

def test_fetch_prefers_synonym_cas(monkeypatch):
    # 1) resolve_to_cids → CID 280
    r1 = _Resp(payload={"IdentifierList": {"CID": [280]}})
    # 2) get_properties → no IUPAC yet
    r2 = _Resp(payload={"PropertyTable": {"Properties": [{"CID": 280, "Title": "CO2"}]}})
    # 3) get_pugview (IUPAC fallback)
    r3 = _Resp(payload={"Record": {"Section":[{"TOCHeading":"IUPAC Name","Information":[{"Value":{"StringWithMarkup":[{"String":"carbon dioxide"}]}}]}]}})
    # 4) get_synonyms → contains valid CAS
    r4 = _Resp(payload={"InformationList":{"Information":[{"Synonym":["124-38-9","foo"]}]}})
    # 5) get_xrefs_rn (won’t be used since synonym provided CAS)
    r5 = _Resp(payload={"InformationList":{"Information":[{"RN":["124-38-9"]}]}})
    sess = _mk_session([r1,r2,r3,r4,r5])
    monkeypatch.setattr(pc, "get_session", lambda: sess)

    recs = fetch_molecule_data("inchikey", "CURLTUGMZLYLDI-UHFFFAOYSA-N")
    assert recs and recs[0]["CID"] == 280
    assert recs[0]["IUPACName"] == "carbon dioxide"
    assert recs[0]["CAS"] == "124-38-9"

def test_resolve_404_soft_miss(monkeypatch):
    r1 = _Resp(ok=False, status=404, reason="NotFound")
    sess = _mk_session([r1])
    monkeypatch.setattr(pc, "get_session", lambda: sess)
    recs = fetch_molecule_data("name", "this-does-not-exist")
    assert recs == []
