imap-processing 0.12.0__py3-none-any.whl → 0.13.0__py3-none-any.whl
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.
Potentially problematic release.
This version of imap-processing might be problematic. Click here for more details.
- imap_processing/__init__.py +1 -0
- imap_processing/_version.py +2 -2
- imap_processing/ccsds/ccsds_data.py +1 -2
- imap_processing/ccsds/excel_to_xtce.py +1 -2
- imap_processing/cdf/config/imap_codice_global_cdf_attrs.yaml +18 -12
- imap_processing/cdf/config/imap_codice_l1a_variable_attrs.yaml +569 -0
- imap_processing/cdf/config/imap_codice_l1b_variable_attrs.yaml +1846 -128
- imap_processing/cdf/config/imap_hit_global_cdf_attrs.yaml +5 -5
- imap_processing/cdf/config/imap_idex_global_cdf_attrs.yaml +20 -1
- imap_processing/cdf/config/imap_idex_l1a_variable_attrs.yaml +6 -4
- imap_processing/cdf/config/imap_idex_l1b_variable_attrs.yaml +3 -3
- imap_processing/cdf/config/imap_mag_global_cdf_attrs.yaml +15 -0
- imap_processing/cdf/config/imap_swapi_variable_attrs.yaml +22 -0
- imap_processing/cdf/config/imap_swe_l1b_variable_attrs.yaml +16 -0
- imap_processing/cdf/config/imap_ultra_global_cdf_attrs.yaml +178 -5
- imap_processing/cdf/config/imap_ultra_l1a_variable_attrs.yaml +5045 -41
- imap_processing/cdf/config/imap_ultra_l1b_variable_attrs.yaml +33 -19
- imap_processing/cdf/config/imap_ultra_l1c_variable_attrs.yaml +8 -48
- imap_processing/cdf/utils.py +41 -33
- imap_processing/cli.py +463 -234
- imap_processing/codice/codice_l1a.py +260 -47
- imap_processing/codice/codice_l1b.py +51 -152
- imap_processing/codice/constants.py +38 -1
- imap_processing/ena_maps/ena_maps.py +658 -65
- imap_processing/ena_maps/utils/coordinates.py +1 -1
- imap_processing/ena_maps/utils/spatial_utils.py +10 -5
- imap_processing/glows/l1a/glows_l1a.py +28 -99
- imap_processing/glows/l1a/glows_l1a_data.py +2 -2
- imap_processing/glows/l1b/glows_l1b.py +1 -4
- imap_processing/glows/l1b/glows_l1b_data.py +1 -3
- imap_processing/glows/l2/glows_l2.py +2 -5
- imap_processing/hi/l1a/hi_l1a.py +31 -12
- imap_processing/hi/l1b/hi_l1b.py +80 -43
- imap_processing/hi/l1c/hi_l1c.py +12 -16
- imap_processing/hit/ancillary/imap_hit_l1b-to-l2-sector-dt0-factors_20250219_v002.csv +81 -0
- imap_processing/hit/hit_utils.py +93 -35
- imap_processing/hit/l0/decom_hit.py +3 -1
- imap_processing/hit/l1a/hit_l1a.py +30 -25
- imap_processing/hit/l1b/constants.py +6 -2
- imap_processing/hit/l1b/hit_l1b.py +279 -318
- imap_processing/hit/l2/constants.py +37 -0
- imap_processing/hit/l2/hit_l2.py +373 -264
- imap_processing/ialirt/l0/parse_mag.py +138 -10
- imap_processing/ialirt/l0/process_swapi.py +69 -0
- imap_processing/ialirt/l0/process_swe.py +318 -22
- imap_processing/ialirt/packet_definitions/ialirt.xml +216 -212
- imap_processing/ialirt/packet_definitions/ialirt_codicehi.xml +1 -1
- imap_processing/ialirt/packet_definitions/ialirt_codicelo.xml +1 -1
- imap_processing/ialirt/packet_definitions/ialirt_swapi.xml +14 -14
- imap_processing/ialirt/utils/grouping.py +1 -1
- imap_processing/idex/idex_constants.py +9 -1
- imap_processing/idex/idex_l0.py +22 -8
- imap_processing/idex/idex_l1a.py +75 -44
- imap_processing/idex/idex_l1b.py +9 -8
- imap_processing/idex/idex_l2a.py +79 -45
- imap_processing/idex/idex_l2b.py +120 -0
- imap_processing/idex/idex_variable_unpacking_and_eu_conversion.csv +33 -39
- imap_processing/idex/packet_definitions/idex_housekeeping_packet_definition.xml +9130 -0
- imap_processing/lo/l0/lo_science.py +1 -2
- imap_processing/lo/l1a/lo_l1a.py +1 -4
- imap_processing/lo/l1b/lo_l1b.py +527 -6
- imap_processing/lo/l1b/tof_conversions.py +11 -0
- imap_processing/lo/l1c/lo_l1c.py +1 -4
- imap_processing/mag/constants.py +43 -0
- imap_processing/mag/imap_mag_sdc_configuration_v001.py +8 -0
- imap_processing/mag/l1a/mag_l1a.py +2 -9
- imap_processing/mag/l1a/mag_l1a_data.py +10 -10
- imap_processing/mag/l1b/mag_l1b.py +84 -17
- imap_processing/mag/l1c/interpolation_methods.py +180 -3
- imap_processing/mag/l1c/mag_l1c.py +236 -70
- imap_processing/mag/l2/mag_l2.py +140 -0
- imap_processing/mag/l2/mag_l2_data.py +288 -0
- imap_processing/spacecraft/quaternions.py +1 -3
- imap_processing/spice/geometry.py +3 -3
- imap_processing/spice/kernels.py +0 -276
- imap_processing/spice/pointing_frame.py +257 -0
- imap_processing/spice/repoint.py +48 -19
- imap_processing/spice/spin.py +38 -33
- imap_processing/spice/time.py +24 -0
- imap_processing/swapi/l1/swapi_l1.py +16 -12
- imap_processing/swapi/l2/swapi_l2.py +116 -4
- imap_processing/swapi/swapi_utils.py +32 -0
- imap_processing/swe/l1a/swe_l1a.py +2 -9
- imap_processing/swe/l1a/swe_science.py +8 -11
- imap_processing/swe/l1b/swe_l1b.py +898 -23
- imap_processing/swe/l2/swe_l2.py +21 -77
- imap_processing/swe/utils/swe_constants.py +1 -0
- imap_processing/tests/ccsds/test_excel_to_xtce.py +1 -1
- imap_processing/tests/cdf/test_utils.py +14 -16
- imap_processing/tests/codice/conftest.py +44 -33
- imap_processing/tests/codice/data/validation/imap_codice_l1a_hi-pha_20241110193700_v0.0.0.cdf +0 -0
- imap_processing/tests/codice/data/validation/imap_codice_l1a_lo-pha_20241110193700_v0.0.0.cdf +0 -0
- imap_processing/tests/codice/test_codice_l1a.py +20 -11
- imap_processing/tests/codice/test_codice_l1b.py +6 -7
- imap_processing/tests/conftest.py +78 -22
- imap_processing/tests/ena_maps/test_ena_maps.py +462 -33
- imap_processing/tests/ena_maps/test_spatial_utils.py +1 -1
- imap_processing/tests/glows/conftest.py +10 -14
- imap_processing/tests/glows/test_glows_decom.py +4 -4
- imap_processing/tests/glows/test_glows_l1a_cdf.py +6 -27
- imap_processing/tests/glows/test_glows_l1a_data.py +6 -8
- imap_processing/tests/glows/test_glows_l1b.py +11 -11
- imap_processing/tests/glows/test_glows_l1b_data.py +5 -5
- imap_processing/tests/glows/test_glows_l2.py +2 -8
- imap_processing/tests/hi/conftest.py +1 -1
- imap_processing/tests/hi/test_hi_l1b.py +10 -12
- imap_processing/tests/hi/test_hi_l1c.py +27 -24
- imap_processing/tests/hi/test_l1a.py +7 -9
- imap_processing/tests/hi/test_science_direct_event.py +2 -2
- imap_processing/tests/hit/helpers/l1_validation.py +44 -43
- imap_processing/tests/hit/test_decom_hit.py +1 -1
- imap_processing/tests/hit/test_hit_l1a.py +9 -9
- imap_processing/tests/hit/test_hit_l1b.py +172 -217
- imap_processing/tests/hit/test_hit_l2.py +380 -118
- imap_processing/tests/hit/test_hit_utils.py +122 -55
- imap_processing/tests/hit/validation_data/hit_l1b_standard_sample2_nsrl_v4_3decimals.csv +62 -62
- imap_processing/tests/hit/validation_data/sci_sample_raw.csv +1 -1
- imap_processing/tests/ialirt/unit/test_decom_ialirt.py +16 -81
- imap_processing/tests/ialirt/unit/test_grouping.py +2 -2
- imap_processing/tests/ialirt/unit/test_parse_mag.py +71 -16
- imap_processing/tests/ialirt/unit/test_process_codicehi.py +3 -3
- imap_processing/tests/ialirt/unit/test_process_codicelo.py +3 -10
- imap_processing/tests/ialirt/unit/test_process_ephemeris.py +4 -4
- imap_processing/tests/ialirt/unit/test_process_hit.py +3 -3
- imap_processing/tests/ialirt/unit/test_process_swapi.py +24 -16
- imap_processing/tests/ialirt/unit/test_process_swe.py +115 -7
- imap_processing/tests/idex/conftest.py +72 -7
- imap_processing/tests/idex/test_data/imap_idex_l0_raw_20241206_v001.pkts +0 -0
- imap_processing/tests/idex/test_data/imap_idex_l0_raw_20250108_v001.pkts +0 -0
- imap_processing/tests/idex/test_idex_l0.py +33 -11
- imap_processing/tests/idex/test_idex_l1a.py +50 -23
- imap_processing/tests/idex/test_idex_l1b.py +104 -25
- imap_processing/tests/idex/test_idex_l2a.py +48 -32
- imap_processing/tests/idex/test_idex_l2b.py +93 -0
- imap_processing/tests/lo/test_lo_l1a.py +3 -3
- imap_processing/tests/lo/test_lo_l1b.py +371 -6
- imap_processing/tests/lo/test_lo_l1c.py +1 -1
- imap_processing/tests/lo/test_lo_science.py +6 -7
- imap_processing/tests/lo/test_star_sensor.py +1 -1
- imap_processing/tests/mag/conftest.py +58 -9
- imap_processing/tests/mag/test_mag_decom.py +4 -3
- imap_processing/tests/mag/test_mag_l1a.py +13 -7
- imap_processing/tests/mag/test_mag_l1b.py +9 -9
- imap_processing/tests/mag/test_mag_l1c.py +151 -47
- imap_processing/tests/mag/test_mag_l2.py +130 -0
- imap_processing/tests/mag/test_mag_validation.py +144 -7
- imap_processing/tests/mag/validation/L1c/T013/mag-l1b-l1c-t013-magi-normal-in.csv +1217 -0
- imap_processing/tests/mag/validation/L1c/T013/mag-l1b-l1c-t013-magi-normal-out.csv +1857 -0
- imap_processing/tests/mag/validation/L1c/T013/mag-l1b-l1c-t013-mago-normal-in.csv +1217 -0
- imap_processing/tests/mag/validation/L1c/T013/mag-l1b-l1c-t013-mago-normal-out.csv +1857 -0
- imap_processing/tests/mag/validation/L1c/T014/mag-l1b-l1c-t014-magi-normal-in.csv +1217 -0
- imap_processing/tests/mag/validation/L1c/T014/mag-l1b-l1c-t014-magi-normal-out.csv +1793 -0
- imap_processing/tests/mag/validation/L1c/T014/mag-l1b-l1c-t014-mago-normal-in.csv +1217 -0
- imap_processing/tests/mag/validation/L1c/T014/mag-l1b-l1c-t014-mago-normal-out.csv +1793 -0
- imap_processing/tests/mag/validation/L1c/T015/mag-l1b-l1c-t015-magi-burst-in.csv +2561 -0
- imap_processing/tests/mag/validation/L1c/T015/mag-l1b-l1c-t015-magi-normal-in.csv +961 -0
- imap_processing/tests/mag/validation/L1c/T015/mag-l1b-l1c-t015-magi-normal-out.csv +1539 -0
- imap_processing/tests/mag/validation/L1c/T015/mag-l1b-l1c-t015-mago-normal-in.csv +1921 -0
- imap_processing/tests/mag/validation/L1c/T015/mag-l1b-l1c-t015-mago-normal-out.csv +2499 -0
- imap_processing/tests/mag/validation/L1c/T016/mag-l1b-l1c-t016-magi-normal-in.csv +865 -0
- imap_processing/tests/mag/validation/L1c/T016/mag-l1b-l1c-t016-magi-normal-out.csv +1196 -0
- imap_processing/tests/mag/validation/L1c/T016/mag-l1b-l1c-t016-mago-normal-in.csv +1729 -0
- imap_processing/tests/mag/validation/L1c/T016/mag-l1b-l1c-t016-mago-normal-out.csv +3053 -0
- imap_processing/tests/mag/validation/L2/imap_mag_l1b_norm-mago_20251017_v002.cdf +0 -0
- imap_processing/tests/mag/validation/calibration/imap_mag_l2-calibration-matrices_20251017_v004.cdf +0 -0
- imap_processing/tests/mag/validation/calibration/imap_mag_l2-offsets-norm_20251017_20251017_v001.cdf +0 -0
- imap_processing/tests/spacecraft/test_quaternions.py +1 -1
- imap_processing/tests/spice/test_data/fake_repoint_data.csv +4 -4
- imap_processing/tests/spice/test_data/fake_spin_data.csv +11 -11
- imap_processing/tests/spice/test_geometry.py +3 -3
- imap_processing/tests/spice/test_kernels.py +1 -200
- imap_processing/tests/spice/test_pointing_frame.py +185 -0
- imap_processing/tests/spice/test_repoint.py +20 -10
- imap_processing/tests/spice/test_spin.py +50 -9
- imap_processing/tests/spice/test_time.py +14 -0
- imap_processing/tests/swapi/lut/imap_swapi_esa-unit-conversion_20250211_v000.csv +73 -0
- imap_processing/tests/swapi/lut/imap_swapi_lut-notes_20250211_v000.csv +1025 -0
- imap_processing/tests/swapi/test_swapi_l1.py +7 -9
- imap_processing/tests/swapi/test_swapi_l2.py +180 -8
- imap_processing/tests/swe/lut/checker-board-indices.csv +24 -0
- imap_processing/tests/swe/lut/imap_swe_esa-lut_20250301_v000.csv +385 -0
- imap_processing/tests/swe/lut/imap_swe_l1b-in-flight-cal_20240510_20260716_v000.csv +3 -0
- imap_processing/tests/swe/test_swe_l1a.py +6 -6
- imap_processing/tests/swe/test_swe_l1a_science.py +3 -3
- imap_processing/tests/swe/test_swe_l1b.py +162 -24
- imap_processing/tests/swe/test_swe_l2.py +82 -102
- imap_processing/tests/test_cli.py +171 -88
- imap_processing/tests/test_utils.py +2 -1
- imap_processing/tests/ultra/data/mock_data.py +49 -21
- imap_processing/tests/ultra/unit/conftest.py +53 -70
- imap_processing/tests/ultra/unit/test_badtimes.py +2 -4
- imap_processing/tests/ultra/unit/test_cullingmask.py +4 -6
- imap_processing/tests/ultra/unit/test_de.py +3 -10
- imap_processing/tests/ultra/unit/test_decom_apid_880.py +27 -76
- imap_processing/tests/ultra/unit/test_decom_apid_881.py +15 -16
- imap_processing/tests/ultra/unit/test_decom_apid_883.py +12 -10
- imap_processing/tests/ultra/unit/test_decom_apid_896.py +202 -55
- imap_processing/tests/ultra/unit/test_lookup_utils.py +23 -1
- imap_processing/tests/ultra/unit/test_spacecraft_pset.py +3 -4
- imap_processing/tests/ultra/unit/test_ultra_l1a.py +84 -307
- imap_processing/tests/ultra/unit/test_ultra_l1b.py +30 -12
- imap_processing/tests/ultra/unit/test_ultra_l1b_annotated.py +2 -2
- imap_processing/tests/ultra/unit/test_ultra_l1b_culling.py +4 -1
- imap_processing/tests/ultra/unit/test_ultra_l1b_extended.py +163 -29
- imap_processing/tests/ultra/unit/test_ultra_l1c.py +5 -5
- imap_processing/tests/ultra/unit/test_ultra_l1c_pset_bins.py +32 -43
- imap_processing/tests/ultra/unit/test_ultra_l2.py +230 -0
- imap_processing/ultra/constants.py +1 -1
- imap_processing/ultra/l0/decom_tools.py +21 -34
- imap_processing/ultra/l0/decom_ultra.py +168 -204
- imap_processing/ultra/l0/ultra_utils.py +152 -136
- imap_processing/ultra/l1a/ultra_l1a.py +55 -243
- imap_processing/ultra/l1b/badtimes.py +1 -4
- imap_processing/ultra/l1b/cullingmask.py +2 -6
- imap_processing/ultra/l1b/de.py +62 -47
- imap_processing/ultra/l1b/extendedspin.py +8 -4
- imap_processing/ultra/l1b/lookup_utils.py +72 -9
- imap_processing/ultra/l1b/ultra_l1b.py +3 -8
- imap_processing/ultra/l1b/ultra_l1b_culling.py +4 -4
- imap_processing/ultra/l1b/ultra_l1b_extended.py +236 -78
- imap_processing/ultra/l1c/histogram.py +2 -6
- imap_processing/ultra/l1c/spacecraft_pset.py +2 -4
- imap_processing/ultra/l1c/ultra_l1c.py +1 -5
- imap_processing/ultra/l1c/ultra_l1c_pset_bins.py +107 -60
- imap_processing/ultra/l2/ultra_l2.py +299 -0
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM45_LeftSlit.csv +526 -0
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM45_RightSlit.csv +526 -0
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM90_LeftSlit.csv +526 -0
- imap_processing/ultra/lookup_tables/Angular_Profiles_FM90_RightSlit.csv +526 -0
- imap_processing/ultra/lookup_tables/FM45_Startup1_ULTRA_IMGPARAMS_20240719.csv +2 -2
- imap_processing/ultra/lookup_tables/FM90_Startup1_ULTRA_IMGPARAMS_20240719.csv +2 -0
- imap_processing/ultra/packet_definitions/README.md +38 -0
- imap_processing/ultra/packet_definitions/ULTRA_SCI_COMBINED.xml +15302 -482
- imap_processing/ultra/utils/ultra_l1_utils.py +13 -12
- imap_processing/utils.py +1 -1
- {imap_processing-0.12.0.dist-info → imap_processing-0.13.0.dist-info}/METADATA +3 -2
- {imap_processing-0.12.0.dist-info → imap_processing-0.13.0.dist-info}/RECORD +264 -225
- imap_processing/hi/l1b/hi_eng_unit_convert_table.csv +0 -154
- imap_processing/mag/imap_mag_sdc-configuration_v001.yaml +0 -6
- imap_processing/mag/l1b/__init__.py +0 -0
- imap_processing/swe/l1b/swe_esa_lookup_table.csv +0 -1441
- imap_processing/swe/l1b/swe_l1b_science.py +0 -699
- imap_processing/tests/swe/test_swe_l1b_science.py +0 -103
- imap_processing/ultra/lookup_tables/dps_sensitivity45.cdf +0 -0
- imap_processing/ultra/lookup_tables/ultra_90_dps_exposure_compressed.cdf +0 -0
- /imap_processing/idex/packet_definitions/{idex_packet_definition.xml → idex_science_packet_definition.xml} +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/20240827095047_SWE_IALIRT_packet.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971383-404.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971384-405.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971385-406.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971386-407.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971387-408.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971388-409.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971389-410.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971390-411.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/461971391-412.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/BinLog CCSDS_FRAG_TLM_20240826_152323Z_IALIRT_data_for_SDC.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/IALiRT Raw Packet Telemetry.txt +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/apid01152.tlm +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/eu_SWP_IAL_20240826_152033.csv +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/hi_fsw_view_1_ccsds.bin +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/hit_ialirt_sample.ccsds +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/hit_ialirt_sample.csv +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/idle_export_eu.SWE_IALIRT_20240827_093852.csv +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/imap_codice_l1a_hi-ialirt_20240523200000_v0.0.0.cdf +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/imap_codice_l1a_lo-ialirt_20241110193700_v0.0.0.cdf +0 -0
- /imap_processing/tests/ialirt/{test_data → data}/l0/sample_decoded_i-alirt_data.csv +0 -0
- /imap_processing/tests/mag/validation/{imap_calibration_mag_20240229_v01.cdf → calibration/imap_mag_l1b-calibration_20240229_v001.cdf} +0 -0
- /imap_processing/{swe/l1b/engineering_unit_convert_table.csv → tests/swe/lut/imap_swe_eu-conversion_20240510_v000.csv} +0 -0
- {imap_processing-0.12.0.dist-info → imap_processing-0.13.0.dist-info}/LICENSE +0 -0
- {imap_processing-0.12.0.dist-info → imap_processing-0.13.0.dist-info}/WHEEL +0 -0
- {imap_processing-0.12.0.dist-info → imap_processing-0.13.0.dist-info}/entry_points.txt +0 -0
|
@@ -6,25 +6,30 @@ import xarray as xr
|
|
|
6
6
|
from imap_processing import imap_module_directory
|
|
7
7
|
from imap_processing.hit.l1a import hit_l1a
|
|
8
8
|
from imap_processing.hit.l1b.hit_l1b import (
|
|
9
|
-
|
|
9
|
+
SUMMED_PARTICLE_ENERGY_RANGE_MAPPING,
|
|
10
10
|
hit_l1b,
|
|
11
11
|
)
|
|
12
12
|
from imap_processing.hit.l2.hit_l2 import (
|
|
13
|
+
FILLVAL_FLOAT32,
|
|
14
|
+
N_AZIMUTH,
|
|
15
|
+
SECONDS_PER_10_MIN,
|
|
16
|
+
SECONDS_PER_MIN,
|
|
13
17
|
STANDARD_PARTICLE_ENERGY_RANGE_MAPPING,
|
|
14
|
-
|
|
18
|
+
VALID_SECTORED_SPECIES,
|
|
15
19
|
add_systematic_uncertainties,
|
|
20
|
+
add_total_uncertainties,
|
|
21
|
+
build_ancillary_dataset,
|
|
16
22
|
calculate_intensities,
|
|
17
23
|
calculate_intensities_for_a_species,
|
|
18
24
|
calculate_intensities_for_all_species,
|
|
19
|
-
get_intensity_factors,
|
|
20
25
|
get_species_ancillary_data,
|
|
21
26
|
hit_l2,
|
|
27
|
+
process_sectored_intensity_data,
|
|
22
28
|
process_standard_intensity_data,
|
|
23
29
|
process_summed_intensity_data,
|
|
30
|
+
reshape_for_sectored,
|
|
24
31
|
)
|
|
25
32
|
|
|
26
|
-
# TODO: add unit test for add_standard_particle_rates_to_dataset
|
|
27
|
-
|
|
28
33
|
|
|
29
34
|
@pytest.fixture(scope="module")
|
|
30
35
|
def sci_packet_filepath():
|
|
@@ -32,112 +37,239 @@ def sci_packet_filepath():
|
|
|
32
37
|
return imap_module_directory / "tests/hit/test_data/sci_sample.ccsds"
|
|
33
38
|
|
|
34
39
|
|
|
35
|
-
@pytest.fixture
|
|
40
|
+
@pytest.fixture
|
|
36
41
|
def dependencies(sci_packet_filepath):
|
|
37
42
|
"""Get dependencies for L2 processing"""
|
|
38
43
|
# Create dictionary of dependencies
|
|
39
44
|
data_dict = {}
|
|
40
|
-
l1a_datasets = hit_l1a.hit_l1a(sci_packet_filepath
|
|
45
|
+
l1a_datasets = hit_l1a.hit_l1a(sci_packet_filepath)
|
|
41
46
|
for l1a_dataset in l1a_datasets:
|
|
42
47
|
l1a_data_dict = {}
|
|
43
48
|
if l1a_dataset.attrs["Logical_source"] == "imap_hit_l1a_counts":
|
|
44
49
|
l1a_data_dict["imap_hit_l1a_counts"] = l1a_dataset
|
|
45
|
-
l1b_datasets = hit_l1b(l1a_data_dict
|
|
50
|
+
l1b_datasets = hit_l1b(l1a_data_dict)
|
|
46
51
|
for l1b_dataset in l1b_datasets:
|
|
47
52
|
data_dict[l1b_dataset.attrs["Logical_source"]] = l1b_dataset
|
|
48
53
|
return data_dict
|
|
49
54
|
|
|
50
55
|
|
|
51
|
-
@pytest.fixture
|
|
56
|
+
@pytest.fixture
|
|
52
57
|
def l1b_summed_rates_dataset(dependencies):
|
|
53
58
|
"""Get L1B summed rates dataset to test l2 processing function"""
|
|
54
59
|
return dependencies["imap_hit_l1b_summed-rates"]
|
|
55
60
|
|
|
56
61
|
|
|
57
|
-
@pytest.fixture
|
|
62
|
+
@pytest.fixture
|
|
58
63
|
def l1b_standard_rates_dataset(dependencies):
|
|
59
64
|
"""Get L1B standard rates dataset to test l2 processing function"""
|
|
60
65
|
return dependencies["imap_hit_l1b_standard-rates"]
|
|
61
66
|
|
|
62
67
|
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
68
|
+
@pytest.fixture
|
|
69
|
+
def l1b_sectored_rates_dataset(dependencies):
|
|
70
|
+
"""Get L1B standard rates dataset to test l2 processing function"""
|
|
71
|
+
return dependencies["imap_hit_l1b_sectored-rates"]
|
|
72
|
+
|
|
73
|
+
|
|
74
|
+
def _check_ancillary_dataset(
|
|
75
|
+
ancillary_ds,
|
|
76
|
+
species_array,
|
|
77
|
+
delta_e,
|
|
78
|
+
geometry_factors,
|
|
79
|
+
efficiencies,
|
|
80
|
+
b,
|
|
81
|
+
expected_delta_time,
|
|
82
|
+
):
|
|
83
|
+
# Helper function - not a test
|
|
84
|
+
|
|
85
|
+
shape = species_array.shape
|
|
86
|
+
|
|
87
|
+
# Assert that all expected variables are present
|
|
88
|
+
assert set(ancillary_ds.data_vars) == {
|
|
89
|
+
"delta_e",
|
|
90
|
+
"geometry_factor",
|
|
91
|
+
"efficiency",
|
|
92
|
+
"b",
|
|
93
|
+
"delta_time",
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
# Check that shapes match
|
|
97
|
+
assert ancillary_ds["delta_e"].shape == shape
|
|
98
|
+
assert ancillary_ds["delta_time"].shape == (len(species_array.coords["epoch"]),)
|
|
99
|
+
|
|
100
|
+
# Check values
|
|
101
|
+
np.testing.assert_array_equal(ancillary_ds["delta_e"].values, delta_e)
|
|
102
|
+
np.testing.assert_array_equal(
|
|
103
|
+
ancillary_ds["geometry_factor"].values, geometry_factors
|
|
104
|
+
)
|
|
105
|
+
np.testing.assert_array_equal(ancillary_ds["efficiency"].values, efficiencies)
|
|
106
|
+
np.testing.assert_array_equal(ancillary_ds["b"].values, b)
|
|
107
|
+
np.testing.assert_array_equal(
|
|
108
|
+
ancillary_ds["delta_time"].values,
|
|
109
|
+
np.full(len(species_array.epoch), expected_delta_time),
|
|
75
110
|
)
|
|
76
111
|
|
|
77
|
-
#
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
112
|
+
# Check coordinates match
|
|
113
|
+
for coord in species_array.coords:
|
|
114
|
+
assert coord in ancillary_ds.coords
|
|
115
|
+
np.testing.assert_array_equal(
|
|
116
|
+
species_array.coords[coord], ancillary_ds.coords[coord]
|
|
117
|
+
)
|
|
118
|
+
|
|
119
|
+
|
|
120
|
+
def test_build_ancillary_dataset_sectored():
|
|
121
|
+
"""
|
|
122
|
+
Test the build_ancillary_dataset function for sectored data
|
|
123
|
+
"""
|
|
124
|
+
np.random.seed(42) # Set a random seed for reproducibility
|
|
125
|
+
epoch = np.array(["2025-01-01T00:00", "2025-01-01T00:01"], dtype="datetime64[m]")
|
|
126
|
+
energy_mean = [1.8, 4, 6]
|
|
127
|
+
declination = np.arange(8)
|
|
128
|
+
azimuth = np.arange(15)
|
|
129
|
+
|
|
130
|
+
species_array = xr.DataArray(
|
|
131
|
+
data=np.random.rand(2, 3, 15, 8), # (epoch, energy_mean, azimuth, declination)
|
|
132
|
+
dims=("epoch", "energy_mean", "azimuth", "declination"),
|
|
133
|
+
coords={
|
|
134
|
+
"epoch": epoch,
|
|
135
|
+
"energy_mean": energy_mean,
|
|
136
|
+
"declination": declination,
|
|
137
|
+
"azimuth": azimuth,
|
|
138
|
+
},
|
|
139
|
+
name="h",
|
|
83
140
|
)
|
|
84
141
|
|
|
85
|
-
|
|
86
|
-
|
|
142
|
+
shape = species_array.shape
|
|
143
|
+
delta_e = np.full(shape, 1.0)
|
|
144
|
+
geometry_factors = np.full(shape, 2.0)
|
|
145
|
+
efficiencies = np.full(shape, 0.5)
|
|
146
|
+
b = np.full(shape, 0.1)
|
|
87
147
|
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
148
|
+
ancillary_ds = build_ancillary_dataset(
|
|
149
|
+
delta_e, geometry_factors, efficiencies, b, species_array
|
|
150
|
+
)
|
|
151
|
+
_check_ancillary_dataset(
|
|
152
|
+
ancillary_ds,
|
|
153
|
+
species_array,
|
|
154
|
+
delta_e,
|
|
155
|
+
geometry_factors,
|
|
156
|
+
efficiencies,
|
|
157
|
+
b,
|
|
158
|
+
SECONDS_PER_10_MIN,
|
|
159
|
+
)
|
|
160
|
+
|
|
161
|
+
|
|
162
|
+
def test_build_ancillary_dataset_nonsectored():
|
|
163
|
+
"""
|
|
164
|
+
Test the build_ancillary_dataset function for non-sectored data.
|
|
165
|
+
|
|
166
|
+
Non-sectored datasets are either L2 standard or L2 summed datasets
|
|
167
|
+
They both have the same shape (epoch, energy_mean).
|
|
168
|
+
"""
|
|
169
|
+
np.random.seed(42) # Set a random seed for reproducibility
|
|
170
|
+
epoch = np.array(["2025-01-01T00:00", "2025-01-01T00:01"], dtype="datetime64[m]")
|
|
171
|
+
energy_mean = [1.8, 4, 6]
|
|
172
|
+
|
|
173
|
+
species_array = xr.DataArray(
|
|
174
|
+
data=np.random.rand(2, 3), # (epoch, energy_mean)
|
|
175
|
+
dims=("epoch", "energy_mean"),
|
|
176
|
+
coords={"epoch": epoch, "energy_mean": energy_mean},
|
|
177
|
+
name="h",
|
|
178
|
+
)
|
|
179
|
+
|
|
180
|
+
shape = species_array.shape
|
|
181
|
+
delta_e = np.full(shape, 1.0)
|
|
182
|
+
geometry_factors = np.full(shape, 2.0)
|
|
183
|
+
efficiencies = np.full(shape, 0.5)
|
|
184
|
+
b = np.full(shape, 0.1)
|
|
185
|
+
|
|
186
|
+
ancillary_ds = build_ancillary_dataset(
|
|
187
|
+
delta_e, geometry_factors, efficiencies, b, species_array
|
|
188
|
+
)
|
|
189
|
+
_check_ancillary_dataset(
|
|
190
|
+
ancillary_ds,
|
|
191
|
+
species_array,
|
|
192
|
+
delta_e,
|
|
193
|
+
geometry_factors,
|
|
194
|
+
efficiencies,
|
|
195
|
+
b,
|
|
196
|
+
SECONDS_PER_MIN,
|
|
197
|
+
)
|
|
99
198
|
|
|
100
199
|
|
|
101
200
|
def test_get_species_ancillary_data():
|
|
102
201
|
"""Test the get_species_ancillary_data function."""
|
|
103
|
-
|
|
104
|
-
|
|
202
|
+
|
|
203
|
+
# Mock ancillary data for dynamic threshold states 0 and 1
|
|
105
204
|
ancillary_data_frames = {
|
|
106
205
|
0: pd.DataFrame(
|
|
107
206
|
{
|
|
108
|
-
"species": ["h", "he", "
|
|
109
|
-
"lower energy (mev)": [1
|
|
110
|
-
"delta e (mev)": [0.1, 0.2, 0.3],
|
|
111
|
-
"geometry factor (cm2 sr)": [
|
|
112
|
-
"efficiency": [0.9, 0.8, 0.7],
|
|
113
|
-
"b": [0.01, 0.02, 0.03],
|
|
207
|
+
"species": ["h", "h", "he", "he"],
|
|
208
|
+
"lower energy (mev)": [1, 2, 1, 2],
|
|
209
|
+
"delta e (mev)": [0.1, 0.2, 0.3, 0.4],
|
|
210
|
+
"geometry factor (cm2 sr)": [10, 20, 30, 40],
|
|
211
|
+
"efficiency": [0.9, 0.8, 0.7, 0.6],
|
|
212
|
+
"b": [0.01, 0.02, 0.03, 0.04],
|
|
114
213
|
}
|
|
115
214
|
),
|
|
116
215
|
1: pd.DataFrame(
|
|
117
216
|
{
|
|
118
|
-
"species": ["h", "he", "
|
|
119
|
-
"lower energy (mev)": [1
|
|
120
|
-
"delta e (mev)": [0.15, 0.25, 0.35],
|
|
121
|
-
"geometry factor (cm2 sr)": [
|
|
122
|
-
"efficiency": [0.85, 0.75, 0.65],
|
|
123
|
-
"b": [0.015, 0.025, 0.035],
|
|
217
|
+
"species": ["h", "h", "he", "he"],
|
|
218
|
+
"lower energy (mev)": [1, 2, 1, 2],
|
|
219
|
+
"delta e (mev)": [0.15, 0.25, 0.35, 0.45],
|
|
220
|
+
"geometry factor (cm2 sr)": [15, 25, 35, 45],
|
|
221
|
+
"efficiency": [0.85, 0.75, 0.65, 0.55],
|
|
222
|
+
"b": [0.015, 0.025, 0.035, 0.045],
|
|
124
223
|
}
|
|
125
224
|
),
|
|
126
225
|
}
|
|
127
|
-
species = "h"
|
|
128
226
|
|
|
129
|
-
#
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
227
|
+
# Test for dynamic threshold state 0 and species "h"
|
|
228
|
+
result = get_species_ancillary_data(0, ancillary_data_frames, "h")
|
|
229
|
+
expected = {
|
|
230
|
+
"delta_e": np.array([[0.1], [0.2]]),
|
|
231
|
+
"geometry_factor": np.array([[10], [20]]),
|
|
232
|
+
"efficiency": np.array([[0.9], [0.8]]),
|
|
233
|
+
"b": np.array([[0.01], [0.02]]),
|
|
234
|
+
}
|
|
235
|
+
for key, value in expected.items():
|
|
236
|
+
np.testing.assert_array_equal(result[key], value)
|
|
237
|
+
|
|
238
|
+
# Test for dynamic threshold state 1 and species "he"
|
|
239
|
+
result = get_species_ancillary_data(1, ancillary_data_frames, "he")
|
|
240
|
+
expected = {
|
|
241
|
+
"delta_e": np.array([[0.35], [0.45]]),
|
|
242
|
+
"geometry_factor": np.array([[35], [45]]),
|
|
243
|
+
"efficiency": np.array([[0.65], [0.55]]),
|
|
244
|
+
"b": np.array([[0.035], [0.045]]),
|
|
245
|
+
}
|
|
246
|
+
for key in expected:
|
|
247
|
+
np.testing.assert_array_equal(result[key], expected[key])
|
|
248
|
+
|
|
249
|
+
|
|
250
|
+
def test_reshape_for_sectored():
|
|
251
|
+
"""
|
|
252
|
+
Test the reshape_for_sectored function.
|
|
253
|
+
"""
|
|
254
|
+
# Mock input data: 3D array (epoch, energy, declination)
|
|
255
|
+
np.random.seed(42) # Set a random seed for reproducibility
|
|
256
|
+
epoch, energy, declination = 2, 3, 8
|
|
257
|
+
input_array = np.random.rand(epoch, energy, declination)
|
|
258
|
+
|
|
259
|
+
# Expected output shape: 4D array (epoch, energy, azimuth, declination)
|
|
260
|
+
expected_shape = (epoch, energy, N_AZIMUTH, declination)
|
|
133
261
|
|
|
134
262
|
# Call the function
|
|
135
|
-
|
|
136
|
-
dynamic_threshold_state, ancillary_data_frames, species
|
|
137
|
-
)
|
|
263
|
+
reshaped_array = reshape_for_sectored(input_array)
|
|
138
264
|
|
|
139
265
|
# Assertions
|
|
140
|
-
|
|
266
|
+
assert reshaped_array.shape == expected_shape, "Output shape mismatch"
|
|
267
|
+
for azimuth in range(N_AZIMUTH):
|
|
268
|
+
np.testing.assert_array_equal(
|
|
269
|
+
reshaped_array[:, :, azimuth, :],
|
|
270
|
+
input_array,
|
|
271
|
+
err_msg=f"Mismatch in azimuth dimension {azimuth}",
|
|
272
|
+
)
|
|
141
273
|
|
|
142
274
|
|
|
143
275
|
def test_calculate_intensities_for_all_species():
|
|
@@ -214,15 +346,23 @@ def test_calculate_intensities_for_all_species():
|
|
|
214
346
|
)
|
|
215
347
|
|
|
216
348
|
# Call the function
|
|
217
|
-
calculate_intensities_for_all_species(
|
|
349
|
+
l2_dataset = calculate_intensities_for_all_species(
|
|
350
|
+
l2_dataset, ancillary_data_frames, valid_data_variables=["h", "ni"]
|
|
351
|
+
)
|
|
218
352
|
|
|
219
353
|
# Assertions
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
)
|
|
354
|
+
(
|
|
355
|
+
np.testing.assert_allclose(
|
|
356
|
+
l2_dataset["h"].values, expected_intensities_h.values
|
|
357
|
+
),
|
|
358
|
+
("Intensities mismatch for H"),
|
|
359
|
+
)
|
|
360
|
+
(
|
|
361
|
+
np.testing.assert_allclose(
|
|
362
|
+
l2_dataset["ni"].values, expected_intensities_ni.values
|
|
363
|
+
),
|
|
364
|
+
("Intensities mismatch for He"),
|
|
365
|
+
)
|
|
226
366
|
|
|
227
367
|
|
|
228
368
|
def test_calculate_intensities_for_a_species():
|
|
@@ -278,62 +418,176 @@ def test_calculate_intensities_for_a_species():
|
|
|
278
418
|
)
|
|
279
419
|
|
|
280
420
|
# Call the function
|
|
281
|
-
calculate_intensities_for_a_species(
|
|
421
|
+
l2_dataset = calculate_intensities_for_a_species(
|
|
282
422
|
species_variable, l2_dataset, ancillary_data_frames
|
|
283
423
|
)
|
|
284
424
|
|
|
285
425
|
# Assertions
|
|
286
|
-
|
|
287
|
-
l2_dataset["h"].values, expected_intensities.values
|
|
288
|
-
|
|
426
|
+
(
|
|
427
|
+
np.testing.assert_allclose(l2_dataset["h"].values, expected_intensities.values),
|
|
428
|
+
("Intensities mismatch"),
|
|
429
|
+
)
|
|
289
430
|
|
|
290
431
|
|
|
291
432
|
def test_calculate_intensities():
|
|
292
433
|
"""Test the calculate_intensities function."""
|
|
293
|
-
#
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
434
|
+
# Create sample function inputs
|
|
435
|
+
rates = xr.DataArray(
|
|
436
|
+
data=[10.0, 20.0, FILLVAL_FLOAT32, 40.0],
|
|
437
|
+
dims=["epoch"],
|
|
438
|
+
coords={"epoch": [0, 1, 2, 3]},
|
|
439
|
+
)
|
|
440
|
+
factors = xr.Dataset(
|
|
441
|
+
{
|
|
442
|
+
"delta_time": ("epoch", [60.0, 60.0, 60.0, 60.0]),
|
|
443
|
+
"delta_e": ("epoch", [1.0, 1.0, 1.0, 1.0]),
|
|
444
|
+
"geometry_factor": ("epoch", [2.0, 2.0, 2.0, 2.0]),
|
|
445
|
+
"efficiency": ("epoch", [0.5, 0.5, 0.5, 0.5]),
|
|
446
|
+
"b": ("epoch", [0.0, 0, 0, 0]),
|
|
447
|
+
}
|
|
448
|
+
)
|
|
299
449
|
|
|
300
450
|
# Expected output
|
|
301
|
-
|
|
302
|
-
[
|
|
451
|
+
expected_intensity = xr.DataArray(
|
|
452
|
+
data=[0.1666667, 0.3333333, FILLVAL_FLOAT32, 0.6666667],
|
|
453
|
+
dims=["epoch"],
|
|
454
|
+
coords={"epoch": [0, 1, 2, 3]},
|
|
303
455
|
)
|
|
304
456
|
|
|
305
457
|
# Call the function
|
|
306
|
-
|
|
307
|
-
rate, delta_e_factor, geometry_factor, efficiency, b
|
|
308
|
-
)
|
|
458
|
+
result = calculate_intensities(rates, factors)
|
|
309
459
|
|
|
310
460
|
# Assertions
|
|
311
|
-
|
|
312
|
-
intensities.values, expected_intensities.values
|
|
313
|
-
), "Intensities mismatch"
|
|
461
|
+
xr.testing.assert_allclose(result, expected_intensity)
|
|
314
462
|
|
|
315
463
|
|
|
316
464
|
def test_add_systematic_uncertainties():
|
|
317
465
|
"""Test the add_systematic_uncertainties function."""
|
|
318
466
|
# Create sample function inputs
|
|
467
|
+
np.random.seed(42) # Set a random seed for reproducibility
|
|
319
468
|
particle = "h"
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
469
|
+
datasets = [
|
|
470
|
+
xr.Dataset(
|
|
471
|
+
{"h": (("epoch", "h_energy_mean"), np.random.rand(2, 3).astype("float32"))}
|
|
472
|
+
),
|
|
473
|
+
xr.Dataset(
|
|
474
|
+
{
|
|
475
|
+
"h": (
|
|
476
|
+
("epoch", "h_energy_mean", "azimuth", "declination"),
|
|
477
|
+
np.random.rand(2, 3, 15, 8).astype("float32"),
|
|
478
|
+
)
|
|
479
|
+
}
|
|
480
|
+
),
|
|
324
481
|
]
|
|
325
|
-
|
|
482
|
+
|
|
483
|
+
for dataset in datasets:
|
|
484
|
+
# Call the function
|
|
485
|
+
updated_dataset = add_systematic_uncertainties(dataset, particle)
|
|
486
|
+
# Assertions
|
|
487
|
+
assert f"{particle}_sys_err_minus" in updated_dataset.data_vars
|
|
488
|
+
assert f"{particle}_sys_err_plus" in updated_dataset.data_vars
|
|
489
|
+
assert (
|
|
490
|
+
updated_dataset[f"{particle}_sys_err_minus"].shape
|
|
491
|
+
== dataset[particle].shape
|
|
492
|
+
)
|
|
493
|
+
assert (
|
|
494
|
+
updated_dataset[f"{particle}_sys_err_plus"].shape == dataset[particle].shape
|
|
495
|
+
)
|
|
496
|
+
np.testing.assert_array_equal(
|
|
497
|
+
updated_dataset[f"{particle}_sys_err_minus"].values, 0
|
|
498
|
+
)
|
|
499
|
+
np.testing.assert_array_equal(
|
|
500
|
+
updated_dataset[f"{particle}_sys_err_plus"].values, 0
|
|
501
|
+
)
|
|
502
|
+
|
|
503
|
+
|
|
504
|
+
def test_add_total_uncertainties():
|
|
505
|
+
# Create a sample dataset
|
|
506
|
+
np.random.seed(42) # Set a random seed for reproducibility
|
|
507
|
+
data = np.random.rand(10, 5).astype(np.float32)
|
|
508
|
+
stat_uncert_minus = np.random.rand(10, 5).astype(np.float32)
|
|
509
|
+
stat_uncert_plus = np.random.rand(10, 5).astype(np.float32)
|
|
510
|
+
sys_err_minus = np.zeros(
|
|
511
|
+
(10, 5), dtype=np.float32
|
|
512
|
+
) # zeros, unless changed during mission
|
|
513
|
+
sys_err_plus = np.zeros(
|
|
514
|
+
(10, 5), dtype=np.float32
|
|
515
|
+
) # zeros, unless changed during mission
|
|
516
|
+
|
|
517
|
+
dataset = xr.Dataset(
|
|
518
|
+
{
|
|
519
|
+
"particle": (("dim_0", "dim_1"), data),
|
|
520
|
+
"particle_stat_uncert_minus": (("dim_0", "dim_1"), stat_uncert_minus),
|
|
521
|
+
"particle_stat_uncert_plus": (("dim_0", "dim_1"), stat_uncert_plus),
|
|
522
|
+
"particle_sys_err_minus": (("dim_0", "dim_1"), sys_err_minus),
|
|
523
|
+
"particle_sys_err_plus": (("dim_0", "dim_1"), sys_err_plus),
|
|
524
|
+
}
|
|
525
|
+
)
|
|
326
526
|
|
|
327
527
|
# Call the function
|
|
328
|
-
|
|
528
|
+
updated_dataset = add_total_uncertainties(dataset, "particle")
|
|
329
529
|
|
|
330
530
|
# Assertions
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
531
|
+
np.testing.assert_array_almost_equal(
|
|
532
|
+
updated_dataset["particle_total_uncert_minus"].values,
|
|
533
|
+
np.sqrt(np.square(stat_uncert_minus) + np.square(sys_err_minus)),
|
|
534
|
+
)
|
|
535
|
+
np.testing.assert_array_almost_equal(
|
|
536
|
+
updated_dataset["particle_total_uncert_plus"].values,
|
|
537
|
+
np.sqrt(np.square(stat_uncert_plus) + np.square(sys_err_plus)),
|
|
538
|
+
)
|
|
539
|
+
|
|
540
|
+
# Check that the dimensions and attributes are preserved
|
|
541
|
+
assert (
|
|
542
|
+
updated_dataset["particle_total_uncert_minus"].dims == dataset["particle"].dims
|
|
543
|
+
)
|
|
544
|
+
assert (
|
|
545
|
+
updated_dataset["particle_total_uncert_plus"].dims == dataset["particle"].dims
|
|
546
|
+
)
|
|
547
|
+
|
|
548
|
+
|
|
549
|
+
def test_process_sectored_intensity_data(l1b_sectored_rates_dataset):
|
|
550
|
+
"""Test the variables in the sectored intensity dataset"""
|
|
551
|
+
|
|
552
|
+
l2_sectored_intensity_dataset = process_sectored_intensity_data(
|
|
553
|
+
l1b_sectored_rates_dataset
|
|
554
|
+
)
|
|
555
|
+
|
|
556
|
+
# Check that a xarray dataset is returned
|
|
557
|
+
assert isinstance(l2_sectored_intensity_dataset, xr.Dataset)
|
|
558
|
+
|
|
559
|
+
valid_coords = {
|
|
560
|
+
"epoch",
|
|
561
|
+
"azimuth",
|
|
562
|
+
"declination",
|
|
563
|
+
"h_energy_mean",
|
|
564
|
+
"he4_energy_mean",
|
|
565
|
+
"cno_energy_mean",
|
|
566
|
+
"nemgsi_energy_mean",
|
|
567
|
+
"fe_energy_mean",
|
|
568
|
+
}
|
|
569
|
+
|
|
570
|
+
# Check that the dataset has the correct coords and variables
|
|
571
|
+
assert valid_coords == set(l2_sectored_intensity_dataset.coords), (
|
|
572
|
+
"Coordinates mismatch"
|
|
573
|
+
)
|
|
574
|
+
|
|
575
|
+
assert "dynamic_threshold_state" in l2_sectored_intensity_dataset.data_vars
|
|
576
|
+
|
|
577
|
+
for particle in VALID_SECTORED_SPECIES:
|
|
578
|
+
assert f"{particle}" in l2_sectored_intensity_dataset.data_vars
|
|
579
|
+
assert (
|
|
580
|
+
f"{particle}_stat_uncert_minus" in l2_sectored_intensity_dataset.data_vars
|
|
581
|
+
)
|
|
582
|
+
assert f"{particle}_stat_uncert_plus" in l2_sectored_intensity_dataset.data_vars
|
|
583
|
+
assert f"{particle}_sys_err_minus" in l2_sectored_intensity_dataset.data_vars
|
|
584
|
+
assert f"{particle}_sys_err_plus" in l2_sectored_intensity_dataset.data_vars
|
|
585
|
+
assert (
|
|
586
|
+
f"{particle}_energy_delta_minus" in l2_sectored_intensity_dataset.data_vars
|
|
587
|
+
)
|
|
588
|
+
assert (
|
|
589
|
+
f"{particle}_energy_delta_plus" in l2_sectored_intensity_dataset.data_vars
|
|
590
|
+
)
|
|
337
591
|
|
|
338
592
|
|
|
339
593
|
def test_process_summed_intensity_data(l1b_summed_rates_dataset):
|
|
@@ -368,18 +622,20 @@ def test_process_summed_intensity_data(l1b_summed_rates_dataset):
|
|
|
368
622
|
}
|
|
369
623
|
|
|
370
624
|
# Check that the dataset has the correct coords and variables
|
|
371
|
-
assert valid_coords == set(
|
|
372
|
-
|
|
373
|
-
)
|
|
625
|
+
assert valid_coords == set(l2_summed_intensity_dataset.coords), (
|
|
626
|
+
"Coordinates mismatch"
|
|
627
|
+
)
|
|
374
628
|
|
|
375
629
|
assert "dynamic_threshold_state" in l1b_summed_rates_dataset.data_vars
|
|
376
630
|
|
|
377
|
-
for particle in
|
|
631
|
+
for particle in SUMMED_PARTICLE_ENERGY_RANGE_MAPPING.keys():
|
|
378
632
|
assert f"{particle}" in l2_summed_intensity_dataset.data_vars
|
|
379
|
-
assert f"{particle}
|
|
380
|
-
assert f"{particle}
|
|
381
|
-
assert f"{particle}
|
|
382
|
-
assert f"{particle}
|
|
633
|
+
assert f"{particle}_stat_uncert_minus" in l2_summed_intensity_dataset.data_vars
|
|
634
|
+
assert f"{particle}_stat_uncert_plus" in l2_summed_intensity_dataset.data_vars
|
|
635
|
+
assert f"{particle}_sys_err_minus" in l2_summed_intensity_dataset.data_vars
|
|
636
|
+
assert f"{particle}_sys_err_plus" in l2_summed_intensity_dataset.data_vars
|
|
637
|
+
assert f"{particle}_energy_delta_minus" in l2_summed_intensity_dataset.data_vars
|
|
638
|
+
assert f"{particle}_energy_delta_plus" in l2_summed_intensity_dataset.data_vars
|
|
383
639
|
|
|
384
640
|
|
|
385
641
|
def test_process_standard_intensity_data(l1b_standard_rates_dataset):
|
|
@@ -414,18 +670,20 @@ def test_process_standard_intensity_data(l1b_standard_rates_dataset):
|
|
|
414
670
|
}
|
|
415
671
|
|
|
416
672
|
# Check that the dataset has the correct coords and variables
|
|
417
|
-
assert valid_coords == set(
|
|
418
|
-
|
|
419
|
-
)
|
|
673
|
+
assert valid_coords == set(l2_standard_intensity_dataset.coords), (
|
|
674
|
+
"Coordinates mismatch"
|
|
675
|
+
)
|
|
420
676
|
|
|
421
677
|
assert "dynamic_threshold_state" in l1b_standard_rates_dataset.data_vars
|
|
422
678
|
|
|
423
679
|
for particle in STANDARD_PARTICLE_ENERGY_RANGE_MAPPING.keys():
|
|
424
680
|
assert f"{particle}" in l2_standard_intensity_dataset.data_vars
|
|
425
|
-
assert
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
assert f"{particle}
|
|
681
|
+
assert (
|
|
682
|
+
f"{particle}_stat_uncert_minus" in l2_standard_intensity_dataset.data_vars
|
|
683
|
+
)
|
|
684
|
+
assert f"{particle}_stat_uncert_plus" in l2_standard_intensity_dataset.data_vars
|
|
685
|
+
assert f"{particle}_sys_err_minus" in l2_standard_intensity_dataset.data_vars
|
|
686
|
+
assert f"{particle}_sys_err_plus" in l2_standard_intensity_dataset.data_vars
|
|
429
687
|
assert (
|
|
430
688
|
f"{particle}_energy_delta_minus" in l2_standard_intensity_dataset.data_vars
|
|
431
689
|
)
|
|
@@ -445,10 +703,14 @@ def test_hit_l2(dependencies):
|
|
|
445
703
|
Dictionary of L1B datasets
|
|
446
704
|
"""
|
|
447
705
|
# TODO: update assertions after science data processing is completed
|
|
448
|
-
l2_datasets = hit_l2(dependencies["imap_hit_l1b_summed-rates"]
|
|
706
|
+
l2_datasets = hit_l2(dependencies["imap_hit_l1b_summed-rates"])
|
|
449
707
|
assert len(l2_datasets) == 1
|
|
450
708
|
assert l2_datasets[0].attrs["Logical_source"] == "imap_hit_l2_summed-intensity"
|
|
451
709
|
|
|
452
|
-
l2_datasets = hit_l2(dependencies["imap_hit_l1b_standard-rates"]
|
|
710
|
+
l2_datasets = hit_l2(dependencies["imap_hit_l1b_standard-rates"])
|
|
453
711
|
assert len(l2_datasets) == 1
|
|
454
712
|
assert l2_datasets[0].attrs["Logical_source"] == "imap_hit_l2_standard-intensity"
|
|
713
|
+
|
|
714
|
+
l2_datasets = hit_l2(dependencies["imap_hit_l1b_sectored-rates"])
|
|
715
|
+
assert len(l2_datasets) == 1
|
|
716
|
+
assert l2_datasets[0].attrs["Logical_source"] == "imap_hit_l2_macropixel-intensity"
|