sidereon 3.0.0__tar.gz → 3.0.2__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {sidereon-3.0.0 → sidereon-3.0.2}/.github/workflows/release.yml +40 -4
- {sidereon-3.0.0 → sidereon-3.0.2}/CHANGELOG.md +21 -2
- {sidereon-3.0.0 → sidereon-3.0.2}/Cargo.lock +5 -5
- {sidereon-3.0.0 → sidereon-3.0.2}/Cargo.toml +4 -4
- {sidereon-3.0.0 → sidereon-3.0.2}/PKG-INFO +1 -1
- {sidereon-3.0.0 → sidereon-3.0.2}/THIRD-PARTY-NOTICES.md +4 -2
- {sidereon-3.0.0 → sidereon-3.0.2}/pyproject.toml +4 -4
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/__init__.py +1 -1
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/distribution.py +72 -3
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/distribution.pyi +4 -1
- {sidereon-3.0.0 → sidereon-3.0.2}/scripts/check-release.py +5 -3
- {sidereon-3.0.0 → sidereon-3.0.2}/scripts/core_source_identity.rs +7 -7
- sidereon-3.0.2/tests/fixtures/bodies/observe_de.bsp +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/core_goldens.json +1 -1
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/ppp_esbc.json +1 -1
- sidereon-3.0.2/tests/test_antex_public_equality.py +166 -0
- sidereon-3.0.2/tests/test_body_observe_reference.py +311 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_core_revision.py +38 -23
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_distribution_fallback.py +73 -0
- sidereon-3.0.2/tests/test_ionex_public_equality.py +135 -0
- sidereon-3.0.2/tests/test_misc_public_equality.py +162 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_observation_qc.py +93 -0
- sidereon-3.0.2/tests/test_precise_interpolant_public_values.py +98 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_release_guard.py +35 -34
- sidereon-3.0.2/tests/test_rinex_clock_equality.py +199 -0
- sidereon-3.0.2/tests/test_sp3_public_metadata.py +83 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/uv.lock +1 -1
- {sidereon-3.0.0 → sidereon-3.0.2}/.cargo/config.toml.disabled +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/.gitattributes +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/.github/workflows/ci.yml +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/.gitignore +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/COVERAGE.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/LICENSE +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/README.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/bench/README.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/bench/bench_fleet.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/docs/antex.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/docs/observations.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/docs/public-gnss-distribution-sources.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/docs/releasing.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/docs/rinex-clock.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/docs/sp3.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/docs/tdm.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/examples/clean_a_phone_track.ipynb +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/examples/static_occupation_vs_cors.ipynb +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/__init__.pyi +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/_compression.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/_exact_cache.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/_ingress.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/data.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/data.pyi +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/exact_cache.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/exact_cache.pyi +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/exact_sp3.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/exact_sp3.pyi +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/ntrip.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/ntrip.pyi +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/python/sidereon/py.typed +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/rust-toolchain.toml +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/scripts/coverage/bindmap.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/scripts/coverage/pubapi.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/scripts/coverage/render_coverage.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/scripts/smoke-release.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/almanac.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/angles.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/anomaly.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/antex.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/araim.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/atmosphere.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/bias.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/bodies.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/body_observe.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/broadcast_comparison.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/cdm.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/clock_stability.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/conjunction.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/constellation.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/core_error_detail.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/covariance.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/coverage.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/data_catalog.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/defaults.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/dgnss.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/doppler.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/elements.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/emission.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/ephemeris.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/equinoctial.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/error_metrics.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/estimation.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/events.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/exact_cache.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/exact_time.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/fallback.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/forces.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/format_diagnostics.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/frame_catalog.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/frames.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/fusion.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/geodesic.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/geodetic_time_series.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/geofence.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/geoid.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/geometry.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/geometry_quality.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/ils.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/iod.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/ionex.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/lambert.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/leap.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/least_squares.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/lib.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/lnav.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/marshal.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/nmea.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/normality.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/ntrip.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/observables.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/observation.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/oem.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/omm.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/opm.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/orbit_determination.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/ppp.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/ppp_corrections.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/products.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/propagation.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/qc.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/reduced_orbit.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/relative.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/reliability.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/rf.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/rinex.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/rinex_clock.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/rtcm.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/rtk.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/sbas_pl.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/sbas_ssr.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/scenario.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/sidereal.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/signal_analysis.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/sky.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/solve_error_detail.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/source_localization.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/space_weather.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/spk.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/spp.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/spp_error_detail.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/staleness.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/static_positioning.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/tca.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/tdm.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/terrain.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/terrain_store.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/tides.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/time_model_error.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/tle_fit_error_detail.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/tropo.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/src/unix_compress.rs +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/_helpers.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/_sp3_merge.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/README.md +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/antex/igs20_pasa_scoa_gps.atx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/antex/igs20_wettzell_trim.atx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/batch_fleet.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/cdm.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/clk/lossless/rinex_clock304_table_a17.clk +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/clk/lossless/rinex_clock304_table_a18.clk +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/clk/synthetic_rinex_clock.clk +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/conjunction.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/constellation/gps_ops_sample.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/constellation/navcen_forecast_cases.html +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/constellation/navcen_gps_sample.html +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/events_bodies_dop.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/format_diagnostics_inputs.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/frames_time.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/geodesic/geodtest_row.dat +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/geoid/egm2008_25_norcal_crop.bin +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/gnss_data/igs22376.sp3.Z.b64 +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/gnss_data/ncompress-current-b9-counter.Z.b64 +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/listings/aiub-iono-prd-20260923.csv +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/listings/gfz-ultra-w2430-20260804.html +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/nav/BRDC00GOP_R_20210010000_01D_MN.rnx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/nav/ESBC00DNK_R_20201770000_01D_MN.rnx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/nav/KMS300DNK_R_20221591000_01H_MN.rnx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/numerical_propagation.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/obs/ESBC00DNK_R_20201770000_01D_30S_MO_trim.crx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/obs/ESBC00DNK_R_20201770000_01D_30S_MO_trim.rnx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/obs/algo0010_2015001_v1_trim.crx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/obs/algo0010_2015001_v1_trim.rnx +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/omm.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/pass_finder.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/rf_link_budget.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/rtk_wtzr.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/scenario_base.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/sgp4_topocentric.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/sp3/IGS0OPSFIN_20261200945_02H30M_15M_ORB.SP3 +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/sp3-merge-input-v1.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/sp3-merge-report-v3.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/sp3_bodies.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/spk/horizons_eros_type21.bsp +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/tdm/annex_e_01.kvn +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/fixtures/tle_roundtrip.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/golden/sp3-terminal-record-v1.json +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_012_bindings.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_013_bindings.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_014_bindings.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_015_bindings.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_016_wave2_bindings.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_017_domain_exposure.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_018_domain_exposure.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_019_track.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_020_error_metrics.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_antex.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_antex_public_pcv_sample_fields.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_atmosphere.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_attested_open.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_batch.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_broadcast_comparison.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_broadcast_fallback.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_cdm.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_cdm_top_level.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_cdm_value_equality.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_codec_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_conjunction.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_constellation.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_constellation_fleet.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_core_defaults.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_core_public_api_parity.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_core_round3_surfaces.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_covariance.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_covariance_propagation.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_coverage.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_crinex.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_data.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_data_publication_resilience.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_dgnss.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_distribution.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_dop_at_epoch.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_dop_convention.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_doppler.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_dted_tile_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_egm96.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_elements.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_events_bodies_dop.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_exact_cache_atomicity.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_field_mode_bindings.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_forces.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_format_diagnostics.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_frames_time.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ftp_transport.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_fusion_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_geoid.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_geometry.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ils.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_import.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_inertial_mechanization.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ionex.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ionex_instant_queries.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ionex_policies.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ionosphere_nequick.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_klobuchar_native.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_lambert_iod.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_leap_seconds.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_least_squares.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_lnav.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_moving_baseline.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_new_core_api.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_next_issue_due.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_nmea_finish_output.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ntrip.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_numerical.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_obs_policies.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_observables.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_observables_broadcast.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_observables_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_observation.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_observe_batch.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_oem.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_oem_full_dto.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_omm.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_omm_full_dto.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_opm.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_opm_full_dto.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_parity_gaps.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_parse_tle_file.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_passes.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ppp.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ppp_corrections.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_ppp_range_corrections.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_precise_samples.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_precise_samples_errors.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_propagation.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_qc.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_reduced_orbit.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_reduced_orbit_piecewise.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_residual_stats.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rf.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rinex_clock.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rinex_clock_header_field_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rinex_clock_lossless.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rinex_nav.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rinex_obs.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rtcm.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rtk.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_rtk_unresolved_carriers.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sbas_decoded_lists.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sbas_unassigned_mask.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_scenario_external_sources.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sky.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_bodies.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_catalog_exact.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_clock_reference.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_interpolation_policy.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_merge.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_merge_coverage.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_merge_per_epoch_provenance.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_terminal_record.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_window_continuity.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_sp3_write_and_records.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_spk.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_spp.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_spp_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_spp_glonass.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_spp_robustness.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_staleness.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_stub_accuracy.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_tca.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_tdm_policies.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_terrain_unknown_elevation.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_tides.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_time_model_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_time_offset_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_tle_fit.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_tle_roundtrip.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_tropo.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_unix_compress.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_visible_ground_track.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/tests/test_weather_terrain_error_details.py +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/third_party_licenses/ERFA-BSD-3-Clause.txt +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/third_party_licenses/IERS-CONVENTIONS-SOFTWARE-LICENSE.txt +0 -0
- {sidereon-3.0.0 → sidereon-3.0.2}/third_party_licenses/SciPy-BSD-3-Clause.txt +0 -0
- {sidereon-3.0.0/third_party_source/sidereon-core-3.0.0 → sidereon-3.0.2/third_party_source/sidereon-core-3.0.2}/tides/mod.rs +0 -0
- {sidereon-3.0.0/third_party_source/sidereon-core-3.0.0 → sidereon-3.0.2/third_party_source/sidereon-core-3.0.2}/tides/ocean.rs +0 -0
- {sidereon-3.0.0/third_party_source/sidereon-core-3.0.0 → sidereon-3.0.2/third_party_source/sidereon-core-3.0.2}/tides/pole.rs +0 -0
|
@@ -153,10 +153,10 @@ jobs:
|
|
|
153
153
|
done
|
|
154
154
|
for source in mod.rs ocean.rs pole.rs; do
|
|
155
155
|
unzip -p "$wheel" \
|
|
156
|
-
"third_party_source/sidereon-core-3.0.
|
|
156
|
+
"third_party_source/sidereon-core-3.0.2/tides/$source" \
|
|
157
157
|
>"$RUNNER_TEMP/$source"
|
|
158
158
|
cmp "$RUNNER_TEMP/$source" \
|
|
159
|
-
"third_party_source/sidereon-core-3.0.
|
|
159
|
+
"third_party_source/sidereon-core-3.0.2/tides/$source"
|
|
160
160
|
done
|
|
161
161
|
done
|
|
162
162
|
notice="$RUNNER_TEMP/sdist.notices"
|
|
@@ -173,10 +173,10 @@ jobs:
|
|
|
173
173
|
done
|
|
174
174
|
for source in mod.rs ocean.rs pole.rs; do
|
|
175
175
|
tar -xOf "${sdists[0]}" --wildcards \
|
|
176
|
-
"*/third_party_source/sidereon-core-3.0.
|
|
176
|
+
"*/third_party_source/sidereon-core-3.0.2/tides/$source" \
|
|
177
177
|
>"$RUNNER_TEMP/sdist-$source"
|
|
178
178
|
cmp "$RUNNER_TEMP/sdist-$source" \
|
|
179
|
-
"third_party_source/sidereon-core-3.0.
|
|
179
|
+
"third_party_source/sidereon-core-3.0.2/tides/$source"
|
|
180
180
|
done
|
|
181
181
|
- name: Smoke-test installed x86_64 Linux wheel
|
|
182
182
|
shell: bash
|
|
@@ -218,3 +218,39 @@ jobs:
|
|
|
218
218
|
uses: pypa/gh-action-pypi-publish@release/v1
|
|
219
219
|
with:
|
|
220
220
|
attestations: true
|
|
221
|
+
|
|
222
|
+
public-consumer:
|
|
223
|
+
name: Verify public PyPI consumer
|
|
224
|
+
runs-on: ubuntu-24.04-arm
|
|
225
|
+
timeout-minutes: 15
|
|
226
|
+
needs: publish
|
|
227
|
+
steps:
|
|
228
|
+
- uses: actions/checkout@v4
|
|
229
|
+
- uses: actions/setup-python@v5
|
|
230
|
+
with:
|
|
231
|
+
python-version: '3.12'
|
|
232
|
+
- name: Install exact published wheel and exercise public references
|
|
233
|
+
shell: bash
|
|
234
|
+
run: |
|
|
235
|
+
set -euo pipefail
|
|
236
|
+
version="${GITHUB_REF_NAME#v}"
|
|
237
|
+
scratch="$(mktemp -d)"
|
|
238
|
+
trap 'rm -rf "$scratch"' EXIT
|
|
239
|
+
python -m venv "$scratch/venv"
|
|
240
|
+
installed=false
|
|
241
|
+
for attempt in 1 2 3 4 5 6; do
|
|
242
|
+
if "$scratch/venv/bin/python" -m pip install --only-binary=sidereon "sidereon==$version" pytest; then
|
|
243
|
+
installed=true
|
|
244
|
+
break
|
|
245
|
+
fi
|
|
246
|
+
sleep 10
|
|
247
|
+
done
|
|
248
|
+
test "$installed" = true
|
|
249
|
+
mkdir -p "$scratch/tests/fixtures/bodies"
|
|
250
|
+
cp scripts/smoke-release.py "$scratch/smoke-release.py"
|
|
251
|
+
cp tests/test_body_observe_reference.py "$scratch/tests/"
|
|
252
|
+
cp tests/fixtures/bodies/observe_de.bsp "$scratch/tests/fixtures/bodies/"
|
|
253
|
+
cd "$scratch"
|
|
254
|
+
unset PYTHONPATH
|
|
255
|
+
SIDEREON_EXPECTED_VERSION="$version" "$scratch/venv/bin/python" -I smoke-release.py
|
|
256
|
+
"$scratch/venv/bin/python" -I -m pytest -q tests/test_body_observe_reference.py
|
|
@@ -2,7 +2,26 @@
|
|
|
2
2
|
|
|
3
3
|
All notable changes to the Sidereon Python interface are documented here.
|
|
4
4
|
|
|
5
|
-
## [
|
|
5
|
+
## [Unreleased]
|
|
6
|
+
|
|
7
|
+
## [3.0.2] - 2026-10-05
|
|
8
|
+
|
|
9
|
+
### Changed
|
|
10
|
+
|
|
11
|
+
- Use the coordinated 3.0.2 Rust engine release, including NaN-safe Portable ULP comparisons.
|
|
12
|
+
- Retain the existing Python API while keeping package versions and shipped source disclosures aligned across all libraries.
|
|
13
|
+
|
|
14
|
+
## [3.0.1] - 2026-10-04
|
|
15
|
+
|
|
16
|
+
### Added
|
|
17
|
+
|
|
18
|
+
- Opt-in `acquire(..., http_client_exception_diagnostics=callback)` reports
|
|
19
|
+
the class and bounded module/function metadata of unexpected exceptions
|
|
20
|
+
from caller-supplied HTTP transports. Diagnostics omit messages, arguments,
|
|
21
|
+
URLs and request/response data; observer failures leave the original terminal
|
|
22
|
+
exception unchanged.
|
|
23
|
+
|
|
24
|
+
## [3.0.0] - 2026-10-04
|
|
6
25
|
|
|
7
26
|
### Added
|
|
8
27
|
|
|
@@ -70,7 +89,7 @@ All notable changes to the Sidereon Python interface are documented here.
|
|
|
70
89
|
- `Sp3MergeOptions` no longer refuses a `target_epoch_interval_s` that is not a whole number of seconds. The merge takes any interval a whole number of 10-nanosecond ticks states and the core refuses the rest; the persisted merge-input identity still binds whole seconds only, and the core refuses a fractional interval there.
|
|
71
90
|
- **Breaking.** The robust (Huber) reweighting runs until it settles: `SPP_DEFAULT_ROBUST_MAX_OUTER`, the default `SppRobustConfig.max_outer`, is 100 instead of 5, a safeguard rather than a working budget. A reweighting that cycles stops with the new status `outer_oscillation`.
|
|
72
91
|
|
|
73
|
-
- Engine update: sidereon and sidereon-core 3.0.0, at core revision `
|
|
92
|
+
- Engine update: sidereon and sidereon-core 3.0.0, at core revision `e2fb3dfdc392d23087ed8aa1ee028a0056b4021b`. Every core breaking change below reaches Python as the core states it; the core CHANGELOG gives the reason for each.
|
|
74
93
|
- **Breaking.** `NmeaDiagnostics.skips` and `warnings` are lists of `FormatSkip` and `FormatWarning` instead of strings, and `NmeaDiagnostics` is `FormatDiagnostics`.
|
|
75
94
|
- **Breaking.** `BiasSet.code_osb_seconds`, `phase_osb_cycles`, `code_dsb_seconds` and `code_bias_model_m` return a `BiasLookup` whose `status` names the outcome (`available`, `absent`, `unsupported_scale`, `ambiguous`, `carrier_frequency_required`, `invalid_carrier_frequency`, `carrier_frequency_unknown`, `undefined_slope_reference`, `invalid_epoch`) instead of a float or `None`. A phase bias stated in nanoseconds needs `carrier_hz`. `BiasSet.time_scale` is `None` for a product with no usable time scale, and a lookup on such a product needs `time_scale`. `BiasRecord.is_phase` follows the observable code, so a phase bias stated in nanoseconds is a phase bias.
|
|
76
95
|
- **Breaking.** The Bias-SINEX readers are strict by default and raise `ValueError` for a file that departs from Bias-SINEX 1.00 or states another version; `BiasReadPolicy.LENIENT` reads it and reports each departure in `BiasSet.notices`. A CODE DCB title whose time-system label names no known scale is refused likewise.
|
|
@@ -611,9 +611,9 @@ checksum = "f8fadd59c855ef2080decdef8ff161eb6661b86933c9d82e5ba29dc602a55aba"
|
|
|
611
611
|
|
|
612
612
|
[[package]]
|
|
613
613
|
name = "sidereon"
|
|
614
|
-
version = "3.0.
|
|
614
|
+
version = "3.0.2"
|
|
615
615
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
616
|
-
checksum = "
|
|
616
|
+
checksum = "8a424bd9dea809b4cf2b816c27aa129a3e437b95139389ecbc94416aeee27951"
|
|
617
617
|
dependencies = [
|
|
618
618
|
"crc32fast",
|
|
619
619
|
"flate2",
|
|
@@ -622,9 +622,9 @@ dependencies = [
|
|
|
622
622
|
|
|
623
623
|
[[package]]
|
|
624
624
|
name = "sidereon-core"
|
|
625
|
-
version = "3.0.
|
|
625
|
+
version = "3.0.2"
|
|
626
626
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
627
|
-
checksum = "
|
|
627
|
+
checksum = "29f682ba7089c512d83cfea712bdc6ce9caac5e46d9acbeca7a1b2151ad8ee5b"
|
|
628
628
|
dependencies = [
|
|
629
629
|
"approx",
|
|
630
630
|
"cc",
|
|
@@ -646,7 +646,7 @@ dependencies = [
|
|
|
646
646
|
|
|
647
647
|
[[package]]
|
|
648
648
|
name = "sidereon-py"
|
|
649
|
-
version = "3.0.
|
|
649
|
+
version = "3.0.2"
|
|
650
650
|
dependencies = [
|
|
651
651
|
"nalgebra",
|
|
652
652
|
"numpy",
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[package]
|
|
2
2
|
name = "sidereon-py"
|
|
3
|
-
version = "3.0.
|
|
3
|
+
version = "3.0.2"
|
|
4
4
|
authors = []
|
|
5
5
|
edition = "2021"
|
|
6
6
|
description = "Python (PyO3) bindings over the sidereon ergonomic API: SP3 loading and SPP/RTK/PPP positioning solves"
|
|
@@ -25,12 +25,12 @@ exact-cache-test-failpoints = ["sidereon-core/exact-cache-test-failpoints"]
|
|
|
25
25
|
# The thin ergonomic engine surface this binding marshals to. No modeling logic
|
|
26
26
|
# lives here: every solve delegates to a `sidereon` entry point, which in turn
|
|
27
27
|
# delegates to `sidereon-core`.
|
|
28
|
-
sidereon =
|
|
29
|
-
sidereon-core = { version = "=3.0.
|
|
28
|
+
sidereon = "=3.0.2"
|
|
29
|
+
sidereon-core = { version = "=3.0.2", features = ["mmap"] }
|
|
30
30
|
# The standalone general-purpose trust-region least-squares solver: a data-driven
|
|
31
31
|
# `least_squares` whose residual and Jacobian are evaluated entirely in Rust, so
|
|
32
32
|
# no per-iteration Python callback is paid.
|
|
33
|
-
trust-region-least-squares = "0.11.0"
|
|
33
|
+
trust-region-least-squares = "=0.11.0"
|
|
34
34
|
pyo3 = { version = "0.25", features = ["abi3-py39"] }
|
|
35
35
|
# Zero-copy ndarray marshalling so a batched propagate/look-angle call crosses
|
|
36
36
|
# the FFI boundary once (1-D epochs in, 2-D states / 1-D angles out) instead of a
|
|
@@ -330,8 +330,10 @@ endorsed by the IERS Conventions Center. The Rust source describes the origin,
|
|
|
330
330
|
the renamed routines, and the differences from the Fortran implementation.
|
|
331
331
|
The complete non-test tide source distributed in the compiled extension is
|
|
332
332
|
included under
|
|
333
|
-
`third_party_source/sidereon-core-3.0.
|
|
334
|
-
distributions.
|
|
333
|
+
`third_party_source/sidereon-core-3.0.2/tides/` in wheels and source
|
|
334
|
+
distributions. These files match sidereon-core 3.0.2 at commit 8694648892d8ab065d94014e2e21d6cd5054818e.
|
|
335
|
+
Source: [sidereon-core tides at the pinned commit](https://github.com/neilberkman/sidereon/tree/8694648892d8ab065d94014e2e21d6cd5054818e/crates/sidereon-core/src/tides).
|
|
336
|
+
The authoritative original is available from:
|
|
335
337
|
|
|
336
338
|
<https://iers-conventions.obspm.fr/content/chapter7/software/dehanttideinel/DEHANTTIDEINEL.F>
|
|
337
339
|
|
|
@@ -4,7 +4,7 @@ build-backend = "maturin"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "sidereon"
|
|
7
|
-
version = "3.0.
|
|
7
|
+
version = "3.0.2"
|
|
8
8
|
description = "Python (PyO3) bindings over the sidereon engine: SP3 loading and SPP/RTK/PPP positioning solves"
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
license = { text = "MIT" }
|
|
@@ -82,7 +82,7 @@ include = [
|
|
|
82
82
|
"third_party_licenses/ERFA-BSD-3-Clause.txt",
|
|
83
83
|
"third_party_licenses/IERS-CONVENTIONS-SOFTWARE-LICENSE.txt",
|
|
84
84
|
"third_party_licenses/SciPy-BSD-3-Clause.txt",
|
|
85
|
-
"third_party_source/sidereon-core-3.0.
|
|
86
|
-
"third_party_source/sidereon-core-3.0.
|
|
87
|
-
"third_party_source/sidereon-core-3.0.
|
|
85
|
+
"third_party_source/sidereon-core-3.0.2/tides/mod.rs",
|
|
86
|
+
"third_party_source/sidereon-core-3.0.2/tides/ocean.rs",
|
|
87
|
+
"third_party_source/sidereon-core-3.0.2/tides/pole.rs",
|
|
88
88
|
]
|
|
@@ -16,10 +16,11 @@ import json
|
|
|
16
16
|
import netrc
|
|
17
17
|
import os
|
|
18
18
|
import time
|
|
19
|
+
from collections import deque
|
|
19
20
|
from dataclasses import asdict, dataclass, field, replace
|
|
20
21
|
from enum import Enum
|
|
21
22
|
from pathlib import Path
|
|
22
|
-
from typing import Mapping, Optional, Sequence, Tuple, Union, cast
|
|
23
|
+
from typing import Callable, Mapping, Optional, Sequence, Tuple, Union, cast
|
|
23
24
|
from urllib.parse import urljoin, urlsplit, urlunsplit
|
|
24
25
|
|
|
25
26
|
import httpx
|
|
@@ -660,8 +661,19 @@ def acquire(
|
|
|
660
661
|
max_archive_bytes: int = _DEFAULT_MAX_ARCHIVE_BYTES,
|
|
661
662
|
max_product_bytes: int = _DEFAULT_MAX_PRODUCT_BYTES,
|
|
662
663
|
http_client: Optional[httpx.Client] = None,
|
|
664
|
+
http_client_exception_diagnostics: Optional[
|
|
665
|
+
Callable[[Mapping[str, object]], None]
|
|
666
|
+
] = None,
|
|
663
667
|
) -> AcquiredProduct:
|
|
664
|
-
"""Acquire
|
|
668
|
+
"""Acquire an exact product from the ordered distributors.
|
|
669
|
+
|
|
670
|
+
When a caller-supplied HTTP transport raises an unexpected exception, the
|
|
671
|
+
optional diagnostic callback receives only the exception class, a client
|
|
672
|
+
callsite, and up to eight module/function/arity frames. Exception messages,
|
|
673
|
+
arguments, URLs, headers, and response bodies are omitted. The original
|
|
674
|
+
exception is re-raised unchanged, and callback failures are ignored.
|
|
675
|
+
Payload keys are ``exception_class``, ``client_callsite`` and ``stack_frames``.
|
|
676
|
+
"""
|
|
665
677
|
return _acquire_impl(
|
|
666
678
|
exact_request,
|
|
667
679
|
cache_dir=cache_dir,
|
|
@@ -675,6 +687,7 @@ def acquire(
|
|
|
675
687
|
max_archive_bytes=max_archive_bytes,
|
|
676
688
|
max_product_bytes=max_product_bytes,
|
|
677
689
|
http_client=http_client,
|
|
690
|
+
http_client_exception_diagnostics=http_client_exception_diagnostics,
|
|
678
691
|
direct_location=None,
|
|
679
692
|
)
|
|
680
693
|
|
|
@@ -706,6 +719,9 @@ def _acquire_impl(
|
|
|
706
719
|
max_archive_bytes: int = _DEFAULT_MAX_ARCHIVE_BYTES,
|
|
707
720
|
max_product_bytes: int = _DEFAULT_MAX_PRODUCT_BYTES,
|
|
708
721
|
http_client: Optional[httpx.Client] = None,
|
|
722
|
+
http_client_exception_diagnostics: Optional[
|
|
723
|
+
Callable[[Mapping[str, object]], None]
|
|
724
|
+
] = None,
|
|
709
725
|
direct_location: Optional[tuple[str, str]],
|
|
710
726
|
) -> AcquiredProduct:
|
|
711
727
|
_validate_requested_identity(exact_request.identity)
|
|
@@ -779,6 +795,7 @@ def _acquire_impl(
|
|
|
779
795
|
max_archive_bytes,
|
|
780
796
|
max_product_bytes,
|
|
781
797
|
http_client,
|
|
798
|
+
http_client_exception_diagnostics,
|
|
782
799
|
attempts,
|
|
783
800
|
exact_cache,
|
|
784
801
|
direct_location,
|
|
@@ -850,6 +867,7 @@ def _acquire_one(
|
|
|
850
867
|
max_archive_bytes: int,
|
|
851
868
|
max_product_bytes: int,
|
|
852
869
|
http_client: Optional[httpx.Client],
|
|
870
|
+
http_client_exception_diagnostics: Optional[Callable[[Mapping[str, object]], None]],
|
|
853
871
|
attempts: Sequence[SourceFailure],
|
|
854
872
|
exact_cache: _exact_cache.ExactCache,
|
|
855
873
|
direct_location: Optional[tuple[str, str]],
|
|
@@ -871,6 +889,7 @@ def _acquire_one(
|
|
|
871
889
|
backoff_s,
|
|
872
890
|
max_archive_bytes,
|
|
873
891
|
http_client,
|
|
892
|
+
http_client_exception_diagnostics,
|
|
874
893
|
)
|
|
875
894
|
archive = download.archive
|
|
876
895
|
elif source is DistributionSource.NASA_CDDIS:
|
|
@@ -885,6 +904,7 @@ def _acquire_one(
|
|
|
885
904
|
backoff_s,
|
|
886
905
|
max_archive_bytes,
|
|
887
906
|
http_client,
|
|
907
|
+
http_client_exception_diagnostics,
|
|
888
908
|
)
|
|
889
909
|
archive = download.archive
|
|
890
910
|
elif source is DistributionSource.LOCAL_FILE:
|
|
@@ -1081,6 +1101,7 @@ def _download_http(
|
|
|
1081
1101
|
backoff_s: float,
|
|
1082
1102
|
max_bytes: int,
|
|
1083
1103
|
supplied_client: Optional[httpx.Client],
|
|
1104
|
+
http_client_exception_diagnostics: Optional[Callable[[Mapping[str, object]], None]],
|
|
1084
1105
|
) -> _Download:
|
|
1085
1106
|
last_error: Optional[AcquisitionError] = None
|
|
1086
1107
|
if urlsplit(original_url).scheme == "ftp":
|
|
@@ -1100,7 +1121,17 @@ def _download_http(
|
|
|
1100
1121
|
for attempt in range(retries):
|
|
1101
1122
|
try:
|
|
1102
1123
|
return _download_http_once(
|
|
1103
|
-
client,
|
|
1124
|
+
client,
|
|
1125
|
+
original_url,
|
|
1126
|
+
source,
|
|
1127
|
+
auth,
|
|
1128
|
+
timeout_s,
|
|
1129
|
+
max_bytes,
|
|
1130
|
+
(
|
|
1131
|
+
http_client_exception_diagnostics
|
|
1132
|
+
if supplied_client is not None
|
|
1133
|
+
else None
|
|
1134
|
+
),
|
|
1104
1135
|
)
|
|
1105
1136
|
except AcquisitionError as error:
|
|
1106
1137
|
last_error = error
|
|
@@ -1114,6 +1145,34 @@ def _download_http(
|
|
|
1114
1145
|
client.close()
|
|
1115
1146
|
|
|
1116
1147
|
|
|
1148
|
+
def _http_client_exception_diagnostic(error: Exception) -> Mapping[str, object]:
|
|
1149
|
+
"""Return bounded exception metadata without reading message or arguments."""
|
|
1150
|
+
exception_type = type(error)
|
|
1151
|
+
class_name = f"{exception_type.__module__}.{exception_type.__qualname__}"[:256]
|
|
1152
|
+
frames: deque[tuple[str, str, int]] = deque(maxlen=8)
|
|
1153
|
+
traceback = error.__traceback__
|
|
1154
|
+
while traceback is not None:
|
|
1155
|
+
frame = traceback.tb_frame
|
|
1156
|
+
module = frame.f_globals.get("__name__", "")
|
|
1157
|
+
module_name = module[:256] if isinstance(module, str) else ""
|
|
1158
|
+
function_name = frame.f_code.co_name[:256]
|
|
1159
|
+
frames.append((module_name, function_name, frame.f_code.co_argcount))
|
|
1160
|
+
traceback = traceback.tb_next
|
|
1161
|
+
stack_frames = tuple(frames)
|
|
1162
|
+
caller_frames = [
|
|
1163
|
+
frame
|
|
1164
|
+
for frame in stack_frames
|
|
1165
|
+
if not frame[0].startswith("httpx.")
|
|
1166
|
+
and frame[0] not in {"contextlib", __name__}
|
|
1167
|
+
]
|
|
1168
|
+
callsite = caller_frames[-1] if caller_frames else ("", "", 0)
|
|
1169
|
+
return {
|
|
1170
|
+
"exception_class": class_name,
|
|
1171
|
+
"client_callsite": callsite,
|
|
1172
|
+
"stack_frames": stack_frames,
|
|
1173
|
+
}
|
|
1174
|
+
|
|
1175
|
+
|
|
1117
1176
|
def _download_http_once(
|
|
1118
1177
|
client: httpx.Client,
|
|
1119
1178
|
original_url: str,
|
|
@@ -1121,6 +1180,7 @@ def _download_http_once(
|
|
|
1121
1180
|
auth: EarthdataAuth,
|
|
1122
1181
|
timeout_s: float,
|
|
1123
1182
|
max_bytes: int,
|
|
1183
|
+
http_client_exception_diagnostics: Optional[Callable[[Mapping[str, object]], None]],
|
|
1124
1184
|
) -> _Download:
|
|
1125
1185
|
current = original_url
|
|
1126
1186
|
for redirect_count in range(_MAX_REDIRECTS + 1):
|
|
@@ -1208,6 +1268,15 @@ def _download_http_once(
|
|
|
1208
1268
|
raise TransportFailure("connection", current) from None
|
|
1209
1269
|
except httpx.RequestError:
|
|
1210
1270
|
raise TransportFailure("other", current) from None
|
|
1271
|
+
except Exception as error: # noqa: BLE001 - caller transports may raise arbitrary errors
|
|
1272
|
+
if http_client_exception_diagnostics is not None:
|
|
1273
|
+
try:
|
|
1274
|
+
diagnostic = _http_client_exception_diagnostic(error)
|
|
1275
|
+
if diagnostic["client_callsite"] != ("", "", 0):
|
|
1276
|
+
http_client_exception_diagnostics(diagnostic)
|
|
1277
|
+
except BaseException: # noqa: BLE001 - diagnostics never mask the transport
|
|
1278
|
+
pass
|
|
1279
|
+
raise
|
|
1211
1280
|
raise RedirectPolicyFailure(f"too many redirects for {_sanitize_url(original_url)}")
|
|
1212
1281
|
|
|
1213
1282
|
|
|
@@ -4,7 +4,7 @@ import datetime as dt
|
|
|
4
4
|
import enum
|
|
5
5
|
import os
|
|
6
6
|
from dataclasses import dataclass
|
|
7
|
-
from typing import Mapping, Optional, Sequence, Tuple, Union
|
|
7
|
+
from typing import Callable, Mapping, Optional, Sequence, Tuple, Union
|
|
8
8
|
|
|
9
9
|
import httpx
|
|
10
10
|
|
|
@@ -185,6 +185,9 @@ def acquire(
|
|
|
185
185
|
max_archive_bytes: int = ...,
|
|
186
186
|
max_product_bytes: int = ...,
|
|
187
187
|
http_client: Optional[httpx.Client] = ...,
|
|
188
|
+
http_client_exception_diagnostics: Optional[
|
|
189
|
+
Callable[[Mapping[str, object]], None]
|
|
190
|
+
] = ...,
|
|
188
191
|
) -> AcquiredProduct: ...
|
|
189
192
|
|
|
190
193
|
__all__: list[str]
|
|
@@ -13,6 +13,7 @@ import tomllib
|
|
|
13
13
|
ROOT = Path(__file__).resolve().parents[1]
|
|
14
14
|
CORE_GIT_URL = "https://github.com/neilberkman/sidereon"
|
|
15
15
|
FULL_GIT_REVISION = re.compile(r"^[0-9a-f]{40}$")
|
|
16
|
+
CORE_SOURCE_REVISION = "8694648892d8ab065d94014e2e21d6cd5054818e"
|
|
16
17
|
|
|
17
18
|
|
|
18
19
|
def registry_version(name, value, package_version):
|
|
@@ -113,7 +114,7 @@ def validate_trust_region_dependency(
|
|
|
113
114
|
value, engine_dependencies, package_version, *, allow_candidate
|
|
114
115
|
):
|
|
115
116
|
"""Accept the registry release or its exact coordinated Git candidate."""
|
|
116
|
-
if value
|
|
117
|
+
if value in ("0.11.0", "=0.11.0"):
|
|
117
118
|
return
|
|
118
119
|
if not allow_candidate:
|
|
119
120
|
raise ValueError(
|
|
@@ -308,7 +309,7 @@ def main() -> None:
|
|
|
308
309
|
"ocean.rs": "25946677944425671a92717860ac2d70f255de5403eeb1fbf98b361716821d5c",
|
|
309
310
|
"pole.rs": "b4cc4c16bdd8ce1d8f04073602ab47dfb85a002b946ab192e8d4d2d600f0a1f8",
|
|
310
311
|
}
|
|
311
|
-
tide_root = ROOT / "third_party_source" / "sidereon-core-3.0.
|
|
312
|
+
tide_root = ROOT / "third_party_source" / "sidereon-core-3.0.2" / "tides"
|
|
312
313
|
for filename, expected_digest in tide_sources.items():
|
|
313
314
|
source = tide_root / filename
|
|
314
315
|
if not source.is_file():
|
|
@@ -317,7 +318,8 @@ def main() -> None:
|
|
|
317
318
|
if digest != expected_digest:
|
|
318
319
|
raise SystemExit(
|
|
319
320
|
f"IERS-derived source disclosure {source} has digest {digest}, "
|
|
320
|
-
f"expected {expected_digest} from sidereon-core 3.0.
|
|
321
|
+
f"expected {expected_digest} from sidereon-core 3.0.2 at "
|
|
322
|
+
f"{CORE_SOURCE_REVISION}"
|
|
321
323
|
)
|
|
322
324
|
|
|
323
325
|
if args.tag is not None and args.tag != f"v{python_version}":
|
|
@@ -8,7 +8,7 @@ use std::path::{Path, PathBuf};
|
|
|
8
8
|
|
|
9
9
|
const REGISTRY_SOURCE: &str = "registry+https://github.com/rust-lang/crates.io-index";
|
|
10
10
|
const GIT_SOURCE_PREFIX: &str = "git+https://github.com/neilberkman/sidereon?rev=";
|
|
11
|
-
const RELEASE_VERSION: &str = "3.0.
|
|
11
|
+
const RELEASE_VERSION: &str = "3.0.2";
|
|
12
12
|
|
|
13
13
|
#[derive(Debug)]
|
|
14
14
|
struct LockedPackage {
|
|
@@ -343,7 +343,7 @@ mod tests {
|
|
|
343
343
|
NEXT_TEMP.fetch_add(1, Ordering::Relaxed)
|
|
344
344
|
));
|
|
345
345
|
let cache = temp.join("registry/cache/test-index");
|
|
346
|
-
let extracted = temp.join("registry/src/test-index/sidereon-3.0.
|
|
346
|
+
let extracted = temp.join("registry/src/test-index/sidereon-3.0.1");
|
|
347
347
|
fs::create_dir_all(&cache).expect("create registry cache");
|
|
348
348
|
fs::create_dir_all(&extracted).expect("create extracted source");
|
|
349
349
|
fs::write(
|
|
@@ -355,17 +355,17 @@ mod tests {
|
|
|
355
355
|
let revision = "0123456789abcdef0123456789abcdef01234567";
|
|
356
356
|
let archive = crate_archive(
|
|
357
357
|
"sidereon",
|
|
358
|
-
"3.0.
|
|
359
|
-
"[package]\nname = \"sidereon\"\nversion = \"3.0.
|
|
358
|
+
"3.0.1",
|
|
359
|
+
"[package]\nname = \"sidereon\"\nversion = \"3.0.1\"\n",
|
|
360
360
|
&format!(r#"{{"git":{{"sha1":"{revision}","dirty":false}}}}"#),
|
|
361
361
|
);
|
|
362
362
|
let checksum = format!("{:x}", Sha256::digest(&archive));
|
|
363
|
-
fs::write(cache.join("sidereon-3.0.
|
|
363
|
+
fs::write(cache.join("sidereon-3.0.1.crate"), archive).expect("write crate archive");
|
|
364
364
|
assert_eq!(
|
|
365
|
-
registry_revision(&temp, "sidereon", "3.0.
|
|
365
|
+
registry_revision(&temp, "sidereon", "3.0.1", &checksum).unwrap(),
|
|
366
366
|
revision
|
|
367
367
|
);
|
|
368
|
-
assert!(registry_revision(&temp, "sidereon", "3.0.
|
|
368
|
+
assert!(registry_revision(&temp, "sidereon", "3.0.1", &"f".repeat(64)).is_err());
|
|
369
369
|
fs::remove_dir_all(temp).expect("remove registry test directory");
|
|
370
370
|
}
|
|
371
371
|
|
|
Binary file
|
|
@@ -16520,5 +16520,5 @@
|
|
|
16520
16520
|
]
|
|
16521
16521
|
}
|
|
16522
16522
|
},
|
|
16523
|
-
"core_revision": "
|
|
16523
|
+
"core_revision": "8694648892d8ab065d94014e2e21d6cd5054818e"
|
|
16524
16524
|
}
|
|
@@ -0,0 +1,166 @@
|
|
|
1
|
+
"""Direct equality coverage for public ANTEX values and parse details."""
|
|
2
|
+
|
|
3
|
+
import sidereon
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
def _record(content, label):
|
|
7
|
+
assert len(content) <= 60
|
|
8
|
+
return f"{content:<60}{label}"
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
def _antex(
|
|
12
|
+
*,
|
|
13
|
+
version="1.4",
|
|
14
|
+
system="M",
|
|
15
|
+
header_comment="header note",
|
|
16
|
+
pcv_type="R",
|
|
17
|
+
reference_type="AOAD/M_T",
|
|
18
|
+
reference_serial="",
|
|
19
|
+
outer_comment="outside note",
|
|
20
|
+
grid=" 0.0 10.0 5.0",
|
|
21
|
+
calibration_date="01-JAN-20",
|
|
22
|
+
pco=" 1.00 2.00 3.00",
|
|
23
|
+
rms_pco=" 0.10 0.20 0.30",
|
|
24
|
+
sample=" NOAZI 1.00 2.00 3.00",
|
|
25
|
+
):
|
|
26
|
+
"""Return a valid, small ANTEX document with all nested value types."""
|
|
27
|
+
pcv_record = f"{pcv_type:<1}{'':19}{reference_type:<20}{reference_serial:<20}"
|
|
28
|
+
calibration = f"{'FIELD':<20}{'IGS':<20}{2:6d}{'':4}{calibration_date:<10}"
|
|
29
|
+
lines = [
|
|
30
|
+
_record(f" {version:<3} {system}", "ANTEX VERSION / SYST"),
|
|
31
|
+
_record(pcv_record, "PCV TYPE / REFANT"),
|
|
32
|
+
_record(header_comment, "COMMENT"),
|
|
33
|
+
_record("", "END OF HEADER"),
|
|
34
|
+
_record(outer_comment, "COMMENT"),
|
|
35
|
+
_record("", "START OF ANTENNA"),
|
|
36
|
+
_record(f"{'TESTANT':<20}{'SERIAL-1':<20}", "TYPE / SERIAL NO"),
|
|
37
|
+
_record(calibration, "METH / BY / # / DATE"),
|
|
38
|
+
_record(" 1", "# OF FREQUENCIES"),
|
|
39
|
+
_record(grid, "ZEN1 / ZEN2 / DZEN"),
|
|
40
|
+
_record(" G01", "START OF FREQUENCY"),
|
|
41
|
+
_record(pco, "NORTH / EAST / UP"),
|
|
42
|
+
sample,
|
|
43
|
+
_record(" G01", "END OF FREQUENCY"),
|
|
44
|
+
_record(" G01", "START OF FREQ RMS"),
|
|
45
|
+
_record(rms_pco, "NORTH / EAST / UP"),
|
|
46
|
+
_record(" NOAZI 0.01 0.02 0.03", ""),
|
|
47
|
+
_record(" G01", "END OF FREQ RMS"),
|
|
48
|
+
_record("", "END OF ANTENNA"),
|
|
49
|
+
_record("after block", "COMMENT"),
|
|
50
|
+
]
|
|
51
|
+
return ("\n".join(lines) + "\n").encode("ascii")
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
def _invalid_pcv_type(value):
|
|
55
|
+
text = "\n".join(
|
|
56
|
+
[
|
|
57
|
+
_record(" 1.4 M", "ANTEX VERSION / SYST"),
|
|
58
|
+
_record(value, "PCV TYPE / REFANT"),
|
|
59
|
+
_record("", "END OF HEADER"),
|
|
60
|
+
]
|
|
61
|
+
)
|
|
62
|
+
try:
|
|
63
|
+
sidereon.load_antex(text.encode("ascii"))
|
|
64
|
+
except sidereon.AntexParseError as error:
|
|
65
|
+
assert error.detail is not None
|
|
66
|
+
return error.detail
|
|
67
|
+
raise AssertionError("invalid PCV type unexpectedly parsed")
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
def _assert_eq_and_ne(equal_left, equal_again, different):
|
|
71
|
+
# These wrappers define __eq__ but rely on Python's normal __ne__ fallback.
|
|
72
|
+
assert equal_left == equal_again
|
|
73
|
+
assert not (equal_left != equal_again)
|
|
74
|
+
assert equal_left != different
|
|
75
|
+
assert not (equal_left == different)
|
|
76
|
+
|
|
77
|
+
|
|
78
|
+
def test_public_antex_value_and_error_detail_equality_protocol():
|
|
79
|
+
source = _antex()
|
|
80
|
+
parsed = sidereon.load_antex(source)
|
|
81
|
+
repeated = sidereon.load_antex(source)
|
|
82
|
+
|
|
83
|
+
header_changed = sidereon.load_antex(_antex(header_comment="changed header"))
|
|
84
|
+
version_changed = sidereon.load_antex(_antex(system="G"))
|
|
85
|
+
pcv_type_changed = sidereon.load_antex(
|
|
86
|
+
_antex(reference_type="OTHER ANT", reference_serial="SERIAL-2")
|
|
87
|
+
)
|
|
88
|
+
outer_comment_changed = sidereon.load_antex(_antex(outer_comment="changed outer"))
|
|
89
|
+
grid_changed = sidereon.load_antex(_antex(grid=" 0.0 12.0 6.0"))
|
|
90
|
+
calibration_changed = sidereon.load_antex(_antex(calibration_date="02-JAN-20"))
|
|
91
|
+
frequency_changed = sidereon.load_antex(
|
|
92
|
+
_antex(pco=" 1.50 2.00 3.00")
|
|
93
|
+
)
|
|
94
|
+
rms_changed = sidereon.load_antex(_antex(rms_pco=" 0.11 0.20 0.30"))
|
|
95
|
+
sample_changed = sidereon.load_antex(
|
|
96
|
+
_antex(sample=" NOAZI 1.00 2.50 3.00")
|
|
97
|
+
)
|
|
98
|
+
|
|
99
|
+
_assert_eq_and_ne(parsed, repeated, header_changed)
|
|
100
|
+
|
|
101
|
+
antenna = parsed.antenna("TESTANT SERIAL-1")
|
|
102
|
+
repeated_antenna = repeated.antenna("TESTANT SERIAL-1")
|
|
103
|
+
changed_antenna = grid_changed.antenna("TESTANT SERIAL-1")
|
|
104
|
+
assert antenna is not None and repeated_antenna is not None
|
|
105
|
+
assert changed_antenna is not None
|
|
106
|
+
_assert_eq_and_ne(antenna, repeated_antenna, changed_antenna)
|
|
107
|
+
|
|
108
|
+
_assert_eq_and_ne(parsed.header, repeated.header, header_changed.header)
|
|
109
|
+
_assert_eq_and_ne(
|
|
110
|
+
parsed.header.version,
|
|
111
|
+
repeated.header.version,
|
|
112
|
+
version_changed.header.version,
|
|
113
|
+
)
|
|
114
|
+
_assert_eq_and_ne(
|
|
115
|
+
parsed.header.pcv_type,
|
|
116
|
+
repeated.header.pcv_type,
|
|
117
|
+
pcv_type_changed.header.pcv_type,
|
|
118
|
+
)
|
|
119
|
+
|
|
120
|
+
_assert_eq_and_ne(
|
|
121
|
+
parsed.outer_comments[0],
|
|
122
|
+
repeated.outer_comments[0],
|
|
123
|
+
outer_comment_changed.outer_comments[0],
|
|
124
|
+
)
|
|
125
|
+
assert len(parsed.outer_comments) == 2
|
|
126
|
+
|
|
127
|
+
assert antenna.zenith_grid is not None
|
|
128
|
+
assert repeated_antenna.zenith_grid is not None
|
|
129
|
+
assert changed_antenna.zenith_grid is not None
|
|
130
|
+
_assert_eq_and_ne(
|
|
131
|
+
antenna.zenith_grid,
|
|
132
|
+
repeated_antenna.zenith_grid,
|
|
133
|
+
changed_antenna.zenith_grid,
|
|
134
|
+
)
|
|
135
|
+
_assert_eq_and_ne(
|
|
136
|
+
antenna.calibrations[0],
|
|
137
|
+
repeated_antenna.calibrations[0],
|
|
138
|
+
calibration_changed.antenna("TESTANT SERIAL-1").calibrations[0],
|
|
139
|
+
)
|
|
140
|
+
|
|
141
|
+
frequency = antenna.frequency_sections[0]
|
|
142
|
+
repeated_frequency = repeated_antenna.frequency_sections[0]
|
|
143
|
+
_assert_eq_and_ne(
|
|
144
|
+
frequency,
|
|
145
|
+
repeated_frequency,
|
|
146
|
+
frequency_changed.antenna("TESTANT SERIAL-1").frequency_sections[0],
|
|
147
|
+
)
|
|
148
|
+
assert frequency.rms is not None and repeated_frequency.rms is not None
|
|
149
|
+
changed_rms = (
|
|
150
|
+
rms_changed.antenna("TESTANT SERIAL-1").frequency_sections[0].rms
|
|
151
|
+
)
|
|
152
|
+
assert changed_rms is not None
|
|
153
|
+
_assert_eq_and_ne(frequency.rms, repeated_frequency.rms, changed_rms)
|
|
154
|
+
_assert_eq_and_ne(
|
|
155
|
+
frequency.pcv_samples[1],
|
|
156
|
+
repeated_frequency.pcv_samples[1],
|
|
157
|
+
sample_changed.antenna("TESTANT SERIAL-1")
|
|
158
|
+
.frequency_sections[0]
|
|
159
|
+
.pcv_samples[1],
|
|
160
|
+
)
|
|
161
|
+
|
|
162
|
+
_assert_eq_and_ne(
|
|
163
|
+
_invalid_pcv_type("X"),
|
|
164
|
+
_invalid_pcv_type("X"),
|
|
165
|
+
_invalid_pcv_type("Y"),
|
|
166
|
+
)
|