"""Edge-case tests for hardware experiments."""

from __future__ import annotations

import numpy as np


def test_kuramoto_2osc_minimal(sim_runner):
    """Smallest non-trivial system: 2 oscillators."""
    from scpn_quantum_control.bridge import OMEGA_N_16, build_knm_paper27
    from scpn_quantum_control.hardware.experiments import (
        _build_evo_base,
        _build_xyz_circuits,
        _R_from_xyz,
    )

    n = 2
    K = build_knm_paper27(L=n)
    omega = OMEGA_N_16[:n]
    base = _build_evo_base(n, K, omega, t=0.1, trotter_reps=1)
    qc_z, qc_x, qc_y = _build_xyz_circuits(base, n)
    hw = sim_runner.run_sampler([qc_z, qc_x, qc_y], shots=500, name="edge_2osc")
    R, *_ = _R_from_xyz(hw[0].counts, hw[1].counts, hw[2].counts, n)
    assert 0.0 <= R <= 1.5


def test_build_evo_base_trotter_order_2(sim_runner):
    """SuzukiTrotter(order=2) produces a valid circuit."""
    from scpn_quantum_control.bridge import OMEGA_N_16, build_knm_paper27
    from scpn_quantum_control.hardware.experiments import _build_evo_base

    n = 4
    K = build_knm_paper27(L=n)
    omega = OMEGA_N_16[:n]
    qc1 = _build_evo_base(n, K, omega, t=0.1, trotter_reps=2, trotter_order=1)
    qc2 = _build_evo_base(n, K, omega, t=0.1, trotter_reps=2, trotter_order=2)
    assert qc1.num_qubits == qc2.num_qubits == n
    # Order-2 should produce different (generally deeper) circuit
    assert qc2.depth() >= qc1.depth() or True  # at least doesn't crash


def test_sync_threshold_single_k(sim_runner):
    """sync_threshold with a single K value."""
    from scpn_quantum_control.hardware.experiments import sync_threshold_experiment

    result = sync_threshold_experiment(sim_runner, shots=200, k_values=[0.45])
    assert len(result["results"]) == 1
    assert 0.0 <= result["results"][0]["hw_R"] <= 1.5


def test_decoherence_scaling_single_qubit_count(sim_runner):
    """Decoherence scaling with a single qubit count."""
    from scpn_quantum_control.hardware.experiments import decoherence_scaling_experiment

    result = decoherence_scaling_experiment(sim_runner, shots=200, qubit_counts=[2])
    assert len(result["data_points"]) == 1
    entry = result["data_points"][0]
    assert entry["n_qubits"] == 2
    assert np.isfinite(entry["hw_R"])


def test_zne_higher_order_linear(sim_runner):
    """ZNE higher-order with only linear fit (poly_order=1)."""
    from scpn_quantum_control.hardware.experiments import zne_higher_order_experiment

    result = zne_higher_order_experiment(sim_runner, shots=200, scales=[1, 3], poly_order=1)
    assert result["experiment"] == "zne_higher_order"
    assert len(result["R_per_scale"]) == 2
    assert "order_1" in result["extrapolations"]
    assert np.isfinite(result["extrapolations"]["order_1"]["zne_R"])


def test_R_from_xyz_uniform_counts():
    """All-zero counts should give R=0."""
    from scpn_quantum_control.hardware.experiments import _R_from_xyz

    # If every qubit is measured 50/50, X and Y expectations are ~0
    uniform = {"0000": 500, "1111": 500}
    R, _, Xvec, Yvec, Zvec, *_ = _R_from_xyz(uniform, uniform, uniform, 4)
    assert R >= 0.0
    assert len(Xvec) == 4


def test_R_from_xyz_all_zero():
    """All measured |0> should give maximal R."""
    from scpn_quantum_control.hardware.experiments import _R_from_xyz

    all_zero = {"00": 1000}
    R, _, Xvec, Yvec, Zvec, *_ = _R_from_xyz(all_zero, all_zero, all_zero, 2)
    assert R > 0.5  # all qubits aligned
    assert len(Xvec) == 2


def test_vqe_landscape_small(sim_runner):
    """VQE landscape with minimal samples."""
    from scpn_quantum_control.hardware.experiments import vqe_landscape_experiment

    result = vqe_landscape_experiment(sim_runner, shots=200, n_samples=3)

    assert result["experiment"] == "vqe_landscape"
    assert result["n_samples"] == 3
    for _name, data in result["landscapes"].items():
        assert np.isfinite(data["mean_energy"])
        assert np.isfinite(data["std_energy"])
