dkist-processing-common 14.3.0__tar.gz → 14.3.1__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.
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/CHANGELOG.rst +11 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/PKG-INFO +1 -1
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/quality.py +16 -1
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/l1_output_data.py +1 -6
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/quality/_base.py +0 -13
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/quality/_metrics.py +5 -41
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/quality_metrics.py +40 -10
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_quality.py +42 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_quality_mixin.py +5 -46
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common.egg-info/PKG-INFO +1 -1
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/.gitignore +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/.pre-commit-config.yaml +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/.readthedocs.yml +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/.rovodev/.review-agent.md +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/.snyk +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/README.rst +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/bitbucket-pipelines.yml +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/changelog/.gitempty +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/_util/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/_util/constants.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/_util/graphql.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/_util/scratch.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/_util/tags.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/array.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/asdf.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/basemodel.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/bytes.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/fits.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/iobase.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/json.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/path.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/quality.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/codecs/str.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/config.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/fonts/Lato-Regular.ttf +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/fonts/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/manual.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/constants.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/dkist_location.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/extras.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/fits_access.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/flower_pot.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/fried_parameter.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/graphql.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/input_dataset.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/message.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/message_queue_binding.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/metric_code.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/parameters.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/tags.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/task_name.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/telemetry.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/models/wavelength.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/average_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/cs_step.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/dsps_repeat.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/experiment_id_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/id_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/l0_fits_access.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/l1_fits_access.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/lookup_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/near_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/observing_program_id_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/proposal_id_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/quality.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/retarder.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/single_value_single_key_flower.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/task.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/time.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/unique_bud.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/parsers/wavelength.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/assemble_movie.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/base.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/globus.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/interservice_bus.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/metadata_store.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/object_store.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/mixin/quality/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/output_data_base.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/parse_l0_input_data.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/teardown.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/transfer_input_data.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/trial_catalog.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/trial_output_data.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/write_extra.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/write_l1.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tasks/write_l1_base.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/__init__.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/conftest.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/mock_metadata_store.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_assemble_movie.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_assemble_quality.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_base.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_codecs.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_constants.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_construct_dataset_extras.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_cs_step.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_dkist_location.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_fits_access.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_flower_pot.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_fried_parameter.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_input_dataset.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_interservice_bus.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_interservice_bus_mixin.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_manual_processing.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_output_data_base.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_parameters.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_parse_l0_input_data.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_publish_catalog_messages.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_scratch.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_stems.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_submit_dataset_metadata.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_tags.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_task_name.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_task_parsing.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_teardown.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_transfer_input_data.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_transfer_l1_output_data.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_trial_catalog.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_trial_output_data.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_workflow_task_base.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/tests/test_write_l1.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common.egg-info/SOURCES.txt +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common.egg-info/dependency_links.txt +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common.egg-info/requires.txt +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common.egg-info/top_level.txt +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/docs/Makefile +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/docs/changelog.rst +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/docs/conf.py +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/docs/index.rst +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/docs/landing_page.rst +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/docs/make.bat +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/docs/requirements.txt +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/licenses/LICENSE.rst +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/pyproject.toml +0 -0
- {dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/setup.cfg +0 -0
|
@@ -1,3 +1,14 @@
|
|
|
1
|
+
v14.3.1 (2026-05-19)
|
|
2
|
+
====================
|
|
3
|
+
|
|
4
|
+
Misc
|
|
5
|
+
----
|
|
6
|
+
|
|
7
|
+
- Migrate `_find_iqr_outliers` from the quality mixin to the `QualityL0Metrics` workflow task. (`#340 <https://bitbucket.org/dkistdc/dkist-processing-common/pull-requests/340>`__)
|
|
8
|
+
- Migrate `quality_task_types` from the quality mixin to the `QualityL0Metrics` workflow task. (`#341 <https://bitbucket.org/dkistdc/dkist-processing-common/pull-requests/341>`__)
|
|
9
|
+
- Migrate `_format_facet` from the quality mixin to the `QualityMetric` `BaseModel`. (`#342 <https://bitbucket.org/dkistdc/dkist-processing-common/pull-requests/342>`__)
|
|
10
|
+
|
|
11
|
+
|
|
1
12
|
v14.3.0 (2026-05-19)
|
|
2
13
|
====================
|
|
3
14
|
|
|
@@ -333,13 +333,28 @@ class EfficiencyData(QualityModel):
|
|
|
333
333
|
pass
|
|
334
334
|
|
|
335
335
|
|
|
336
|
+
def format_facet(v: Any) -> Any:
|
|
337
|
+
"""Format the string input as a typical key. For example, `Beam 1` becomes `BEAM_1`."""
|
|
338
|
+
if v is None:
|
|
339
|
+
return None
|
|
340
|
+
if isinstance(v, str) and v.strip() == "":
|
|
341
|
+
return None
|
|
342
|
+
return str(v).replace(" ", "_").upper()
|
|
343
|
+
|
|
344
|
+
|
|
345
|
+
QualityFacet = Annotated[
|
|
346
|
+
str | None,
|
|
347
|
+
BeforeValidator(format_facet),
|
|
348
|
+
]
|
|
349
|
+
|
|
350
|
+
|
|
336
351
|
class QualityMetric(QualityModel):
|
|
337
352
|
"""Quality Metric."""
|
|
338
353
|
|
|
339
354
|
name: str
|
|
340
355
|
description: str
|
|
341
356
|
metric_code: str
|
|
342
|
-
facet:
|
|
357
|
+
facet: QualityFacet = None
|
|
343
358
|
statement: list[str] | None = None
|
|
344
359
|
plot_data: list[XYData] | None = None
|
|
345
360
|
multi_plot_data: list[MultiPlotData] | None = None
|
|
@@ -158,12 +158,7 @@ class TransferL1Data(TransferDataBase, GlobusMixin):
|
|
|
158
158
|
|
|
159
159
|
|
|
160
160
|
class AssembleQualityData(L1OutputDataBase, QualityMixin):
|
|
161
|
-
"""
|
|
162
|
-
Assemble quality data from the various quality metrics.
|
|
163
|
-
|
|
164
|
-
**NOTE:** Please set `~dkist_processing_common.tasks.mixin.quality.QualityMixin.quality_task_types` in any subclass
|
|
165
|
-
to the same value that was used in a subclass of `~dkist_processing_common.tasks.quality_metrics.QualityL0Metrics`.
|
|
166
|
-
"""
|
|
161
|
+
"""Assemble quality data from the various quality metrics."""
|
|
167
162
|
|
|
168
163
|
@property
|
|
169
164
|
def polcal_label_list(self) -> list[str] | None:
|
|
@@ -5,14 +5,11 @@ from typing import Iterable
|
|
|
5
5
|
from dkist_processing_common.codecs.json import json_encoder
|
|
6
6
|
from dkist_processing_common.codecs.quality import QualityValueEncoder
|
|
7
7
|
from dkist_processing_common.models.tags import Tag
|
|
8
|
-
from dkist_processing_common.models.task_name import TaskName
|
|
9
8
|
from dkist_processing_common.tasks.mixin.quality._metrics import _PolcalQualityMixin
|
|
10
|
-
from dkist_processing_common.tasks.mixin.quality._metrics import _SimplePlotQualityMixin
|
|
11
9
|
from dkist_processing_common.tasks.mixin.quality._metrics import _WavecalQualityMixin
|
|
12
10
|
|
|
13
11
|
|
|
14
12
|
class QualityMixin(
|
|
15
|
-
_SimplePlotQualityMixin,
|
|
16
13
|
_PolcalQualityMixin,
|
|
17
14
|
_WavecalQualityMixin,
|
|
18
15
|
):
|
|
@@ -46,16 +43,6 @@ class QualityMixin(
|
|
|
46
43
|
|
|
47
44
|
return result
|
|
48
45
|
|
|
49
|
-
@property
|
|
50
|
-
def quality_task_types(self) -> list[str]:
|
|
51
|
-
"""Task types to use in generating metrics that work on several task types."""
|
|
52
|
-
return [
|
|
53
|
-
TaskName.dark.value,
|
|
54
|
-
TaskName.gain.value,
|
|
55
|
-
TaskName.lamp_gain.value,
|
|
56
|
-
TaskName.solar_gain.value,
|
|
57
|
-
]
|
|
58
|
-
|
|
59
46
|
@property
|
|
60
47
|
def quality_metrics_no_task_dependence(self) -> dict:
|
|
61
48
|
"""Return a dict of the quality metrics with no task dependence."""
|
|
@@ -6,8 +6,6 @@ These classes should not be directly mixed in to anything. They are pre-mixed in
|
|
|
6
6
|
import copy
|
|
7
7
|
import json
|
|
8
8
|
import logging
|
|
9
|
-
from datetime import datetime
|
|
10
|
-
from typing import Sequence
|
|
11
9
|
|
|
12
10
|
import astropy.units as u
|
|
13
11
|
import numpy as np
|
|
@@ -29,39 +27,12 @@ from dkist_processing_common.models.quality import PlotRaincloud
|
|
|
29
27
|
from dkist_processing_common.models.quality import ReportMetric
|
|
30
28
|
from dkist_processing_common.models.quality import SimpleTable
|
|
31
29
|
from dkist_processing_common.models.quality import VerticalMultiPanePlot2D
|
|
30
|
+
from dkist_processing_common.models.quality import format_facet
|
|
32
31
|
from dkist_processing_common.models.tags import Tag
|
|
33
32
|
|
|
34
33
|
logger = logging.getLogger(__name__)
|
|
35
34
|
|
|
36
35
|
|
|
37
|
-
class _SimplePlotQualityMixin:
|
|
38
|
-
"""Mixin containing metrics that present as simple x/y plots."""
|
|
39
|
-
|
|
40
|
-
@staticmethod
|
|
41
|
-
def _find_iqr_outliers(datetimes: Sequence[datetime], values: Sequence[float]) -> list[str]:
|
|
42
|
-
"""
|
|
43
|
-
Given a list of values, find values that fall more than (1.5 * iqr) outside the quartiles of the data.
|
|
44
|
-
|
|
45
|
-
Parameters
|
|
46
|
-
----------
|
|
47
|
-
datetimes: list of datetime strings used to reference the files that are outliers
|
|
48
|
-
values: values to use to determine outliers from the iqr
|
|
49
|
-
"""
|
|
50
|
-
if len(values) == 0:
|
|
51
|
-
raise ValueError("No values provided.")
|
|
52
|
-
warnings = []
|
|
53
|
-
q1 = np.quantile(values, 0.25)
|
|
54
|
-
q3 = np.quantile(values, 0.75)
|
|
55
|
-
iqr = q3 - q1
|
|
56
|
-
for i, val in enumerate(values):
|
|
57
|
-
if val < q1 - (iqr * 1.5) or val > q3 + (iqr * 1.5):
|
|
58
|
-
warnings.append(
|
|
59
|
-
f"File with datetime {datetimes[i]} has a value considered to be an outlier "
|
|
60
|
-
f"for this metric"
|
|
61
|
-
)
|
|
62
|
-
return warnings
|
|
63
|
-
|
|
64
|
-
|
|
65
36
|
class _PolcalQualityMixin:
|
|
66
37
|
"""Mixin Class supporting the building of polcal-specific metrics."""
|
|
67
38
|
|
|
@@ -112,13 +83,6 @@ class _PolcalQualityMixin:
|
|
|
112
83
|
thinning_stride=thinning_stride,
|
|
113
84
|
)
|
|
114
85
|
|
|
115
|
-
@staticmethod
|
|
116
|
-
def _format_facet(label: str | None) -> str | None:
|
|
117
|
-
"""Format the label as a typical key. For example, `Beam 1` becomes `BEAM_1`."""
|
|
118
|
-
if label is None or label == "":
|
|
119
|
-
return None
|
|
120
|
-
return str(label).replace(" ", "_").upper()
|
|
121
|
-
|
|
122
86
|
@staticmethod
|
|
123
87
|
def _compute_thinning_stride(
|
|
124
88
|
polcal_fitter: PolcalFitter, num_points_to_sample: int
|
|
@@ -340,7 +304,7 @@ class _PolcalQualityMixin:
|
|
|
340
304
|
description="The deviation from database metrology values for Calibration Unit parameters used to compute "
|
|
341
305
|
f"demodulation matrices. These parameters are fit the same across all polcal bins.",
|
|
342
306
|
metric_code=MetricCode.polcal_global_par_vals,
|
|
343
|
-
facet=
|
|
307
|
+
facet=format_facet(label),
|
|
344
308
|
table_data=SimpleTable(rows=table_data),
|
|
345
309
|
warnings=self._format_warnings(data["warnings"]),
|
|
346
310
|
)
|
|
@@ -481,7 +445,7 @@ class _PolcalQualityMixin:
|
|
|
481
445
|
name=f"PolCal Local Bin Fits - {label}",
|
|
482
446
|
description=description,
|
|
483
447
|
metric_code=MetricCode.polcal_local_par_vals,
|
|
484
|
-
facet=
|
|
448
|
+
facet=format_facet(label),
|
|
485
449
|
modmat_data=modmat_hist,
|
|
486
450
|
histogram_data=param_histograms,
|
|
487
451
|
)
|
|
@@ -601,7 +565,7 @@ class _PolcalQualityMixin:
|
|
|
601
565
|
name=f"PolCal Fit Residuals - {label}",
|
|
602
566
|
description=description,
|
|
603
567
|
metric_code=MetricCode.polcal_fit_residuals,
|
|
604
|
-
facet=
|
|
568
|
+
facet=format_facet(label),
|
|
605
569
|
histogram_data=chisq_hist,
|
|
606
570
|
raincloud_data=residual_series,
|
|
607
571
|
)
|
|
@@ -675,7 +639,7 @@ class _PolcalQualityMixin:
|
|
|
675
639
|
name=f"PolCal Modulation Efficiency - {label}",
|
|
676
640
|
description=description,
|
|
677
641
|
metric_code=MetricCode.polcal_efficiency,
|
|
678
|
-
facet=
|
|
642
|
+
facet=format_facet(label),
|
|
679
643
|
efficiency_data=EfficiencyHistograms(efficiency_list=data["efficiency_list"]),
|
|
680
644
|
warnings=self._format_warnings(data["warnings"]),
|
|
681
645
|
)
|
|
@@ -5,6 +5,7 @@ from collections import defaultdict
|
|
|
5
5
|
from datetime import datetime
|
|
6
6
|
from itertools import chain
|
|
7
7
|
from typing import Iterable
|
|
8
|
+
from typing import Sequence
|
|
8
9
|
from typing import Type
|
|
9
10
|
|
|
10
11
|
import numpy as np
|
|
@@ -23,6 +24,7 @@ from dkist_processing_common.models.quality import TableData
|
|
|
23
24
|
from dkist_processing_common.models.quality import TimeSeriesData
|
|
24
25
|
from dkist_processing_common.models.quality import XYData
|
|
25
26
|
from dkist_processing_common.models.tags import Tag
|
|
27
|
+
from dkist_processing_common.models.task_name import TaskName
|
|
26
28
|
from dkist_processing_common.parsers.l0_fits_access import L0FitsAccess
|
|
27
29
|
from dkist_processing_common.parsers.quality import L1QualityFitsAccess
|
|
28
30
|
from dkist_processing_common.tasks.base import WorkflowTaskBase
|
|
@@ -76,20 +78,14 @@ class QualityL0Metrics(WorkflowTaskBase, QualityMixin):
|
|
|
76
78
|
instruments this can be left as the default `Tag.input()`, but IR cameras will probably want to set this to
|
|
77
79
|
`Tag.linearized()` or similar.
|
|
78
80
|
|
|
79
|
-
|
|
81
|
+
`quality_task_types` (`list[str]`)
|
|
80
82
|
A list of IPTASK types. A separate set of L0 metrics will be reported for each task type listed here.
|
|
81
|
-
|
|
82
|
-
sensible defaults. If overloading, please use controlled `~dkist_processing_common.models.task_name.TaskName`
|
|
83
|
-
values, if possible.
|
|
83
|
+
If overloading, please use controlled `~dkist_processing_common.models.task_name.TaskName` values, if possible.
|
|
84
84
|
|
|
85
85
|
`modstate_list` (`list[int] | None`)
|
|
86
86
|
A list of modstates over which to separate each metric. Adding modstates does not create new metric entries, but
|
|
87
87
|
does sub-divide each TASK's metric into modstate bins. If you want *all* files of a single TASK to be considered
|
|
88
88
|
together return ``None`` here.
|
|
89
|
-
|
|
90
|
-
**NOTE:** The `~dkist_processing_common.tasks.mixin.quality.QualityMixin.quality_task_types` on an instrument
|
|
91
|
-
subclass of `~dkist_processing_common.tasks.l1_output_data.AssembleQualityData` should match whatever is set here
|
|
92
|
-
(although in both cases the default is probably fine).
|
|
93
89
|
"""
|
|
94
90
|
|
|
95
91
|
@property
|
|
@@ -115,6 +111,40 @@ class QualityL0Metrics(WorkflowTaskBase, QualityMixin):
|
|
|
115
111
|
"""Define the `FitsAccess`-type class used to parse the headers of L0 frames."""
|
|
116
112
|
return L0FitsAccess
|
|
117
113
|
|
|
114
|
+
@property
|
|
115
|
+
def quality_task_types(self) -> list[str]:
|
|
116
|
+
"""Task types to use in generating metrics that work on several task types."""
|
|
117
|
+
return [
|
|
118
|
+
TaskName.dark.value,
|
|
119
|
+
TaskName.gain.value,
|
|
120
|
+
TaskName.lamp_gain.value,
|
|
121
|
+
TaskName.solar_gain.value,
|
|
122
|
+
]
|
|
123
|
+
|
|
124
|
+
@staticmethod
|
|
125
|
+
def _find_iqr_outliers(datetimes: Sequence[datetime], values: Sequence[float]) -> list[str]:
|
|
126
|
+
"""
|
|
127
|
+
Given a list of values, find values that fall more than (1.5 * iqr) outside the quartiles of the data.
|
|
128
|
+
|
|
129
|
+
Parameters
|
|
130
|
+
----------
|
|
131
|
+
datetimes: list of datetime strings used to reference the files that are outliers
|
|
132
|
+
values: values to use to determine outliers from the iqr
|
|
133
|
+
"""
|
|
134
|
+
if len(values) == 0:
|
|
135
|
+
raise ValueError("No values provided.")
|
|
136
|
+
warnings = []
|
|
137
|
+
q1 = np.quantile(values, 0.25)
|
|
138
|
+
q3 = np.quantile(values, 0.75)
|
|
139
|
+
iqr = q3 - q1
|
|
140
|
+
for i, val in enumerate(values):
|
|
141
|
+
if val < q1 - (iqr * 1.5) or val > q3 + (iqr * 1.5):
|
|
142
|
+
warnings.append(
|
|
143
|
+
f"File with datetime {datetimes[i]} has a value considered to be an outlier "
|
|
144
|
+
f"for this metric"
|
|
145
|
+
)
|
|
146
|
+
return warnings
|
|
147
|
+
|
|
118
148
|
def run(self) -> None:
|
|
119
149
|
"""
|
|
120
150
|
Calculate L0 quality metrics for all TASK/MODSTATE combinations.
|
|
@@ -316,7 +346,7 @@ class QualityL0Metrics(WorkflowTaskBase, QualityMixin):
|
|
|
316
346
|
name=f"Average Across Frame - {task_type.upper()}",
|
|
317
347
|
description=f"Average intensity value across frames of task type {task_type}. One measurement is taken per frame in each task type.",
|
|
318
348
|
metric_code=MetricCode.frame_average,
|
|
319
|
-
facet=task_type
|
|
349
|
+
facet=task_type,
|
|
320
350
|
plot_data=[xy_data],
|
|
321
351
|
warnings=warnings,
|
|
322
352
|
)
|
|
@@ -361,7 +391,7 @@ class QualityL0Metrics(WorkflowTaskBase, QualityMixin):
|
|
|
361
391
|
name=f"Root Mean Square (RMS) Across Frame - {task_type.upper()}",
|
|
362
392
|
description=f"RMS value across frames of task type {task_type}. One measurement is taken per frame in each task type.",
|
|
363
393
|
metric_code=MetricCode.frame_rms,
|
|
364
|
-
facet=task_type
|
|
394
|
+
facet=task_type,
|
|
365
395
|
plot_data=[xy_data],
|
|
366
396
|
warnings=warnings,
|
|
367
397
|
)
|
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
from datetime import datetime
|
|
4
4
|
from datetime import timedelta
|
|
5
5
|
from pathlib import Path
|
|
6
|
+
from typing import Any
|
|
6
7
|
from typing import Sequence
|
|
7
8
|
|
|
8
9
|
import numpy as np
|
|
@@ -18,6 +19,7 @@ from dkist_processing_common.codecs.fits import fits_hdulist_encoder
|
|
|
18
19
|
from dkist_processing_common.models.quality import QualityMetric
|
|
19
20
|
from dkist_processing_common.models.quality import TableData
|
|
20
21
|
from dkist_processing_common.models.quality import XYData
|
|
22
|
+
from dkist_processing_common.models.quality import format_facet
|
|
21
23
|
from dkist_processing_common.models.tags import Tag
|
|
22
24
|
from dkist_processing_common.models.task_name import TaskName
|
|
23
25
|
from dkist_processing_common.tasks.quality_metrics import L0QualityData
|
|
@@ -1126,3 +1128,43 @@ def test_no_calibration_frames_no_l1_metrics(quality_l1_task_no_scratch_data: Qu
|
|
|
1126
1128
|
task.read(tags=tags, decoder=basemodel_decoder, model=QualityMetric)
|
|
1127
1129
|
)
|
|
1128
1130
|
assert len(metrics) == 0
|
|
1131
|
+
|
|
1132
|
+
|
|
1133
|
+
def test_find_iqr_outliers(quality_l0_task):
|
|
1134
|
+
"""
|
|
1135
|
+
Given: a list of float values
|
|
1136
|
+
When: checking data for outliers
|
|
1137
|
+
Then: the correct outliers are found
|
|
1138
|
+
"""
|
|
1139
|
+
task = quality_l0_task
|
|
1140
|
+
start = datetime.now()
|
|
1141
|
+
datetimes = tuple([start + timedelta(milliseconds=i) for i in range(5)])
|
|
1142
|
+
values = [5.1, 4.9, 9.3, 5.3, 4.9]
|
|
1143
|
+
warnings = task._find_iqr_outliers(datetimes=datetimes, values=values)
|
|
1144
|
+
assert warnings == [
|
|
1145
|
+
f"File with datetime {datetimes[2]} has a value considered to be an outlier for this metric"
|
|
1146
|
+
]
|
|
1147
|
+
|
|
1148
|
+
|
|
1149
|
+
@pytest.mark.parametrize(
|
|
1150
|
+
"label, expected_result",
|
|
1151
|
+
[
|
|
1152
|
+
pytest.param(None, None, id="none"),
|
|
1153
|
+
pytest.param("", None, id="empty"),
|
|
1154
|
+
pytest.param("abc", "ABC", id="lower"),
|
|
1155
|
+
pytest.param("XYZ", "XYZ", id="upper"),
|
|
1156
|
+
pytest.param("lMn", "LMN", id="mixed"),
|
|
1157
|
+
pytest.param("heLLo 1 abc", "HELLO_1__ABC", id="spaces"),
|
|
1158
|
+
pytest.param(0, "0", id="zero"),
|
|
1159
|
+
pytest.param(1, "1", id="one"),
|
|
1160
|
+
pytest.param(False, "FALSE", id="false"),
|
|
1161
|
+
pytest.param("@,$#", "@,$#", id="random"),
|
|
1162
|
+
],
|
|
1163
|
+
)
|
|
1164
|
+
def test_format_facet(label: str | Any, expected_result: str):
|
|
1165
|
+
"""
|
|
1166
|
+
Given: A label
|
|
1167
|
+
When: formatting the label as a key
|
|
1168
|
+
Then: the label is properly formatted
|
|
1169
|
+
"""
|
|
1170
|
+
assert format_facet(label) == expected_result
|
|
@@ -1,6 +1,4 @@
|
|
|
1
1
|
import json
|
|
2
|
-
from datetime import datetime
|
|
3
|
-
from datetime import timedelta
|
|
4
2
|
from io import StringIO
|
|
5
3
|
from typing import Any
|
|
6
4
|
|
|
@@ -19,6 +17,7 @@ from dkist_processing_common.codecs.quality import QualityValueEncoder
|
|
|
19
17
|
from dkist_processing_common.models.metric_code import MetricCode
|
|
20
18
|
from dkist_processing_common.models.quality import Plot2D
|
|
21
19
|
from dkist_processing_common.models.quality import VerticalMultiPanePlot2D
|
|
20
|
+
from dkist_processing_common.models.quality import format_facet
|
|
22
21
|
from dkist_processing_common.models.tags import Tag
|
|
23
22
|
from dkist_processing_common.tasks import WorkflowTaskBase
|
|
24
23
|
from dkist_processing_common.tasks.mixin.quality import QualityMixin
|
|
@@ -81,22 +80,6 @@ def test_format_warnings(quality_mixin_task):
|
|
|
81
80
|
assert warnings is None
|
|
82
81
|
|
|
83
82
|
|
|
84
|
-
def test_find_iqr_outliers(quality_mixin_task):
|
|
85
|
-
"""
|
|
86
|
-
Given: a task with the QualityMixin
|
|
87
|
-
When: checking data for outliers
|
|
88
|
-
Then: the correct outliers are found
|
|
89
|
-
"""
|
|
90
|
-
task = quality_mixin_task
|
|
91
|
-
start = datetime.now()
|
|
92
|
-
datetimes = tuple([start + timedelta(milliseconds=i) for i in range(5)])
|
|
93
|
-
values = [5.1, 4.9, 9.3, 5.3, 4.9]
|
|
94
|
-
warnings = task._find_iqr_outliers(datetimes=datetimes, values=values)
|
|
95
|
-
assert warnings == [
|
|
96
|
-
f"File with datetime {datetimes[2]} has a value considered to be an outlier for this metric"
|
|
97
|
-
]
|
|
98
|
-
|
|
99
|
-
|
|
100
83
|
@pytest.mark.parametrize(
|
|
101
84
|
"thin, samples_larger_than_total",
|
|
102
85
|
[
|
|
@@ -362,7 +345,7 @@ def test_polcal_build_global_parameter_values(quality_mixin_task, polcal_global_
|
|
|
362
345
|
|
|
363
346
|
assert metric["name"] == f"PolCal Global Calibration Unit Fit - {label}"
|
|
364
347
|
assert metric["metric_code"] == "POLCAL_GLOBAL_PAR_VALS"
|
|
365
|
-
assert metric["facet"] ==
|
|
348
|
+
assert metric["facet"] == format_facet(label)
|
|
366
349
|
assert metric["warnings"] == ["A thing is bad"]
|
|
367
350
|
metric_table = metric["table_data"]["rows"]
|
|
368
351
|
assert len(metric_table) == 4 # 3 rows + one for header
|
|
@@ -416,7 +399,7 @@ def test_polcal_build_local_parameter_values(quality_mixin_task, polcal_local_pa
|
|
|
416
399
|
|
|
417
400
|
assert metric["name"] == f"PolCal Local Bin Fits - {label}"
|
|
418
401
|
assert metric["metric_code"] == "POLCAL_LOCAL_PAR_VALS"
|
|
419
|
-
assert metric["facet"] ==
|
|
402
|
+
assert metric["facet"] == format_facet(label)
|
|
420
403
|
assert metric["description"].endswith(
|
|
421
404
|
"Data show 3 uniformly sampled points from 6 total points spanning 2 spatial and 3 radical bins."
|
|
422
405
|
)
|
|
@@ -468,7 +451,7 @@ def test_polcal_build_fit_residuals(quality_mixin_task, polcal_fit_residuals_jso
|
|
|
468
451
|
|
|
469
452
|
assert metric["name"] == f"PolCal Fit Residuals - {label}"
|
|
470
453
|
assert metric["metric_code"] == "POLCAL_FIT_RESIDUALS"
|
|
471
|
-
assert metric["facet"] ==
|
|
454
|
+
assert metric["facet"] == format_facet(label)
|
|
472
455
|
|
|
473
456
|
assert metric["description"].endswith(
|
|
474
457
|
"Data show 3 uniformly sampled points from 6 total points spanning 21 financial bins."
|
|
@@ -521,7 +504,7 @@ def test_polcal_build_efficiency(quality_mixin_task, polcal_efficiency_json):
|
|
|
521
504
|
"Data show 33 uniformly sampled points from 99 total points spanning 2 spatial, 4 forever, and 6 smelly bins."
|
|
522
505
|
)
|
|
523
506
|
assert metric["metric_code"] == "POLCAL_EFFICIENCY"
|
|
524
|
-
assert metric["facet"] ==
|
|
507
|
+
assert metric["facet"] == format_facet(label)
|
|
525
508
|
efficiency_data = metric["efficiency_data"]
|
|
526
509
|
assert efficiency_data["efficiency_list"] == [[1.0, 2.0], [2.0, 3.0]]
|
|
527
510
|
|
|
@@ -759,30 +742,6 @@ def test_compute_bin_description(
|
|
|
759
742
|
assert result == expected_full
|
|
760
743
|
|
|
761
744
|
|
|
762
|
-
@pytest.mark.parametrize(
|
|
763
|
-
"label, expected_result",
|
|
764
|
-
[
|
|
765
|
-
pytest.param(None, None, id="none"),
|
|
766
|
-
pytest.param("", None, id="empty"),
|
|
767
|
-
pytest.param("abc", "ABC", id="lower"),
|
|
768
|
-
pytest.param("XYZ", "XYZ", id="upper"),
|
|
769
|
-
pytest.param("lMn", "LMN", id="mixed"),
|
|
770
|
-
pytest.param("heLLo 1 abc", "HELLO_1__ABC", id="spaces"),
|
|
771
|
-
pytest.param(0, "0", id="zero"),
|
|
772
|
-
pytest.param(1, "1", id="one"),
|
|
773
|
-
pytest.param(False, "FALSE", id="false"),
|
|
774
|
-
pytest.param("@,$#", "@,$#", id="random"),
|
|
775
|
-
],
|
|
776
|
-
)
|
|
777
|
-
def test_format_facet(label: str | Any, expected_result: str):
|
|
778
|
-
"""
|
|
779
|
-
Given: A label
|
|
780
|
-
When: formatting the label as a key
|
|
781
|
-
Then: the label is properly formatted
|
|
782
|
-
"""
|
|
783
|
-
assert QualityMixin._format_facet(label) == expected_result
|
|
784
|
-
|
|
785
|
-
|
|
786
745
|
def test_validate_vertical_multi_pane_plot_model():
|
|
787
746
|
"""
|
|
788
747
|
Given: A `VerticalMultiPanePlot2D` model and some `Plot2D` models
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/config.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{dkist_processing_common-14.3.0 → dkist_processing_common-14.3.1}/dkist_processing_common/manual.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|