Initial commit. Stage one work done.

This commit is contained in:
2026-07-23 11:35:25 -05:00
parent a7be272917
commit dd3b0f9c45
37 changed files with 3429 additions and 171 deletions

84
tests/test_api.py Normal file
View File

@@ -0,0 +1,84 @@
"""API surface tests: registry integrity and the pylibxc-compatible shim."""
import numpy as np
import pytest
import funxc
from funxc.libxc_compat import LibXCFunctional
def test_registry_specs_wellformed():
for fid, spec in funxc.REGISTRY.items():
assert spec.id == fid
assert spec.family in ("lda", "gga", "mgga")
assert spec.kind in ("x", "c", "xc", "k")
assert spec.libxc_id > 0
assert spec.kernel_fn is not None
assert spec.doi
def test_get_spec_is_case_insensitive():
assert funxc.get_spec("gga_x_pbe") is funxc.get_spec("GGA_X_PBE")
assert funxc.get_spec("XC_GGA_X_PBE") is funxc.get_spec("GGA_X_PBE")
with pytest.raises(KeyError):
funxc.get_spec("GGA_X_DOES_NOT_EXIST")
def test_shim_polarized_shapes():
f = LibXCFunctional("gga_x_pbe", "polarized")
n = 4
rng = np.random.default_rng(0)
inp = {
"rho": rng.uniform(0.1, 1.0, (n, 2)),
"sigma": rng.uniform(0.0, 0.5, (n, 3)),
}
out = f.compute(inp)
assert out["zk"].shape == (n, 1)
assert out["vrho"].shape == (n, 2)
assert out["vsigma"].shape == (n, 3)
def test_shim_unpolarized_shapes_and_flat_input():
f = LibXCFunctional("lda_x", 1)
rho = np.linspace(0.1, 2.0, 5)
out = f.compute({"rho": rho})
assert out["zk"].shape == (5, 1)
assert out["vrho"].shape == (5, 1)
out_exc_only = f.compute({"rho": rho}, do_vxc=False)
assert set(out_exc_only) == {"zk"}
def test_shim_mgga_shapes():
f = LibXCFunctional("mgga_x_lta", "polarized")
n = 4
rng = np.random.default_rng(1)
inp = {
"rho": rng.uniform(0.1, 1.0, (n, 2)),
"sigma": rng.uniform(0.0, 0.5, (n, 3)),
"lapl": rng.uniform(-1.0, 1.0, (n, 2)),
"tau": rng.uniform(0.1, 1.0, (n, 2)),
}
out = f.compute(inp)
assert out["zk"].shape == (n, 1)
assert out["vrho"].shape == (n, 2)
assert out["vsigma"].shape == (n, 3)
assert out["vlapl"].shape == (n, 2)
assert out["vtau"].shape == (n, 2)
# LTA has no lapl dependence: vlapl must be exactly zero
assert np.all(out["vlapl"] == 0.0)
def test_shim_metadata():
f = LibXCFunctional("gga_c_lyp", "polarized")
assert f.get_number() == 131
assert f.get_family() == "gga"
def test_composition_blyp():
"""X and C functionals compose additively (BLYP = B88 + LYP)."""
rho = np.array([[0.4, 0.3]])
sigma = np.array([[0.02, 0.01, 0.015]])
b88 = funxc.functional("GGA_X_B88").exc(rho, sigma)
lyp = funxc.functional("GGA_C_LYP").exc(rho, sigma)
total = np.asarray(b88) + np.asarray(lyp)
assert np.all(np.isfinite(total)) and total[0] < 0