import numpy as np
import pytest
from astropy import units as u
from astrora._core import Epoch
from astrora.bodies import Earth
class TestUnitsModuleComprehensive:
def test_to_si_velocity(self):
from astrora.units import to_si_velocity
result = to_si_velocity(7500)
assert result == 7500
v_kms = 7.5 * (u.km / u.s)
result = to_si_velocity(v_kms)
assert abs(result - 7500) < 1e-6
v_array = np.array([1000, 2000, 3000])
result = to_si_velocity(v_array)
assert np.allclose(result, v_array)
def test_to_si_angle(self):
from astrora.units import to_si_angle
result = to_si_angle(np.pi)
assert result == np.pi
angle_deg = 180 * u.deg
result = to_si_angle(angle_deg)
assert abs(result - np.pi) < 1e-10
angles = np.array([0, np.pi / 2, np.pi])
result = to_si_angle(angles)
assert np.allclose(result, angles)
def test_to_si_time(self):
from astrora.units import to_si_time
result = to_si_time(3600)
assert result == 3600
t_hours = 1 * u.hour
result = to_si_time(t_hours)
assert abs(result - 3600) < 1e-6
times = np.array([60, 120, 180])
result = to_si_time(times)
assert np.allclose(result, times)
def test_to_dimensionless(self):
from astrora.units import to_dimensionless
result = to_dimensionless(0.5)
assert result == 0.5
q = 0.7 * u.dimensionless_unscaled
result = to_dimensionless(q)
assert abs(result - 0.7) < 1e-10
def test_to_si_length(self):
from astrora.units import to_si_length
result = to_si_length(7000000)
assert result == 7000000
d_km = 7000 * u.km
result = to_si_length(d_km)
assert abs(result - 7000000) < 1
def test_to_si_position(self):
from astrora.units import to_si_position
pos = np.array([7000e3, 0, 0])
result = to_si_position(pos)
assert np.allclose(result, pos)
pos_km = np.array([7000, 0, 0]) * u.km
result = to_si_position(pos_km)
assert np.allclose(result, [7000e3, 0, 0])
def test_as_quantity_functions(self):
from astrora.units import as_quantity_angle, as_quantity_length, as_quantity_velocity
length_q = as_quantity_length(7000e3) assert length_q.unit == u.km
assert abs(length_q.value - 7000) < 0.1
vel_q = as_quantity_velocity(7546) assert vel_q.unit == (u.km / u.s)
assert abs(vel_q.value - 7.546) < 0.001
angle_q = as_quantity_angle(np.pi / 2) assert angle_q.unit == u.rad
assert abs(angle_q.value - np.pi / 2) < 1e-10
class TestCoordinatesModuleComprehensive:
def test_check_astropy_function(self):
from astrora.coordinates import _check_astropy
_check_astropy()
def test_coordinate_frame_classes(self):
from astrora.coordinates import AstroraGCRS, AstroraICRS, AstroraITRS
assert AstroraICRS is not None
assert AstroraGCRS is not None
assert AstroraITRS is not None
assert callable(AstroraICRS)
assert callable(AstroraGCRS)
assert callable(AstroraITRS)
def test_astropy_integration_functions(self):
try:
from astropy.time import Time
from astrora.coordinates import to_astropy_coord
r = np.array([7000e3, 0, 0])
v = np.array([0, 7546, 0])
obstime = Time("2025-01-01T00:00:00")
assert callable(to_astropy_coord)
except ImportError:
pytest.skip("Astropy coordinate integration not available")
class TestManeuverModuleComprehensive:
def test_maneuver_creation(self):
from astrora.maneuver import Maneuver
dv = np.array([100, 0, 0]) maneuver = Maneuver((0, dv))
assert maneuver is not None
assert len(maneuver.impulses) == 1
maneuver2 = Maneuver((0, dv), (3600, -dv))
assert len(maneuver2.impulses) == 2
def test_maneuver_from_hohmann_direct(self):
try:
from astrora._core import hohmann_transfer
r_leo = 7000e3 r_geo = 42164e3 mu = Earth.mu
result = hohmann_transfer(r_leo, r_geo, mu)
assert isinstance(result, dict)
assert len(result) > 0
except ImportError:
pytest.skip("Rust _core module not available")
def test_maneuver_from_bielliptic_direct(self):
try:
from astrora._core import bielliptic_transfer
r_i = 7000e3 r_f = 42164e3 r_b = 80000e3 mu = Earth.mu
try:
result = bielliptic_transfer(r_i, r_b, r_f, mu)
assert isinstance(result, dict)
assert len(result) > 0
except ValueError as e:
assert "Invalid parameter" in str(e)
except ImportError:
pytest.skip("Rust _core module not available")
class TestTimeModuleComprehensive:
def test_epoch_to_astropy_time(self):
try:
from astrora._core import Epoch
from astrora.time import epoch_to_astropy_time
epoch = Epoch.from_midnight_utc(2025, 1, 1)
astropy_time = epoch_to_astropy_time(epoch)
assert astropy_time is not None
except ImportError:
pytest.skip("Astropy Time integration not available")
def test_astropy_time_to_epoch(self):
try:
from astropy.time import Time
from astrora.time import astropy_time_to_epoch
t = Time("2025-01-01T00:00:00", scale="utc")
epoch = astropy_time_to_epoch(t)
assert epoch is not None
except ImportError:
pytest.skip("Astropy Time integration not available")
def test_to_epoch_function(self):
from astrora.time import to_epoch
result = to_epoch(None)
assert result is None
epoch = Epoch.from_midnight_utc(2025, 1, 1)
result = to_epoch(epoch)
assert result is epoch
def test_to_astropy_time_function(self):
try:
from astrora._core import Epoch
from astrora.time import to_astropy_time
epoch = Epoch.from_midnight_utc(2025, 1, 1)
astropy_time = to_astropy_time(epoch)
assert astropy_time is not None
except ImportError:
pytest.skip("Astropy Time integration not available")
def test_epoch_direct_usage(self):
epoch = Epoch.from_midnight_utc(2025, 6, 15)
assert epoch is not None
assert hasattr(epoch, "jd_utc") or hasattr(epoch, "jd_tt")
jd = epoch.jd_utc
assert jd > 0
class TestUtilModuleComprehensive:
def test_time_range_function(self):
from astropy.time import Time
from astrora.util import time_range
start_time = Time("2025-01-01T00:00:00")
end_time = Time("2025-01-02T00:00:00")
times = time_range(start_time, periods=100, end=end_time)
assert len(times) == 100
assert times[0].jd == start_time.jd
assert times[-1].jd == end_time.jd
def test_wrap_angle_function(self):
from astrora.util import wrap_angle
angle_deg = wrap_angle(270) assert -180 <= angle_deg < 180
angle_rad = wrap_angle(3 * np.pi * u.rad, limit=np.pi * u.rad)
assert angle_rad.value >= -np.pi
assert angle_rad.value < np.pi
def test_alinspace_function(self):
from astrora.util import alinspace
angles = alinspace(0, 2 * np.pi, num=100)
assert len(angles) == 100
assert abs(angles[0]) < 1e-10
assert abs(angles[-1] - 2 * np.pi) < 1e-6
def test_find_closest_value(self):
from astrora.util import find_closest_value
array = np.array([1, 3, 5, 7, 9])
value = 6
idx = find_closest_value(array, value)
assert idx == 2
class TestInitModule:
def test_version_attribute(self):
import astrora
assert hasattr(astrora, "__version__")
assert isinstance(astrora.__version__, str)
def test_core_imports(self):
import astrora
assert hasattr(astrora, "Orbit")
assert hasattr(astrora, "Maneuver")
assert hasattr(astrora, "bodies")
assert hasattr(astrora, "twobody")
from astrora import bodies
assert hasattr(bodies, "Earth")
def test_submodule_imports(self):
from astrora import bodies, maneuver, plotting, twobody
assert twobody is not None
assert bodies is not None
assert plotting is not None
assert maneuver is not None
if __name__ == "__main__":
pytest.main([__file__, "-v"])