chronaxis 0.1.0.dev0__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.
- chronaxis/__init__.py +72 -0
- chronaxis/__main__.py +12 -0
- chronaxis/analysis_cli.py +181 -0
- chronaxis/batch/__init__.py +14 -0
- chronaxis/batch/api.py +46 -0
- chronaxis/batch/cli.py +48 -0
- chronaxis/batch/config.py +37 -0
- chronaxis/batch/models.py +202 -0
- chronaxis/batch/process_transport.py +149 -0
- chronaxis/batch/process_tree.py +72 -0
- chronaxis/batch/publication.py +41 -0
- chronaxis/batch/runner.py +236 -0
- chronaxis/batch/templates.py +42 -0
- chronaxis/can_dependencies.py +42 -0
- chronaxis/cli.py +193 -0
- chronaxis/configuration/__init__.py +46 -0
- chronaxis/configuration/cli.py +41 -0
- chronaxis/configuration/diagnostics.py +107 -0
- chronaxis/configuration/explanation.py +233 -0
- chronaxis/configuration/file_tools.py +140 -0
- chronaxis/configuration/imports.py +144 -0
- chronaxis/configuration/initialization.py +36 -0
- chronaxis/configuration/json_parser.py +114 -0
- chronaxis/configuration/models.py +74 -0
- chronaxis/configuration/origins.py +90 -0
- chronaxis/configuration/overrides.py +55 -0
- chronaxis/configuration/resolution.py +150 -0
- chronaxis/configuration/template_catalog.py +68 -0
- chronaxis/configuration/templates/batch/analysis-annotated.yaml +18 -0
- chronaxis/configuration/templates/batch/analysis-minimal.yaml +18 -0
- chronaxis/configuration/templates/batch/annotated.yaml +6 -0
- chronaxis/configuration/templates/batch/minimal.yaml +6 -0
- chronaxis/configuration/templates/can-asc/annotated.yaml +18 -0
- chronaxis/configuration/templates/can-asc/minimal.yaml +18 -0
- chronaxis/configuration/templates/can-blf/annotated.yaml +18 -0
- chronaxis/configuration/templates/can-blf/minimal.yaml +18 -0
- chronaxis/configuration/templates/can-export/annotated.yaml +23 -0
- chronaxis/configuration/templates/can-export/minimal.yaml +23 -0
- chronaxis/configuration/templates/catalog.json +233 -0
- chronaxis/configuration/templates/charge-session/annotated.yaml +38 -0
- chronaxis/configuration/templates/charge-session/minimal.yaml +38 -0
- chronaxis/configuration/templates/command-response/annotated.yaml +32 -0
- chronaxis/configuration/templates/command-response/minimal.yaml +36 -0
- chronaxis/configuration/templates/fault-window/annotated.yaml +25 -0
- chronaxis/configuration/templates/fault-window/minimal.yaml +27 -0
- chronaxis/configuration/templates/ini-mapping/annotated.yaml +20 -0
- chronaxis/configuration/templates/ini-mapping/minimal.yaml +20 -0
- chronaxis/configuration/templates/raw-can-csv/annotated.yaml +34 -0
- chronaxis/configuration/templates/raw-can-csv/minimal.yaml +35 -0
- chronaxis/configuration/templates/shared/charge-session.asc +5 -0
- chronaxis/configuration/templates/shared/command-response.asc +8 -0
- chronaxis/configuration/templates/shared/fault-window.asc +5 -0
- chronaxis/configuration/templates/shared/power.asc +7 -0
- chronaxis/configuration/templates/shared/sample.asc +6 -0
- chronaxis/configuration/templates/shared/sample.blf +0 -0
- chronaxis/configuration/templates/shared/sample.csv +5 -0
- chronaxis/configuration/templates/shared/sample.dbc +11 -0
- chronaxis/configuration/templates/shared/signals.csv +6 -0
- chronaxis/configuration/templates/shared/source.ini +5 -0
- chronaxis/configuration/templates/shared/stability.asc +9 -0
- chronaxis/configuration/templates/shared/teaching.dbc +27 -0
- chronaxis/configuration/templates/shared/threshold.asc +7 -0
- chronaxis/configuration/templates/signal-csv/annotated.yaml +27 -0
- chronaxis/configuration/templates/signal-csv/minimal.yaml +27 -0
- chronaxis/configuration/templates/signal-export/annotated.yaml +27 -0
- chronaxis/configuration/templates/signal-export/minimal.yaml +29 -0
- chronaxis/configuration/templates/stability/annotated.yaml +35 -0
- chronaxis/configuration/templates/stability/minimal.yaml +35 -0
- chronaxis/configuration/templates/threshold/annotated.yaml +22 -0
- chronaxis/configuration/templates/threshold/minimal.yaml +22 -0
- chronaxis/configuration/yaml_parser.py +125 -0
- chronaxis/core/__init__.py +71 -0
- chronaxis/core/binding.py +449 -0
- chronaxis/core/calculation_series_join.py +106 -0
- chronaxis/core/calculations.py +435 -0
- chronaxis/core/calculations_memory_numpy.py +136 -0
- chronaxis/core/calculations_memory_reference.py +165 -0
- chronaxis/core/calculations_numpy.py +298 -0
- chronaxis/core/calculations_reference.py +294 -0
- chronaxis/core/condition_evidence.py +182 -0
- chronaxis/core/conditional_integral_result.py +43 -0
- chronaxis/core/conditional_integral_terms.py +146 -0
- chronaxis/core/conditional_integral_terms_numpy.py +148 -0
- chronaxis/core/conditional_integral_terms_reference.py +111 -0
- chronaxis/core/conditional_time_reduction.py +118 -0
- chronaxis/core/conditional_time_reduction_numpy.py +223 -0
- chronaxis/core/conditional_time_reduction_reference.py +213 -0
- chronaxis/core/declarations.py +192 -0
- chronaxis/core/decoded_binding.py +197 -0
- chronaxis/core/direct_message.py +387 -0
- chronaxis/core/export_interpolation.py +54 -0
- chronaxis/core/expression.py +642 -0
- chronaxis/core/expression_numpy.py +314 -0
- chronaxis/core/expression_reference.py +272 -0
- chronaxis/core/integral_result.py +53 -0
- chronaxis/core/integral_sum.py +77 -0
- chronaxis/core/integral_sum_numpy.py +224 -0
- chronaxis/core/integral_sum_reference.py +148 -0
- chronaxis/core/integral_terms.py +119 -0
- chronaxis/core/integral_terms_numpy.py +127 -0
- chronaxis/core/integral_terms_reference.py +91 -0
- chronaxis/core/mean_weights_numpy.py +29 -0
- chronaxis/core/mean_weights_reference.py +27 -0
- chronaxis/core/message_binding.py +305 -0
- chronaxis/core/models.py +485 -0
- chronaxis/core/normalize_numpy.py +396 -0
- chronaxis/core/numeric.py +472 -0
- chronaxis/core/numeric_numpy.py +440 -0
- chronaxis/core/record_intervals.py +115 -0
- chronaxis/core/sample_reduction.py +161 -0
- chronaxis/core/sample_reduction_numpy.py +160 -0
- chronaxis/core/sample_reduction_reference.py +154 -0
- chronaxis/core/selection.py +74 -0
- chronaxis/core/sequence.py +160 -0
- chronaxis/core/sequence_reference.py +248 -0
- chronaxis/core/stability.py +249 -0
- chronaxis/core/start_end.py +169 -0
- chronaxis/core/state.py +494 -0
- chronaxis/core/state_numpy.py +296 -0
- chronaxis/core/temporal.py +373 -0
- chronaxis/core/temporal_clock.py +25 -0
- chronaxis/core/temporal_memory_numpy.py +163 -0
- chronaxis/core/temporal_memory_reference.py +161 -0
- chronaxis/core/temporal_numpy.py +345 -0
- chronaxis/core/temporal_reference.py +304 -0
- chronaxis/core/time_reduction.py +190 -0
- chronaxis/core/time_reduction_numpy.py +205 -0
- chronaxis/core/time_reduction_reference.py +203 -0
- chronaxis/core/types.py +105 -0
- chronaxis/core/units.py +81 -0
- chronaxis/core/validation.py +94 -0
- chronaxis/core/window_delta.py +123 -0
- chronaxis/core/window_delta_numpy.py +78 -0
- chronaxis/core/window_delta_reference.py +69 -0
- chronaxis/core/windows.py +224 -0
- chronaxis/core/windows_numpy.py +78 -0
- chronaxis/core/windows_reference.py +61 -0
- chronaxis/execution/__init__.py +6 -0
- chronaxis/execution/batch_signal_groups.py +122 -0
- chronaxis/execution/bindings.py +296 -0
- chronaxis/execution/boundaries.py +568 -0
- chronaxis/execution/calculation_blocks.py +338 -0
- chronaxis/execution/calculation_values.py +55 -0
- chronaxis/execution/can_batch_reader.py +356 -0
- chronaxis/execution/can_reader.py +948 -0
- chronaxis/execution/can_reference_template.py +61 -0
- chronaxis/execution/condition_evidence.py +370 -0
- chronaxis/execution/conditional_integral_facts.py +310 -0
- chronaxis/execution/conditional_integral_reduction.py +216 -0
- chronaxis/execution/csv_observation.py +524 -0
- chronaxis/execution/csv_reader.py +662 -0
- chronaxis/execution/current_message_calculation.py +225 -0
- chronaxis/execution/driver_expression.py +274 -0
- chronaxis/execution/expressions.py +618 -0
- chronaxis/execution/frame_capture.py +245 -0
- chronaxis/execution/groups.py +236 -0
- chronaxis/execution/historical_conditional_blocks.py +264 -0
- chronaxis/execution/historical_conditional_integral.py +226 -0
- chronaxis/execution/historical_conditional_time_calculation.py +368 -0
- chronaxis/execution/historical_integral.py +219 -0
- chronaxis/execution/historical_observation.py +372 -0
- chronaxis/execution/historical_sample_calculation.py +338 -0
- chronaxis/execution/historical_selection_rows.py +300 -0
- chronaxis/execution/historical_time_calculation.py +341 -0
- chronaxis/execution/history.py +572 -0
- chronaxis/execution/history_records.py +225 -0
- chronaxis/execution/hold.py +448 -0
- chronaxis/execution/integral_facts.py +311 -0
- chronaxis/execution/integral_reduction.py +216 -0
- chronaxis/execution/legacy_frame_samples.py +94 -0
- chronaxis/execution/memory_reader.py +247 -0
- chronaxis/execution/message_bindings.py +293 -0
- chronaxis/execution/message_delivery.py +37 -0
- chronaxis/execution/observed_ingestion.py +551 -0
- chronaxis/execution/raw_signal_groups.py +192 -0
- chronaxis/execution/record_alarm_duration.py +114 -0
- chronaxis/execution/record_delta_condition.py +167 -0
- chronaxis/execution/record_diagnostics.py +87 -0
- chronaxis/execution/record_event_durations.py +143 -0
- chronaxis/execution/record_export_samples.py +94 -0
- chronaxis/execution/record_exports.py +155 -0
- chronaxis/execution/record_integral.py +196 -0
- chronaxis/execution/record_point_buffer.py +101 -0
- chronaxis/execution/record_rule_timeline.py +344 -0
- chronaxis/execution/record_sample.py +46 -0
- chronaxis/execution/record_sample_series.py +29 -0
- chronaxis/execution/record_scope_calculations.py +290 -0
- chronaxis/execution/record_selection.py +62 -0
- chronaxis/execution/record_sequences.py +199 -0
- chronaxis/execution/record_session_calculations.py +778 -0
- chronaxis/execution/record_signal_export.py +133 -0
- chronaxis/execution/record_source_cursor.py +295 -0
- chronaxis/execution/record_time_calculation.py +322 -0
- chronaxis/execution/record_time_indexes.py +143 -0
- chronaxis/execution/record_value_history.py +160 -0
- chronaxis/execution/record_windows.py +229 -0
- chronaxis/execution/required_expression.py +52 -0
- chronaxis/execution/retained_metadata.py +71 -0
- chronaxis/execution/run_session.py +402 -0
- chronaxis/execution/scanned_signal_proof.py +550 -0
- chronaxis/execution/signal_validity.py +40 -0
- chronaxis/execution/state.py +280 -0
- chronaxis/execution/temporal_buffer.py +508 -0
- chronaxis/execution/text_can_reader.py +359 -0
- chronaxis/execution/timeline.py +309 -0
- chronaxis/execution/timeline_multi.py +415 -0
- chronaxis/execution/window_delta_events.py +220 -0
- chronaxis/execution/window_replay.py +350 -0
- chronaxis/execution/windows.py +173 -0
- chronaxis/guide/README.md +70 -0
- chronaxis/guide/api/AnalysisError.md +14 -0
- chronaxis/guide/api/AnalysisPlan.md +96 -0
- chronaxis/guide/api/AnalysisResult.md +398 -0
- chronaxis/guide/api/AnalysisRunner.md +155 -0
- chronaxis/guide/api/BatchJob.md +19 -0
- chronaxis/guide/api/BatchJobResult.md +61 -0
- chronaxis/guide/api/BatchPlan.md +48 -0
- chronaxis/guide/api/BatchReport.md +108 -0
- chronaxis/guide/api/BatchRunner.md +84 -0
- chronaxis/guide/api/OutputManifest.md +23 -0
- chronaxis/guide/api/PlanFragment.md +47 -0
- chronaxis/guide/api/PlanValidationError.md +98 -0
- chronaxis/guide/api/PresetSpec.md +63 -0
- chronaxis/guide/api/ResultClosedError.md +14 -0
- chronaxis/guide/api/RunMetadata.md +100 -0
- chronaxis/guide/api/TimeConversion.md +29 -0
- chronaxis/guide/api/TimeOverflowError.md +17 -0
- chronaxis/guide/api/build_preset.md +36 -0
- chronaxis/guide/api/checked_add_ns.md +30 -0
- chronaxis/guide/api/convert_time.md +40 -0
- chronaxis/guide/api/explain_analysis_plan.md +38 -0
- chronaxis/guide/api/index.json +185 -0
- chronaxis/guide/api/load_analysis_plan.md +34 -0
- chronaxis/guide/api/load_batch_plan.md +36 -0
- chronaxis/guide/api/parse_datetime_ns.md +35 -0
- chronaxis/guide/api/parse_duration.md +30 -0
- chronaxis/guide/api/resolve_preset_roles.md +37 -0
- chronaxis/guide/api/run_batch.md +38 -0
- chronaxis/guide/api/shift_times_reference.md +33 -0
- chronaxis/guide/api/time_deltas_reference.md +37 -0
- chronaxis/guide/api/validate_analysis_plan.md +38 -0
- chronaxis/guide/en/README.md +74 -0
- chronaxis/guide/en/api/AnalysisError.md +14 -0
- chronaxis/guide/en/api/AnalysisPlan.md +93 -0
- chronaxis/guide/en/api/AnalysisResult.md +398 -0
- chronaxis/guide/en/api/AnalysisRunner.md +191 -0
- chronaxis/guide/en/api/BatchJob.md +17 -0
- chronaxis/guide/en/api/BatchJobResult.md +43 -0
- chronaxis/guide/en/api/BatchPlan.md +37 -0
- chronaxis/guide/en/api/BatchReport.md +52 -0
- chronaxis/guide/en/api/BatchRunner.md +51 -0
- chronaxis/guide/en/api/OutputManifest.md +23 -0
- chronaxis/guide/en/api/PlanFragment.md +33 -0
- chronaxis/guide/en/api/PlanValidationError.md +58 -0
- chronaxis/guide/en/api/PresetSpec.md +51 -0
- chronaxis/guide/en/api/ResultClosedError.md +14 -0
- chronaxis/guide/en/api/RunMetadata.md +100 -0
- chronaxis/guide/en/api/TimeConversion.md +23 -0
- chronaxis/guide/en/api/TimeOverflowError.md +14 -0
- chronaxis/guide/en/api/build_preset.md +23 -0
- chronaxis/guide/en/api/checked_add_ns.md +21 -0
- chronaxis/guide/en/api/convert_time.md +25 -0
- chronaxis/guide/en/api/explain_analysis_plan.md +30 -0
- chronaxis/guide/en/api/index.json +185 -0
- chronaxis/guide/en/api/load_analysis_plan.md +27 -0
- chronaxis/guide/en/api/load_batch_plan.md +28 -0
- chronaxis/guide/en/api/parse_datetime_ns.md +23 -0
- chronaxis/guide/en/api/parse_duration.md +20 -0
- chronaxis/guide/en/api/resolve_preset_roles.md +23 -0
- chronaxis/guide/en/api/run_batch.md +39 -0
- chronaxis/guide/en/api/shift_times_reference.md +21 -0
- chronaxis/guide/en/api/time_deltas_reference.md +22 -0
- chronaxis/guide/en/api/validate_analysis_plan.md +29 -0
- chronaxis/guide/en/fields/analysis/calculations-all-1.json +345 -0
- chronaxis/guide/en/fields/analysis/calculations-all-2.json +300 -0
- chronaxis/guide/en/fields/analysis/calculations-all-3.json +84 -0
- chronaxis/guide/en/fields/analysis/config_version-all-1.json +24 -0
- chronaxis/guide/en/fields/analysis/dataset-all-1.json +344 -0
- chronaxis/guide/en/fields/analysis/derived-all-1.json +147 -0
- chronaxis/guide/en/fields/analysis/diagnostics-all-1.json +69 -0
- chronaxis/guide/en/fields/analysis/execution-all-1.json +167 -0
- chronaxis/guide/en/fields/analysis/imports-all-1.json +39 -0
- chronaxis/guide/en/fields/analysis/intervals-all-1.json +173 -0
- chronaxis/guide/en/fields/analysis/message_calculations-all-1.json +345 -0
- chronaxis/guide/en/fields/analysis/message_calculations-all-2.json +270 -0
- chronaxis/guide/en/fields/analysis/metadata-all-1.json +24 -0
- chronaxis/guide/en/fields/analysis/outputs-all-1.json +332 -0
- chronaxis/guide/en/fields/analysis/outputs-all-2.json +319 -0
- chronaxis/guide/en/fields/analysis/outputs-all-3.json +321 -0
- chronaxis/guide/en/fields/analysis/outputs-all-4.json +236 -0
- chronaxis/guide/en/fields/analysis/outputs-all-5.json +246 -0
- chronaxis/guide/en/fields/analysis/outputs-all-6.json +214 -0
- chronaxis/guide/en/fields/analysis/overrides-all-1.json +104 -0
- chronaxis/guide/en/fields/analysis/presets-charge_session-1.json +398 -0
- chronaxis/guide/en/fields/analysis/presets-charge_session-2.json +114 -0
- chronaxis/guide/en/fields/analysis/presets-command_response-1.json +376 -0
- chronaxis/guide/en/fields/analysis/presets-fault_context-1.json +285 -0
- chronaxis/guide/en/fields/analysis/presets-threshold_excursion-1.json +317 -0
- chronaxis/guide/en/fields/analysis/rules-condition_duration-1.json +344 -0
- chronaxis/guide/en/fields/analysis/rules-condition_duration-2.json +27 -0
- chronaxis/guide/en/fields/analysis/rules-debounce-1.json +335 -0
- chronaxis/guide/en/fields/analysis/rules-falling_edge-1.json +317 -0
- chronaxis/guide/en/fields/analysis/rules-hysteresis-1.json +334 -0
- chronaxis/guide/en/fields/analysis/rules-hysteresis-2.json +27 -0
- chronaxis/guide/en/fields/analysis/rules-rising_edge-1.json +317 -0
- chronaxis/guide/en/fields/analysis/rules-start_end-1.json +333 -0
- chronaxis/guide/en/fields/analysis/rules-start_end-2.json +60 -0
- chronaxis/guide/en/fields/analysis/rules-start_only-1.json +334 -0
- chronaxis/guide/en/fields/analysis/rules-window_delta-1.json +338 -0
- chronaxis/guide/en/fields/analysis/rules-window_delta-2.json +96 -0
- chronaxis/guide/en/fields/analysis/sequences-all-1.json +378 -0
- chronaxis/guide/en/fields/analysis/sequences-all-2.json +70 -0
- chronaxis/guide/en/fields/analysis/signals-variant-1-1.json +349 -0
- chronaxis/guide/en/fields/analysis/signals-variant-1-2.json +297 -0
- chronaxis/guide/en/fields/analysis/signals-variant-1-3.json +323 -0
- chronaxis/guide/en/fields/analysis/signals-variant-1-4.json +192 -0
- chronaxis/guide/en/fields/analysis/signals-variant-2-1.json +327 -0
- chronaxis/guide/en/fields/analysis/signals-variant-2-2.json +312 -0
- chronaxis/guide/en/fields/analysis/signals-variant-2-3.json +294 -0
- chronaxis/guide/en/fields/analysis/signals-variant-2-4.json +253 -0
- chronaxis/guide/en/fields/analysis/signals-variant-2-5.json +44 -0
- chronaxis/guide/en/fields/analysis/sources-can_asc-1.json +318 -0
- chronaxis/guide/en/fields/analysis/sources-can_asc-2.json +310 -0
- chronaxis/guide/en/fields/analysis/sources-can_asc-3.json +311 -0
- chronaxis/guide/en/fields/analysis/sources-can_asc-4.json +69 -0
- chronaxis/guide/en/fields/analysis/sources-can_blf-1.json +317 -0
- chronaxis/guide/en/fields/analysis/sources-can_blf-2.json +310 -0
- chronaxis/guide/en/fields/analysis/sources-can_blf-3.json +317 -0
- chronaxis/guide/en/fields/analysis/sources-memory-1.json +332 -0
- chronaxis/guide/en/fields/analysis/sources-memory-2.json +125 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-1.json +330 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-10.json +233 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-11.json +225 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-12.json +228 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-13.json +226 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-14.json +230 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-15.json +227 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-16.json +230 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-17.json +238 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-18.json +239 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-19.json +233 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-2.json +310 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-20.json +242 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-21.json +230 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-22.json +228 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-23.json +230 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-24.json +223 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-25.json +290 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-26.json +131 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-3.json +297 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-4.json +226 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-5.json +230 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-6.json +227 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-7.json +230 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-8.json +238 -0
- chronaxis/guide/en/fields/analysis/sources-raw_can_csv-9.json +239 -0
- chronaxis/guide/en/fields/analysis/sources-signal_csv-1.json +331 -0
- chronaxis/guide/en/fields/analysis/sources-signal_csv-2.json +307 -0
- chronaxis/guide/en/fields/analysis/sources-signal_csv-3.json +315 -0
- chronaxis/guide/en/fields/analysis/sources-variant-6-1.json +319 -0
- chronaxis/guide/en/fields/analysis/sources-variant-6-2.json +307 -0
- chronaxis/guide/en/fields/analysis/sources-variant-6-3.json +312 -0
- chronaxis/guide/en/fields/analysis/sources-variant-6-4.json +113 -0
- chronaxis/guide/en/fields/analysis/windows-all-1.json +361 -0
- chronaxis/guide/en/fields/analysis/windows-all-2.json +187 -0
- chronaxis/guide/en/fields/batch/backend-all-1.json +26 -0
- chronaxis/guide/en/fields/batch/batch_version-all-1.json +22 -0
- chronaxis/guide/en/fields/batch/fail_fast-all-1.json +22 -0
- chronaxis/guide/en/fields/batch/inputs-all-1.json +161 -0
- chronaxis/guide/en/fields/batch/jobs-all-1.json +58 -0
- chronaxis/guide/en/fields/batch/process_count-all-1.json +23 -0
- chronaxis/guide/en/fields/batch/source-all-1.json +22 -0
- chronaxis/guide/en/fields/batch/template-all-1.json +22 -0
- chronaxis/guide/en/fields/definitions/derived-all-1.json +121 -0
- chronaxis/guide/en/fields/definitions/signals-all-1.json +336 -0
- chronaxis/guide/en/fields/definitions/signals-all-2.json +307 -0
- chronaxis/guide/en/fields/definitions/signals-all-3.json +290 -0
- chronaxis/guide/en/fields/definitions/signals-all-4.json +347 -0
- chronaxis/guide/en/fields/definitions/signals-all-5.json +297 -0
- chronaxis/guide/en/fields/definitions/signals-all-6.json +259 -0
- chronaxis/guide/en/fields/definitions/signals-all-7.json +117 -0
- chronaxis/guide/en/fields/definitions/sources-all-1.json +332 -0
- chronaxis/guide/en/fields/definitions/sources-all-10.json +306 -0
- chronaxis/guide/en/fields/definitions/sources-all-11.json +294 -0
- chronaxis/guide/en/fields/definitions/sources-all-12.json +212 -0
- chronaxis/guide/en/fields/definitions/sources-all-13.json +217 -0
- chronaxis/guide/en/fields/definitions/sources-all-14.json +213 -0
- chronaxis/guide/en/fields/definitions/sources-all-15.json +214 -0
- chronaxis/guide/en/fields/definitions/sources-all-16.json +215 -0
- chronaxis/guide/en/fields/definitions/sources-all-17.json +213 -0
- chronaxis/guide/en/fields/definitions/sources-all-18.json +214 -0
- chronaxis/guide/en/fields/definitions/sources-all-19.json +213 -0
- chronaxis/guide/en/fields/definitions/sources-all-2.json +323 -0
- chronaxis/guide/en/fields/definitions/sources-all-20.json +217 -0
- chronaxis/guide/en/fields/definitions/sources-all-21.json +210 -0
- chronaxis/guide/en/fields/definitions/sources-all-22.json +214 -0
- chronaxis/guide/en/fields/definitions/sources-all-23.json +218 -0
- chronaxis/guide/en/fields/definitions/sources-all-24.json +209 -0
- chronaxis/guide/en/fields/definitions/sources-all-25.json +215 -0
- chronaxis/guide/en/fields/definitions/sources-all-26.json +218 -0
- chronaxis/guide/en/fields/definitions/sources-all-27.json +224 -0
- chronaxis/guide/en/fields/definitions/sources-all-28.json +215 -0
- chronaxis/guide/en/fields/definitions/sources-all-29.json +205 -0
- chronaxis/guide/en/fields/definitions/sources-all-3.json +303 -0
- chronaxis/guide/en/fields/definitions/sources-all-30.json +298 -0
- chronaxis/guide/en/fields/definitions/sources-all-31.json +315 -0
- chronaxis/guide/en/fields/definitions/sources-all-32.json +306 -0
- chronaxis/guide/en/fields/definitions/sources-all-33.json +209 -0
- chronaxis/guide/en/fields/definitions/sources-all-4.json +336 -0
- chronaxis/guide/en/fields/definitions/sources-all-5.json +299 -0
- chronaxis/guide/en/fields/definitions/sources-all-6.json +307 -0
- chronaxis/guide/en/fields/definitions/sources-all-7.json +320 -0
- chronaxis/guide/en/fields/definitions/sources-all-8.json +303 -0
- chronaxis/guide/en/fields/definitions/sources-all-9.json +315 -0
- chronaxis/guide/en/fields/index.json +3450 -0
- chronaxis/guide/en/fields/mapping/aliases-all-1.json +91 -0
- chronaxis/guide/en/fields/mapping/analysis-all-1.json +382 -0
- chronaxis/guide/en/fields/mapping/analysis-all-10.json +301 -0
- chronaxis/guide/en/fields/mapping/analysis-all-11.json +312 -0
- chronaxis/guide/en/fields/mapping/analysis-all-12.json +311 -0
- chronaxis/guide/en/fields/mapping/analysis-all-13.json +314 -0
- chronaxis/guide/en/fields/mapping/analysis-all-14.json +310 -0
- chronaxis/guide/en/fields/mapping/analysis-all-15.json +297 -0
- chronaxis/guide/en/fields/mapping/analysis-all-16.json +226 -0
- chronaxis/guide/en/fields/mapping/analysis-all-17.json +230 -0
- chronaxis/guide/en/fields/mapping/analysis-all-18.json +227 -0
- chronaxis/guide/en/fields/mapping/analysis-all-19.json +230 -0
- chronaxis/guide/en/fields/mapping/analysis-all-2.json +323 -0
- chronaxis/guide/en/fields/mapping/analysis-all-20.json +221 -0
- chronaxis/guide/en/fields/mapping/analysis-all-21.json +237 -0
- chronaxis/guide/en/fields/mapping/analysis-all-22.json +233 -0
- chronaxis/guide/en/fields/mapping/analysis-all-23.json +222 -0
- chronaxis/guide/en/fields/mapping/analysis-all-24.json +231 -0
- chronaxis/guide/en/fields/mapping/analysis-all-25.json +225 -0
- chronaxis/guide/en/fields/mapping/analysis-all-26.json +230 -0
- chronaxis/guide/en/fields/mapping/analysis-all-27.json +228 -0
- chronaxis/guide/en/fields/mapping/analysis-all-28.json +230 -0
- chronaxis/guide/en/fields/mapping/analysis-all-29.json +223 -0
- chronaxis/guide/en/fields/mapping/analysis-all-3.json +318 -0
- chronaxis/guide/en/fields/mapping/analysis-all-30.json +233 -0
- chronaxis/guide/en/fields/mapping/analysis-all-31.json +218 -0
- chronaxis/guide/en/fields/mapping/analysis-all-32.json +239 -0
- chronaxis/guide/en/fields/mapping/analysis-all-33.json +233 -0
- chronaxis/guide/en/fields/mapping/analysis-all-34.json +225 -0
- chronaxis/guide/en/fields/mapping/analysis-all-35.json +228 -0
- chronaxis/guide/en/fields/mapping/analysis-all-36.json +226 -0
- chronaxis/guide/en/fields/mapping/analysis-all-37.json +244 -0
- chronaxis/guide/en/fields/mapping/analysis-all-38.json +326 -0
- chronaxis/guide/en/fields/mapping/analysis-all-39.json +299 -0
- chronaxis/guide/en/fields/mapping/analysis-all-4.json +297 -0
- chronaxis/guide/en/fields/mapping/analysis-all-40.json +311 -0
- chronaxis/guide/en/fields/mapping/analysis-all-41.json +310 -0
- chronaxis/guide/en/fields/mapping/analysis-all-42.json +346 -0
- chronaxis/guide/en/fields/mapping/analysis-all-43.json +267 -0
- chronaxis/guide/en/fields/mapping/analysis-all-44.json +327 -0
- chronaxis/guide/en/fields/mapping/analysis-all-45.json +279 -0
- chronaxis/guide/en/fields/mapping/analysis-all-46.json +327 -0
- chronaxis/guide/en/fields/mapping/analysis-all-47.json +312 -0
- chronaxis/guide/en/fields/mapping/analysis-all-48.json +294 -0
- chronaxis/guide/en/fields/mapping/analysis-all-49.json +253 -0
- chronaxis/guide/en/fields/mapping/analysis-all-5.json +312 -0
- chronaxis/guide/en/fields/mapping/analysis-all-50.json +346 -0
- chronaxis/guide/en/fields/mapping/analysis-all-51.json +324 -0
- chronaxis/guide/en/fields/mapping/analysis-all-52.json +335 -0
- chronaxis/guide/en/fields/mapping/analysis-all-53.json +317 -0
- chronaxis/guide/en/fields/mapping/analysis-all-54.json +316 -0
- chronaxis/guide/en/fields/mapping/analysis-all-55.json +302 -0
- chronaxis/guide/en/fields/mapping/analysis-all-56.json +319 -0
- chronaxis/guide/en/fields/mapping/analysis-all-57.json +334 -0
- chronaxis/guide/en/fields/mapping/analysis-all-58.json +333 -0
- chronaxis/guide/en/fields/mapping/analysis-all-59.json +359 -0
- chronaxis/guide/en/fields/mapping/analysis-all-6.json +327 -0
- chronaxis/guide/en/fields/mapping/analysis-all-60.json +303 -0
- chronaxis/guide/en/fields/mapping/analysis-all-61.json +326 -0
- chronaxis/guide/en/fields/mapping/analysis-all-62.json +301 -0
- chronaxis/guide/en/fields/mapping/analysis-all-63.json +326 -0
- chronaxis/guide/en/fields/mapping/analysis-all-64.json +367 -0
- chronaxis/guide/en/fields/mapping/analysis-all-65.json +334 -0
- chronaxis/guide/en/fields/mapping/analysis-all-66.json +358 -0
- chronaxis/guide/en/fields/mapping/analysis-all-67.json +349 -0
- chronaxis/guide/en/fields/mapping/analysis-all-68.json +331 -0
- chronaxis/guide/en/fields/mapping/analysis-all-69.json +304 -0
- chronaxis/guide/en/fields/mapping/analysis-all-7.json +303 -0
- chronaxis/guide/en/fields/mapping/analysis-all-70.json +349 -0
- chronaxis/guide/en/fields/mapping/analysis-all-71.json +288 -0
- chronaxis/guide/en/fields/mapping/analysis-all-72.json +316 -0
- chronaxis/guide/en/fields/mapping/analysis-all-73.json +266 -0
- chronaxis/guide/en/fields/mapping/analysis-all-74.json +227 -0
- chronaxis/guide/en/fields/mapping/analysis-all-75.json +239 -0
- chronaxis/guide/en/fields/mapping/analysis-all-76.json +274 -0
- chronaxis/guide/en/fields/mapping/analysis-all-77.json +380 -0
- chronaxis/guide/en/fields/mapping/analysis-all-78.json +313 -0
- chronaxis/guide/en/fields/mapping/analysis-all-79.json +338 -0
- chronaxis/guide/en/fields/mapping/analysis-all-8.json +292 -0
- chronaxis/guide/en/fields/mapping/analysis-all-80.json +304 -0
- chronaxis/guide/en/fields/mapping/analysis-all-81.json +140 -0
- chronaxis/guide/en/fields/mapping/analysis-all-9.json +332 -0
- chronaxis/guide/en/fields/mapping/io_policy-all-1.json +19 -0
- chronaxis/guide/en/fields/mapping/mapping_version-all-1.json +19 -0
- chronaxis/guide/en/fields/mapping/path_base-all-1.json +19 -0
- chronaxis/guide/en/fields/mapping/sections-all-1.json +402 -0
- chronaxis/guide/en/fields/mapping/sections-all-2.json +232 -0
- chronaxis/guide/en/semantics.md +70 -0
- chronaxis/guide/en/tasks.json +290 -0
- chronaxis/guide/en/workflow.md +41 -0
- chronaxis/guide/examples/analysis-imports.yaml +22 -0
- chronaxis/guide/examples/analysis.yaml +23 -0
- chronaxis/guide/examples/batch-minimal.yaml +3 -0
- chronaxis/guide/examples/conditional-energy.yaml +36 -0
- chronaxis/guide/examples/data/activity.csv +6 -0
- chronaxis/guide/examples/data/can/activity.asc +11 -0
- chronaxis/guide/examples/data/can/calculation-minimal.asc +6 -0
- chronaxis/guide/examples/data/can/conditional-energy/part-1.asc +92 -0
- chronaxis/guide/examples/data/can/conditional-energy/part-2.asc +36 -0
- chronaxis/guide/examples/data/can/conditional-energy/signals.dbc +10 -0
- chronaxis/guide/examples/data/can/execution-comparison.asc +12 -0
- chronaxis/guide/examples/data/can/execution-report.asc +4 -0
- chronaxis/guide/examples/data/can/expression-extended.asc +11 -0
- chronaxis/guide/examples/data/can/interval-actual.asc +6 -0
- chronaxis/guide/examples/data/can/preset-charge-energy.asc +15 -0
- chronaxis/guide/examples/data/can/preset-charge-minimal.asc +11 -0
- chronaxis/guide/examples/data/can/preset-command-automatic.asc +11 -0
- chronaxis/guide/examples/data/can/preset-fault-context.asc +7 -0
- chronaxis/guide/examples/data/can/preset-threshold-delay.asc +7 -0
- chronaxis/guide/examples/data/can/preset-threshold-partial.asc +7 -0
- chronaxis/guide/examples/data/can/quality.asc +6 -0
- chronaxis/guide/examples/data/can/quickstart-parts/part1.asc +4 -0
- chronaxis/guide/examples/data/can/quickstart-parts/part2.asc +3 -0
- chronaxis/guide/examples/data/can/quickstart.asc +6 -0
- chronaxis/guide/examples/data/can/rule-condition_duration-extended.asc +35 -0
- chronaxis/guide/examples/data/can/rule-condition_duration-minimal.asc +19 -0
- chronaxis/guide/examples/data/can/rule-debounce-extended.asc +19 -0
- chronaxis/guide/examples/data/can/rule-falling_edge-extended.asc +35 -0
- chronaxis/guide/examples/data/can/rule-hysteresis-extended.asc +19 -0
- chronaxis/guide/examples/data/can/rule-start_end-extended.asc +35 -0
- chronaxis/guide/examples/data/can/rule-start_only-extended.asc +19 -0
- chronaxis/guide/examples/data/can/rule-window_delta-extended.asc +19 -0
- chronaxis/guide/examples/data/can/sequence-outcomes.asc +19 -0
- chronaxis/guide/examples/data/can/signal-types.asc +13 -0
- chronaxis/guide/examples/data/can/start-end.asc +30 -0
- chronaxis/guide/examples/data/can/teaching-base.asc +58 -0
- chronaxis/guide/examples/data/can/teaching.dbc +53 -0
- chronaxis/guide/examples/data/joint-current.csv +5 -0
- chronaxis/guide/examples/data/joint.asc +5 -0
- chronaxis/guide/examples/data/joint.dbc +7 -0
- chronaxis/guide/examples/data/message-clean.asc +6 -0
- chronaxis/guide/examples/data/message-direction.asc +7 -0
- chronaxis/guide/examples/data/message-direction.dbc +7 -0
- chronaxis/guide/examples/data/power.blf +0 -0
- chronaxis/guide/examples/data/power.dbc +6 -0
- chronaxis/guide/examples/data/quality.csv +5 -0
- chronaxis/guide/examples/data/raw-can-example.csv +5 -0
- chronaxis/guide/examples/data/signal-types.csv +5 -0
- chronaxis/guide/examples/data/signals.csv +6 -0
- chronaxis/guide/examples/data/timing.asc +6 -0
- chronaxis/guide/examples/data/timing.dbc +11 -0
- chronaxis/guide/examples/export-can-minimal.yaml +24 -0
- chronaxis/guide/examples/input-csv-minimal.yaml +23 -0
- chronaxis/guide/examples/preset-charge-energy.yaml +41 -0
- chronaxis/guide/examples/preset-charge-minimal.yaml +31 -0
- chronaxis/guide/examples/preset-fault-context.yaml +27 -0
- chronaxis/guide/examples/quality.yaml +19 -0
- chronaxis/guide/examples/sequence-outcomes.yaml +39 -0
- chronaxis/guide/examples/shared/definitions.yaml +14 -0
- chronaxis/guide/examples/signal-enum-minimal.yaml +19 -0
- chronaxis/guide/examples/signal-number-conversion.yaml +24 -0
- chronaxis/guide/examples/window-merged.yaml +28 -0
- chronaxis/guide/fields/analysis/calculations-all-1.json +360 -0
- chronaxis/guide/fields/analysis/calculations-all-2.json +299 -0
- chronaxis/guide/fields/analysis/calculations-all-3.json +70 -0
- chronaxis/guide/fields/analysis/config_version-all-1.json +24 -0
- chronaxis/guide/fields/analysis/dataset-all-1.json +344 -0
- chronaxis/guide/fields/analysis/derived-all-1.json +147 -0
- chronaxis/guide/fields/analysis/diagnostics-all-1.json +69 -0
- chronaxis/guide/fields/analysis/execution-all-1.json +167 -0
- chronaxis/guide/fields/analysis/imports-all-1.json +39 -0
- chronaxis/guide/fields/analysis/intervals-all-1.json +173 -0
- chronaxis/guide/fields/analysis/message_calculations-all-1.json +360 -0
- chronaxis/guide/fields/analysis/message_calculations-all-2.json +255 -0
- chronaxis/guide/fields/analysis/metadata-all-1.json +24 -0
- chronaxis/guide/fields/analysis/outputs-all-1.json +349 -0
- chronaxis/guide/fields/analysis/outputs-all-2.json +302 -0
- chronaxis/guide/fields/analysis/outputs-all-3.json +321 -0
- chronaxis/guide/fields/analysis/outputs-all-4.json +253 -0
- chronaxis/guide/fields/analysis/outputs-all-5.json +244 -0
- chronaxis/guide/fields/analysis/outputs-all-6.json +199 -0
- chronaxis/guide/fields/analysis/overrides-all-1.json +104 -0
- chronaxis/guide/fields/analysis/presets-charge_session-1.json +398 -0
- chronaxis/guide/fields/analysis/presets-charge_session-2.json +114 -0
- chronaxis/guide/fields/analysis/presets-command_response-1.json +376 -0
- chronaxis/guide/fields/analysis/presets-fault_context-1.json +285 -0
- chronaxis/guide/fields/analysis/presets-threshold_excursion-1.json +317 -0
- chronaxis/guide/fields/analysis/rules-condition_duration-1.json +344 -0
- chronaxis/guide/fields/analysis/rules-condition_duration-2.json +27 -0
- chronaxis/guide/fields/analysis/rules-debounce-1.json +335 -0
- chronaxis/guide/fields/analysis/rules-falling_edge-1.json +317 -0
- chronaxis/guide/fields/analysis/rules-hysteresis-1.json +334 -0
- chronaxis/guide/fields/analysis/rules-hysteresis-2.json +27 -0
- chronaxis/guide/fields/analysis/rules-rising_edge-1.json +317 -0
- chronaxis/guide/fields/analysis/rules-start_end-1.json +349 -0
- chronaxis/guide/fields/analysis/rules-start_end-2.json +44 -0
- chronaxis/guide/fields/analysis/rules-start_only-1.json +334 -0
- chronaxis/guide/fields/analysis/rules-window_delta-1.json +356 -0
- chronaxis/guide/fields/analysis/rules-window_delta-2.json +78 -0
- chronaxis/guide/fields/analysis/sequences-all-1.json +394 -0
- chronaxis/guide/fields/analysis/sequences-all-2.json +54 -0
- chronaxis/guide/fields/analysis/signals-variant-1-1.json +349 -0
- chronaxis/guide/fields/analysis/signals-variant-1-2.json +297 -0
- chronaxis/guide/fields/analysis/signals-variant-1-3.json +340 -0
- chronaxis/guide/fields/analysis/signals-variant-1-4.json +175 -0
- chronaxis/guide/fields/analysis/signals-variant-2-1.json +327 -0
- chronaxis/guide/fields/analysis/signals-variant-2-2.json +335 -0
- chronaxis/guide/fields/analysis/signals-variant-2-3.json +289 -0
- chronaxis/guide/fields/analysis/signals-variant-2-4.json +270 -0
- chronaxis/guide/fields/analysis/sources-can_asc-1.json +318 -0
- chronaxis/guide/fields/analysis/sources-can_asc-2.json +310 -0
- chronaxis/guide/fields/analysis/sources-can_asc-3.json +311 -0
- chronaxis/guide/fields/analysis/sources-can_asc-4.json +69 -0
- chronaxis/guide/fields/analysis/sources-can_blf-1.json +317 -0
- chronaxis/guide/fields/analysis/sources-can_blf-2.json +310 -0
- chronaxis/guide/fields/analysis/sources-can_blf-3.json +317 -0
- chronaxis/guide/fields/analysis/sources-memory-1.json +347 -0
- chronaxis/guide/fields/analysis/sources-memory-2.json +110 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-1.json +330 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-10.json +233 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-11.json +225 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-12.json +228 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-13.json +226 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-14.json +230 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-15.json +227 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-16.json +230 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-17.json +238 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-18.json +239 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-19.json +233 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-2.json +310 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-20.json +242 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-21.json +230 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-22.json +228 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-23.json +230 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-24.json +223 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-25.json +290 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-26.json +131 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-3.json +297 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-4.json +226 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-5.json +230 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-6.json +227 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-7.json +230 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-8.json +238 -0
- chronaxis/guide/fields/analysis/sources-raw_can_csv-9.json +239 -0
- chronaxis/guide/fields/analysis/sources-signal_csv-1.json +331 -0
- chronaxis/guide/fields/analysis/sources-signal_csv-2.json +327 -0
- chronaxis/guide/fields/analysis/sources-signal_csv-3.json +295 -0
- chronaxis/guide/fields/analysis/sources-variant-6-1.json +319 -0
- chronaxis/guide/fields/analysis/sources-variant-6-2.json +327 -0
- chronaxis/guide/fields/analysis/sources-variant-6-3.json +314 -0
- chronaxis/guide/fields/analysis/sources-variant-6-4.json +91 -0
- chronaxis/guide/fields/analysis/windows-all-1.json +361 -0
- chronaxis/guide/fields/analysis/windows-all-2.json +187 -0
- chronaxis/guide/fields/batch/backend-all-1.json +26 -0
- chronaxis/guide/fields/batch/batch_version-all-1.json +22 -0
- chronaxis/guide/fields/batch/fail_fast-all-1.json +22 -0
- chronaxis/guide/fields/batch/inputs-all-1.json +161 -0
- chronaxis/guide/fields/batch/jobs-all-1.json +58 -0
- chronaxis/guide/fields/batch/process_count-all-1.json +23 -0
- chronaxis/guide/fields/batch/source-all-1.json +22 -0
- chronaxis/guide/fields/batch/template-all-1.json +22 -0
- chronaxis/guide/fields/definitions/derived-all-1.json +121 -0
- chronaxis/guide/fields/definitions/signals-all-1.json +336 -0
- chronaxis/guide/fields/definitions/signals-all-2.json +307 -0
- chronaxis/guide/fields/definitions/signals-all-3.json +305 -0
- chronaxis/guide/fields/definitions/signals-all-4.json +352 -0
- chronaxis/guide/fields/definitions/signals-all-5.json +311 -0
- chronaxis/guide/fields/definitions/signals-all-6.json +254 -0
- chronaxis/guide/fields/definitions/signals-all-7.json +88 -0
- chronaxis/guide/fields/definitions/sources-all-1.json +332 -0
- chronaxis/guide/fields/definitions/sources-all-10.json +307 -0
- chronaxis/guide/fields/definitions/sources-all-11.json +280 -0
- chronaxis/guide/fields/definitions/sources-all-12.json +209 -0
- chronaxis/guide/fields/definitions/sources-all-13.json +219 -0
- chronaxis/guide/fields/definitions/sources-all-14.json +213 -0
- chronaxis/guide/fields/definitions/sources-all-15.json +212 -0
- chronaxis/guide/fields/definitions/sources-all-16.json +232 -0
- chronaxis/guide/fields/definitions/sources-all-17.json +213 -0
- chronaxis/guide/fields/definitions/sources-all-18.json +212 -0
- chronaxis/guide/fields/definitions/sources-all-19.json +217 -0
- chronaxis/guide/fields/definitions/sources-all-2.json +336 -0
- chronaxis/guide/fields/definitions/sources-all-20.json +228 -0
- chronaxis/guide/fields/definitions/sources-all-21.json +212 -0
- chronaxis/guide/fields/definitions/sources-all-22.json +232 -0
- chronaxis/guide/fields/definitions/sources-all-23.json +213 -0
- chronaxis/guide/fields/definitions/sources-all-24.json +212 -0
- chronaxis/guide/fields/definitions/sources-all-25.json +217 -0
- chronaxis/guide/fields/definitions/sources-all-26.json +228 -0
- chronaxis/guide/fields/definitions/sources-all-27.json +212 -0
- chronaxis/guide/fields/definitions/sources-all-28.json +217 -0
- chronaxis/guide/fields/definitions/sources-all-29.json +227 -0
- chronaxis/guide/fields/definitions/sources-all-3.json +306 -0
- chronaxis/guide/fields/definitions/sources-all-30.json +333 -0
- chronaxis/guide/fields/definitions/sources-all-31.json +302 -0
- chronaxis/guide/fields/definitions/sources-all-32.json +319 -0
- chronaxis/guide/fields/definitions/sources-all-33.json +89 -0
- chronaxis/guide/fields/definitions/sources-all-4.json +336 -0
- chronaxis/guide/fields/definitions/sources-all-5.json +313 -0
- chronaxis/guide/fields/definitions/sources-all-6.json +292 -0
- chronaxis/guide/fields/definitions/sources-all-7.json +319 -0
- chronaxis/guide/fields/definitions/sources-all-8.json +315 -0
- chronaxis/guide/fields/definitions/sources-all-9.json +318 -0
- chronaxis/guide/fields/index.json +3432 -0
- chronaxis/guide/fields/mapping/aliases-all-1.json +91 -0
- chronaxis/guide/fields/mapping/analysis-all-1.json +382 -0
- chronaxis/guide/fields/mapping/analysis-all-10.json +307 -0
- chronaxis/guide/fields/mapping/analysis-all-11.json +311 -0
- chronaxis/guide/fields/mapping/analysis-all-12.json +329 -0
- chronaxis/guide/fields/mapping/analysis-all-13.json +294 -0
- chronaxis/guide/fields/mapping/analysis-all-14.json +311 -0
- chronaxis/guide/fields/mapping/analysis-all-15.json +280 -0
- chronaxis/guide/fields/mapping/analysis-all-16.json +227 -0
- chronaxis/guide/fields/mapping/analysis-all-17.json +230 -0
- chronaxis/guide/fields/mapping/analysis-all-18.json +221 -0
- chronaxis/guide/fields/mapping/analysis-all-19.json +237 -0
- chronaxis/guide/fields/mapping/analysis-all-2.json +342 -0
- chronaxis/guide/fields/mapping/analysis-all-20.json +233 -0
- chronaxis/guide/fields/mapping/analysis-all-21.json +244 -0
- chronaxis/guide/fields/mapping/analysis-all-22.json +228 -0
- chronaxis/guide/fields/mapping/analysis-all-23.json +226 -0
- chronaxis/guide/fields/mapping/analysis-all-24.json +230 -0
- chronaxis/guide/fields/mapping/analysis-all-25.json +227 -0
- chronaxis/guide/fields/mapping/analysis-all-26.json +230 -0
- chronaxis/guide/fields/mapping/analysis-all-27.json +221 -0
- chronaxis/guide/fields/mapping/analysis-all-28.json +237 -0
- chronaxis/guide/fields/mapping/analysis-all-29.json +233 -0
- chronaxis/guide/fields/mapping/analysis-all-3.json +322 -0
- chronaxis/guide/fields/mapping/analysis-all-30.json +244 -0
- chronaxis/guide/fields/mapping/analysis-all-31.json +228 -0
- chronaxis/guide/fields/mapping/analysis-all-32.json +226 -0
- chronaxis/guide/fields/mapping/analysis-all-33.json +230 -0
- chronaxis/guide/fields/mapping/analysis-all-34.json +227 -0
- chronaxis/guide/fields/mapping/analysis-all-35.json +230 -0
- chronaxis/guide/fields/mapping/analysis-all-36.json +221 -0
- chronaxis/guide/fields/mapping/analysis-all-37.json +291 -0
- chronaxis/guide/fields/mapping/analysis-all-38.json +315 -0
- chronaxis/guide/fields/mapping/analysis-all-39.json +304 -0
- chronaxis/guide/fields/mapping/analysis-all-4.json +312 -0
- chronaxis/guide/fields/mapping/analysis-all-40.json +307 -0
- chronaxis/guide/fields/mapping/analysis-all-41.json +292 -0
- chronaxis/guide/fields/mapping/analysis-all-42.json +333 -0
- chronaxis/guide/fields/mapping/analysis-all-43.json +296 -0
- chronaxis/guide/fields/mapping/analysis-all-44.json +322 -0
- chronaxis/guide/fields/mapping/analysis-all-45.json +298 -0
- chronaxis/guide/fields/mapping/analysis-all-46.json +347 -0
- chronaxis/guide/fields/mapping/analysis-all-47.json +302 -0
- chronaxis/guide/fields/mapping/analysis-all-48.json +263 -0
- chronaxis/guide/fields/mapping/analysis-all-49.json +301 -0
- chronaxis/guide/fields/mapping/analysis-all-5.json +313 -0
- chronaxis/guide/fields/mapping/analysis-all-50.json +336 -0
- chronaxis/guide/fields/mapping/analysis-all-51.json +335 -0
- chronaxis/guide/fields/mapping/analysis-all-52.json +335 -0
- chronaxis/guide/fields/mapping/analysis-all-53.json +334 -0
- chronaxis/guide/fields/mapping/analysis-all-54.json +339 -0
- chronaxis/guide/fields/mapping/analysis-all-55.json +335 -0
- chronaxis/guide/fields/mapping/analysis-all-56.json +336 -0
- chronaxis/guide/fields/mapping/analysis-all-57.json +335 -0
- chronaxis/guide/fields/mapping/analysis-all-58.json +333 -0
- chronaxis/guide/fields/mapping/analysis-all-59.json +325 -0
- chronaxis/guide/fields/mapping/analysis-all-6.json +323 -0
- chronaxis/guide/fields/mapping/analysis-all-60.json +334 -0
- chronaxis/guide/fields/mapping/analysis-all-61.json +311 -0
- chronaxis/guide/fields/mapping/analysis-all-62.json +289 -0
- chronaxis/guide/fields/mapping/analysis-all-63.json +383 -0
- chronaxis/guide/fields/mapping/analysis-all-64.json +357 -0
- chronaxis/guide/fields/mapping/analysis-all-65.json +375 -0
- chronaxis/guide/fields/mapping/analysis-all-66.json +351 -0
- chronaxis/guide/fields/mapping/analysis-all-67.json +346 -0
- chronaxis/guide/fields/mapping/analysis-all-68.json +317 -0
- chronaxis/guide/fields/mapping/analysis-all-69.json +313 -0
- chronaxis/guide/fields/mapping/analysis-all-7.json +306 -0
- chronaxis/guide/fields/mapping/analysis-all-70.json +326 -0
- chronaxis/guide/fields/mapping/analysis-all-71.json +316 -0
- chronaxis/guide/fields/mapping/analysis-all-72.json +264 -0
- chronaxis/guide/fields/mapping/analysis-all-73.json +228 -0
- chronaxis/guide/fields/mapping/analysis-all-74.json +241 -0
- chronaxis/guide/fields/mapping/analysis-all-75.json +273 -0
- chronaxis/guide/fields/mapping/analysis-all-76.json +382 -0
- chronaxis/guide/fields/mapping/analysis-all-77.json +328 -0
- chronaxis/guide/fields/mapping/analysis-all-78.json +338 -0
- chronaxis/guide/fields/mapping/analysis-all-79.json +304 -0
- chronaxis/guide/fields/mapping/analysis-all-8.json +309 -0
- chronaxis/guide/fields/mapping/analysis-all-80.json +140 -0
- chronaxis/guide/fields/mapping/analysis-all-9.json +329 -0
- chronaxis/guide/fields/mapping/io_policy-all-1.json +19 -0
- chronaxis/guide/fields/mapping/mapping_version-all-1.json +19 -0
- chronaxis/guide/fields/mapping/path_base-all-1.json +19 -0
- chronaxis/guide/fields/mapping/sections-all-1.json +402 -0
- chronaxis/guide/fields/mapping/sections-all-2.json +232 -0
- chronaxis/guide/lookup.py +90 -0
- chronaxis/guide/manifest.json +614 -0
- chronaxis/guide/run_analysis.py +34 -0
- chronaxis/guide/schemas/analysis.schema.json +8451 -0
- chronaxis/guide/schemas/batch-v1.schema.json +172 -0
- chronaxis/guide/schemas/definitions.schema.json +29 -0
- chronaxis/guide/schemas/legacy-import-v1.schema.json +143 -0
- chronaxis/guide/semantics.md +62 -0
- chronaxis/guide/tasks.json +290 -0
- chronaxis/guide/workflow.md +38 -0
- chronaxis/legacy/__init__.py +46 -0
- chronaxis/legacy/batch_read.py +412 -0
- chronaxis/legacy/batch_validation.py +134 -0
- chronaxis/legacy/batch_wire.py +264 -0
- chronaxis/legacy/batch_worker.py +417 -0
- chronaxis/legacy/binding.py +154 -0
- chronaxis/legacy/dbc_cycles.py +47 -0
- chronaxis/legacy/decode_policy.py +28 -0
- chronaxis/legacy/disjunction.py +79 -0
- chronaxis/legacy/export_worker.py +147 -0
- chronaxis/legacy/export_write.py +378 -0
- chronaxis/legacy/message_store.py +562 -0
- chronaxis/legacy/process_read.py +526 -0
- chronaxis/legacy/raw_store.py +341 -0
- chronaxis/legacy/records.py +709 -0
- chronaxis/legacy/required_records.py +122 -0
- chronaxis/legacy/sum.py +403 -0
- chronaxis/legacy/sum_numpy.py +43 -0
- chronaxis/legacy/updates.py +277 -0
- chronaxis/legacy/vendor/sclicer_functions_v1/can_processor.py +138 -0
- chronaxis/legacy/vendor/sclicer_functions_v1/file_processor.py +218 -0
- chronaxis/legacy/vendor/sclicer_functions_v1/utils.py +447 -0
- chronaxis/legacy/worker.py +352 -0
- chronaxis/migration/__init__.py +11 -0
- chronaxis/migration/api.py +270 -0
- chronaxis/migration/ini.py +110 -0
- chronaxis/migration/legacy_sum.py +304 -0
- chronaxis/migration/models.py +83 -0
- chronaxis/migration/publication.py +230 -0
- chronaxis/migration/sclicer.py +241 -0
- chronaxis/migration/slope.py +78 -0
- chronaxis/migration/start_end.py +48 -0
- chronaxis/planning/__init__.py +19 -0
- chronaxis/planning/channels.py +30 -0
- chronaxis/planning/checks.py +447 -0
- chronaxis/planning/config_groups.py +215 -0
- chronaxis/planning/dbc_defaults.py +88 -0
- chronaxis/planning/export_options.py +247 -0
- chronaxis/planning/input_defaults.py +62 -0
- chronaxis/planning/input_paths.py +124 -0
- chronaxis/planning/input_requirements.py +250 -0
- chronaxis/planning/inputs.py +306 -0
- chronaxis/planning/intervals.py +242 -0
- chronaxis/planning/legacy_execution.py +38 -0
- chronaxis/planning/message_calculations.py +171 -0
- chronaxis/planning/models.py +369 -0
- chronaxis/planning/nodes.py +355 -0
- chronaxis/planning/plan.py +294 -0
- chronaxis/planning/preset_models.py +211 -0
- chronaxis/planning/record_execution.py +76 -0
- chronaxis/planning/reports.py +523 -0
- chronaxis/planning/sequences.py +91 -0
- chronaxis/planning/signal_groups.py +61 -0
- chronaxis/planning/signal_validity.py +46 -0
- chronaxis/planning/text_inputs.py +110 -0
- chronaxis/presets.py +270 -0
- chronaxis/results/__init__.py +34 -0
- chronaxis/results/analysis_outcome.py +67 -0
- chronaxis/results/artifact_exports.py +212 -0
- chronaxis/results/binding_metadata.py +54 -0
- chronaxis/results/budget.py +138 -0
- chronaxis/results/can_metadata.py +247 -0
- chronaxis/results/codec.py +246 -0
- chronaxis/results/errors.py +25 -0
- chronaxis/results/export_files.py +216 -0
- chronaxis/results/frame_exports.py +299 -0
- chronaxis/results/frame_patch.py +186 -0
- chronaxis/results/frame_rebuild.py +458 -0
- chronaxis/results/frame_sort.py +223 -0
- chronaxis/results/input_diagnostics.py +51 -0
- chronaxis/results/manifest.py +343 -0
- chronaxis/results/merge_runs.py +207 -0
- chronaxis/results/owned_directory.py +32 -0
- chronaxis/results/raw_exports.py +689 -0
- chronaxis/results/readable.py +355 -0
- chronaxis/results/readable_format.py +94 -0
- chronaxis/results/result.py +734 -0
- chronaxis/results/rows.py +57 -0
- chronaxis/results/signal_exports.py +209 -0
- chronaxis/results/signal_grid.py +219 -0
- chronaxis/results/spool.py +421 -0
- chronaxis/results/summary.py +350 -0
- chronaxis/results/text_can_metadata.py +64 -0
- chronaxis/results/threshold_metadata.py +105 -0
- chronaxis/runner.py +121 -0
- chronaxis/sources/__init__.py +23 -0
- chronaxis/sources/asc.py +412 -0
- chronaxis/sources/blf.py +101 -0
- chronaxis/sources/can_spec.py +179 -0
- chronaxis/sources/can_updates.py +160 -0
- chronaxis/sources/csv_spec.py +133 -0
- chronaxis/sources/descriptions.py +65 -0
- chronaxis/sources/memory.py +299 -0
- chronaxis/sources/models.py +497 -0
- chronaxis/sources/packing.py +170 -0
- chronaxis/sources/protocol.py +221 -0
- chronaxis/sources/raw_can.py +62 -0
- chronaxis/sources/raw_csv.py +470 -0
- chronaxis/sources/raw_csv_layout.py +310 -0
- chronaxis/sources/signal_csv.py +608 -0
- chronaxis/sources/text_can_decode.py +421 -0
- chronaxis/sources/text_can_ref.py +48 -0
- chronaxis/sources/text_can_spec.py +61 -0
- chronaxis/timebase/__init__.py +19 -0
- chronaxis/timebase/conversion.py +364 -0
- chronaxis/timebase/numpy_ops.py +104 -0
- chronaxis/user_guide.py +81 -0
- chronaxis-0.1.0.dev0.dist-info/METADATA +172 -0
- chronaxis-0.1.0.dev0.dist-info/RECORD +917 -0
- chronaxis-0.1.0.dev0.dist-info/WHEEL +5 -0
- chronaxis-0.1.0.dev0.dist-info/entry_points.txt +2 -0
- chronaxis-0.1.0.dev0.dist-info/licenses/LICENSE +21 -0
- chronaxis-0.1.0.dev0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
"""仅在信号省略类型/单位或enum映射时读取DBC元数据,不读取报文。
|
|
2
|
+
|
|
3
|
+
每次计划编译按DBC路径共用一次加载;结果冻结为已有SignalDefinition字段。
|
|
4
|
+
数值信号不会因存在VAL表而变成文字枚举。重新加载配置才重新推导默认值。
|
|
5
|
+
"""
|
|
6
|
+
from .checks import PlanValidationError
|
|
7
|
+
from ..legacy.binding import dbc_candidates
|
|
8
|
+
from ..can_dependencies import CANDependencyError, import_can_dependency
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
def _numeric_dtype(signal):
|
|
12
|
+
"""按解码后的数值范围选类型;有浮点缩放就使用float64,不丢弃小数。"""
|
|
13
|
+
if signal.is_float or type(signal.scale) is not int or type(signal.offset) is not int:
|
|
14
|
+
return 'float64'
|
|
15
|
+
low = -(2**(signal.length-1)) if signal.is_signed else 0
|
|
16
|
+
high = 2**(signal.length-1)-1 if signal.is_signed else 2**signal.length-1
|
|
17
|
+
limits = sorted((low*signal.scale+signal.offset, high*signal.scale+signal.offset))
|
|
18
|
+
if -(2**63) <= limits[0] and limits[1] < 2**63:
|
|
19
|
+
return 'int64'
|
|
20
|
+
if 0 <= limits[0] and limits[1] < 2**64:
|
|
21
|
+
return 'uint64'
|
|
22
|
+
raise ValueError('DBC缩放后的整数超出64位,请显式选择dtype并核对数值范围')
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
def _enum_choices(signal):
|
|
26
|
+
"""把DBC原码表转换到既有解码值域,不对实际记录再施加一次DBC缩放。"""
|
|
27
|
+
if not signal.choices:
|
|
28
|
+
raise ValueError('DBC没有该信号的枚举表,请提供choices或选择数值dtype')
|
|
29
|
+
result = []
|
|
30
|
+
for code, label in signal.choices.items():
|
|
31
|
+
value = signal.conversion.raw_to_scaled(code, decode_choices=False)
|
|
32
|
+
# 核心枚举编码保持int/bool/str契约;不把浮点物理值截断成整数码。
|
|
33
|
+
if type(value) is not int or signal.is_float:
|
|
34
|
+
raise ValueError('DBC枚举缩放产生浮点值,当前枚举编码不支持;请使用数值dtype,不会截断或重复缩放')
|
|
35
|
+
text = str(label)
|
|
36
|
+
if not text:
|
|
37
|
+
raise ValueError('DBC枚举标签为空,请提供明确choices')
|
|
38
|
+
result.append([value,text])
|
|
39
|
+
return result
|
|
40
|
+
|
|
41
|
+
|
|
42
|
+
class DBCDefaults:
|
|
43
|
+
"""一次计划编译内的临时数据库缓存,显式完整声明不打开DBC。"""
|
|
44
|
+
def __init__(self):
|
|
45
|
+
"""创建空缓存,不访问磁盘。"""
|
|
46
|
+
self.databases = {}
|
|
47
|
+
|
|
48
|
+
def fill(self, raw, config, field, path):
|
|
49
|
+
"""参数为信号配置、CAN来源和定位;返回补默认值的独立dict,错误定位到信号。"""
|
|
50
|
+
result = dict(raw)
|
|
51
|
+
# 手工映射已明确标签类型,可以直接得出逻辑dtype,不读取DBC作第二次猜测。
|
|
52
|
+
choices = result.get('choices')
|
|
53
|
+
if 'dtype' not in result and type(choices) is list and choices:
|
|
54
|
+
if all(type(pair) is list and len(pair)==2 and type(pair[1]) is str for pair in choices):
|
|
55
|
+
result['dtype']='enum'
|
|
56
|
+
elif all(type(pair) is list and len(pair)==2 and type(pair[1]) is bool for pair in choices):
|
|
57
|
+
result['dtype']='bool'
|
|
58
|
+
needed = [key for key in ('dtype','unit') if key not in result]
|
|
59
|
+
if result.get('dtype') == 'enum' and 'choices' not in result:
|
|
60
|
+
needed.append('choices')
|
|
61
|
+
if not needed:
|
|
62
|
+
return result
|
|
63
|
+
try:
|
|
64
|
+
key = str(config.dbc_path)
|
|
65
|
+
if key not in self.databases:
|
|
66
|
+
cantools = import_can_dependency('cantools')
|
|
67
|
+
self.databases[key] = cantools.database.load_file(key)
|
|
68
|
+
candidates = dbc_candidates(self.databases[key],field.frame_id,(field.signal,),field.is_extended,field.is_fd)
|
|
69
|
+
signals = [next(s for s in message.signals if s.name==field.signal) for message in candidates]
|
|
70
|
+
for name in needed:
|
|
71
|
+
if name == 'dtype':
|
|
72
|
+
values = [_numeric_dtype(signal) for signal in signals]
|
|
73
|
+
elif name == 'unit':
|
|
74
|
+
# 无单位定义时标未知,不冒称已核实为V/A或无量纲。
|
|
75
|
+
values = [signal.unit or ('1' if result.get('dtype') in ('enum','bool') else 'unknown') for signal in signals]
|
|
76
|
+
else:
|
|
77
|
+
values = [_enum_choices(signal) for signal in signals]
|
|
78
|
+
if any(value != values[0] for value in values[1:]):
|
|
79
|
+
raise ValueError(f'候选DBC的{name}不同,请补充帧类型或显式{name}')
|
|
80
|
+
result[name] = values[0]
|
|
81
|
+
except CANDependencyError as error:
|
|
82
|
+
# 这是来源的安装环境缺项,不要求用户反复修改当前信号字段。
|
|
83
|
+
raise PlanValidationError('$.sources', str(error), error.code,
|
|
84
|
+
hint=error.hint, object_name='来源 ' + config.name) from error
|
|
85
|
+
except Exception as error:
|
|
86
|
+
# 不吞文件/解析错误,不用猜测值替代无法读取的元数据。
|
|
87
|
+
raise PlanValidationError(path,'无法从DBC补充信号声明:'+str(error)) from error
|
|
88
|
+
return result
|
|
@@ -0,0 +1,247 @@
|
|
|
1
|
+
"""解释独立的信号CSV和CAN报文输出选项,默认均关闭。
|
|
2
|
+
|
|
3
|
+
只构造已实现低层导出的类型化规格;不加载DBC、不读取输入或输出文件。
|
|
4
|
+
信号分类使用明确别名,报文重建用明确原字段,范围引用既有会话或窗口。
|
|
5
|
+
日期规则按用户确认检查,未支持的选项严格拒绝,不让schema接受空实现。
|
|
6
|
+
"""
|
|
7
|
+
|
|
8
|
+
from dataclasses import dataclass
|
|
9
|
+
|
|
10
|
+
from ..core.types import SignalDType
|
|
11
|
+
from ..results.signal_exports import SignalCSVExportSpec
|
|
12
|
+
from ..results.signal_grid import SignalGridSpec
|
|
13
|
+
from ..results.frame_exports import FrameExportSpec
|
|
14
|
+
from ..results.frame_rebuild import FrameGridSpec
|
|
15
|
+
from ..results.frame_patch import FrameRebuildRule
|
|
16
|
+
from .checks import (PlanValidationError,array_at,choice_at,coordinate_at,duration_at,model_at,object_at,text_at)
|
|
17
|
+
from ..core.validation import require_identifier
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
@dataclass(frozen=True)
|
|
21
|
+
class SignalCSVOutput:
|
|
22
|
+
"""保存信号表输出规格及范围,不拥有运行时历史或文件。"""
|
|
23
|
+
|
|
24
|
+
spec: SignalCSVExportSpec
|
|
25
|
+
scope: str = 'session'
|
|
26
|
+
window: str | None = None
|
|
27
|
+
period_driver: str | None = None # 仅DBC信号网格,已解析的原始报文别名。
|
|
28
|
+
|
|
29
|
+
def __post_init__(self):
|
|
30
|
+
"""校验冻结声明,typed构造同样受约束。参数: 字段。返回: None。异常: 类型/范围错。
|
|
31
|
+
"""
|
|
32
|
+
if type(self.spec) is not SignalCSVExportSpec:
|
|
33
|
+
raise TypeError('signal_csv需要SignalCSVExportSpec')
|
|
34
|
+
_typed_scope(self.scope,self.window)
|
|
35
|
+
if self.period_driver is not None:
|
|
36
|
+
require_identifier(self.period_driver,'signal_csv.resampling.period.driver')
|
|
37
|
+
if (self.period_driver is not None)!=(self.spec.resampling is not None and self.spec.resampling.period_ns is None):
|
|
38
|
+
raise ValueError('DBC信号网格需要已解析驱动,固定网格不能附带驱动')
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
@dataclass(frozen=True)
|
|
42
|
+
class CANFramesOutput:
|
|
43
|
+
"""保存一个来源的原始/重建帧输出规格,与信号表的网格和开关独立。"""
|
|
44
|
+
|
|
45
|
+
source: str
|
|
46
|
+
spec: FrameExportSpec
|
|
47
|
+
scope: str = 'session'
|
|
48
|
+
window: str | None = None
|
|
49
|
+
resampling: FrameGridSpec | None = None
|
|
50
|
+
rules: tuple[FrameRebuildRule,...] = ()
|
|
51
|
+
|
|
52
|
+
def __post_init__(self):
|
|
53
|
+
"""校验来源、独立规格和重建规则。参数: 字段。返回: None。异常: 类型/范围错。
|
|
54
|
+
"""
|
|
55
|
+
require_identifier(self.source,'can_frames.source'); _typed_scope(self.scope,self.window,allow_all=True)
|
|
56
|
+
if type(self.spec) is not FrameExportSpec or self.resampling is not None and type(self.resampling) is not FrameGridSpec:
|
|
57
|
+
raise TypeError('can_frames需要冻结帧规格与可选网格')
|
|
58
|
+
if type(self.rules) is not tuple or len(self.rules)>4096 or any(type(r) is not FrameRebuildRule for r in self.rules):
|
|
59
|
+
raise TypeError('重建规则需要有限FrameRebuildRule tuple')
|
|
60
|
+
if self.rules and self.resampling is None:
|
|
61
|
+
raise ValueError('未启用重采样不能配置重建规则')
|
|
62
|
+
identities={(r.channel,r.frame_id,r.is_extended,r.is_fd) for r in self.rules}
|
|
63
|
+
if len(identities)!=len(self.rules) or self.resampling is not None and not self.rules and self.resampling.unknown_policy!='nearest':
|
|
64
|
+
raise ValueError('重建规则重复或没有可执行规则')
|
|
65
|
+
|
|
66
|
+
|
|
67
|
+
def _typed_scope(scope,window,*,allow_all=False):
|
|
68
|
+
"""核typed范围与窗口配对。参数: scope/window。返回: None。异常: 不支持或组合错误。
|
|
69
|
+
"""
|
|
70
|
+
if scope not in ('session','segments') or scope=='session' and window is not None:
|
|
71
|
+
raise ValueError('导出范围错误')
|
|
72
|
+
if scope=='segments' and not (allow_all and window is None):
|
|
73
|
+
require_identifier(window,'exports.window')
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
def require_export_options(plan):
|
|
77
|
+
"""核typed选项引用当前来源/信号/窗口,不读DBC。参数: plan。返回: None。异常: 声明或引用错误。
|
|
78
|
+
"""
|
|
79
|
+
windows={w.window_id for w in plan.windows}; definitions={s.definition.name:s.definition for s in plan.signals}
|
|
80
|
+
for export_type,expected in (('signal_csv',SignalCSVOutput),('can_frames',CANFramesOutput)):
|
|
81
|
+
option=getattr(plan.outputs,export_type)
|
|
82
|
+
if option is None:
|
|
83
|
+
continue
|
|
84
|
+
if type(option) is not expected:
|
|
85
|
+
raise TypeError(export_type+'需要冻结typed输出声明')
|
|
86
|
+
option.__post_init__()
|
|
87
|
+
if option.scope=='segments' and not ((export_type=='can_frames') and (option.window is None)) and option.window not in windows:
|
|
88
|
+
raise ValueError('导出窗口未在当前计划声明')
|
|
89
|
+
if export_type=='signal_csv':
|
|
90
|
+
if any(name not in definitions for name in option.spec.signals):
|
|
91
|
+
raise ValueError('导出信号未在当前计划声明')
|
|
92
|
+
if option.spec.resampling is not None and any(definitions[name].dtype not in
|
|
93
|
+
(SignalDType.FLOAT64,SignalDType.INT64,SignalDType.UINT64) for name in option.spec.resampling.continuous):
|
|
94
|
+
raise ValueError('状态/枚举信号不能线性插值')
|
|
95
|
+
if option.period_driver is not None:
|
|
96
|
+
_signal_grid_driver(definitions,plan.sources,option.spec.resampling.continuous,option.period_driver,'$.outputs.signal_csv')
|
|
97
|
+
else:
|
|
98
|
+
source=next((s for s in plan.sources if s.name==option.source),None)
|
|
99
|
+
if source is None or source.source_type not in ('can_blf','can_asc','asc_or_blf','raw_can_csv'):
|
|
100
|
+
raise ValueError('报文导出需要本计划CAN来源')
|
|
101
|
+
_require_frame_direction(source)
|
|
102
|
+
if any(rule.channel!=source.config.channel for rule in option.rules):
|
|
103
|
+
raise ValueError('重建报文通道与来源不同')
|
|
104
|
+
|
|
105
|
+
|
|
106
|
+
def _scope(raw,path,windows,*,allow_all=False):
|
|
107
|
+
"""核会话或单个显式窗口引用。参数: raw/path/windows。返回: (scope,window)。异常: 配置错。
|
|
108
|
+
"""
|
|
109
|
+
scope=choice_at(raw.get('scope','session'),('session','segments'),path+'.scope')
|
|
110
|
+
window=raw.get('window')
|
|
111
|
+
if scope=='session' and window is not None:
|
|
112
|
+
raise PlanValidationError(path+'.window','session范围不能同时指定窗口')
|
|
113
|
+
if scope=='segments' and not (allow_all and 'window' not in raw):
|
|
114
|
+
window=text_at(window,path+'.window',identifier=True)
|
|
115
|
+
if window not in {item.window_id for item in windows}:
|
|
116
|
+
raise PlanValidationError(path+'.window','未知窗口:'+window)
|
|
117
|
+
return scope,window
|
|
118
|
+
|
|
119
|
+
|
|
120
|
+
def _grid(raw,path):
|
|
121
|
+
"""解析显式单位的全局网格。参数: raw/path。返回: period/origin/max_gap整数ns。异常: 时间错。
|
|
122
|
+
"""
|
|
123
|
+
return (duration_at(raw['period'],path+'.period',positive=True),
|
|
124
|
+
coordinate_at(raw.get('origin','0s'),path+'.origin'),duration_at(raw['max_gap'],path+'.max_gap',positive=True))
|
|
125
|
+
|
|
126
|
+
|
|
127
|
+
def _signal_grid_driver(definitions,sources,continuous,driver,path):
|
|
128
|
+
"""同一信号网格使用一个明确DBC周期;多报文不能擅自选最快周期。
|
|
129
|
+
|
|
130
|
+
参数: 有限定义/来源/连续量/可选驱动/路径。返回: 唯一原始别名。异常: 类型/格式/歧义。
|
|
131
|
+
"""
|
|
132
|
+
from ..sources.can_spec import can_field_from_key
|
|
133
|
+
source_types={source.name:source.source_type for source in sources}
|
|
134
|
+
candidates={}
|
|
135
|
+
for name in continuous:
|
|
136
|
+
definition=definitions[name]
|
|
137
|
+
if source_types[definition.source] not in ('can_blf','can_asc','asc_or_blf','raw_can_csv'):
|
|
138
|
+
raise PlanValidationError(path+'.resampling.period','已解析信号不能选择DBC周期')
|
|
139
|
+
field=can_field_from_key(definition.field)
|
|
140
|
+
candidates.setdefault((definition.source,field.channel,field.frame_id,field.is_extended,field.is_fd),name)
|
|
141
|
+
if driver is not None:
|
|
142
|
+
if type(driver) is not str or driver not in continuous:
|
|
143
|
+
raise PlanValidationError(path+'.resampling.period.driver','驱动须属于本次连续原始信号')
|
|
144
|
+
return driver
|
|
145
|
+
if len(candidates)!=1:
|
|
146
|
+
raise PlanValidationError(path+'.resampling.period.driver','多个报文周期需要明确指定驱动信号')
|
|
147
|
+
return next(iter(candidates.values()))
|
|
148
|
+
|
|
149
|
+
|
|
150
|
+
def parse_signal_output(value,signals,windows,*,sources=()):
|
|
151
|
+
"""核显式信号选择及连续量分类。参数: value、当前信号/窗口。返回: SignalCSVOutput或None。异常: 定位配置错。
|
|
152
|
+
"""
|
|
153
|
+
if value is None:
|
|
154
|
+
return None
|
|
155
|
+
path='$.outputs.signal_csv'
|
|
156
|
+
raw=object_at(value,path,('signals',),('scope','window','resampling'))
|
|
157
|
+
names=tuple(array_at(raw['signals'],path+'.signals'))
|
|
158
|
+
definitions={s.definition.name:s.definition for s in signals}
|
|
159
|
+
if any(type(n) is not str or n not in definitions for n in names):
|
|
160
|
+
raise PlanValidationError(path+'.signals','导出信号必须为已定义的原信号别名')
|
|
161
|
+
grid=None;driver=None
|
|
162
|
+
if raw.get('resampling') is not None:
|
|
163
|
+
res=object_at(raw['resampling'],path+'.resampling',('continuous','period','max_gap'),('origin',))
|
|
164
|
+
continuous=tuple(array_at(res['continuous'],path+'.resampling.continuous'))
|
|
165
|
+
if any(type(n) is not str or n not in definitions or definitions[n].dtype not in
|
|
166
|
+
(SignalDType.FLOAT64,SignalDType.INT64,SignalDType.UINT64) for n in continuous):
|
|
167
|
+
raise PlanValidationError(path+'.resampling.continuous','连续量必须为当前已定义的数值信号,状态/枚举不能插值')
|
|
168
|
+
if type(res['period']) is dict:
|
|
169
|
+
period_choice=object_at(res['period'],path+'.resampling.period',('mode',),('driver',))
|
|
170
|
+
if 'driver' in period_choice and type(period_choice['driver']) is not str:
|
|
171
|
+
raise PlanValidationError(path+'.resampling.period.driver','显式driver必须为信号名称')
|
|
172
|
+
if period_choice['mode']!='dbc':raise PlanValidationError(path+'.resampling.period.mode','网格对象需dbc,固定周期使用带单位数值')
|
|
173
|
+
driver=_signal_grid_driver(definitions,sources,continuous,period_choice.get('driver'),path)
|
|
174
|
+
period=None
|
|
175
|
+
origin=coordinate_at(res.get('origin','0s'),path+'.resampling.origin')
|
|
176
|
+
gap=duration_at(res['max_gap'],path+'.resampling.max_gap',positive=True)
|
|
177
|
+
else:
|
|
178
|
+
period,origin,gap=_grid(res,path+'.resampling')
|
|
179
|
+
grid=model_at(SignalGridSpec,path+'.resampling',continuous,period,origin,gap)
|
|
180
|
+
spec=model_at(SignalCSVExportSpec,path,names,grid)
|
|
181
|
+
scope,window=_scope(raw,path,windows)
|
|
182
|
+
return SignalCSVOutput(spec,scope,window,driver)
|
|
183
|
+
|
|
184
|
+
|
|
185
|
+
def _require_frame_direction(source):
|
|
186
|
+
"""只有原帧导出/重建需要收发方向;分析可保留未知方向。"""
|
|
187
|
+
if source.source_type == 'raw_can_csv' and any(
|
|
188
|
+
'is_rx' not in item.layout.fields for item in source.config.inputs):
|
|
189
|
+
raise PlanValidationError('$.outputs.can_frames',
|
|
190
|
+
'原始报文导出或重建需要收发方向,请在CSV字段映射中提供is_rx;普通分析可以省略')
|
|
191
|
+
|
|
192
|
+
|
|
193
|
+
def parse_frame_output(value,sources,windows):
|
|
194
|
+
"""核帧来源、日期和可选重建规则。参数: value、当前来源/窗口。返回: CANFramesOutput或None。异常: 定位配置错。
|
|
195
|
+
"""
|
|
196
|
+
if value is None:
|
|
197
|
+
return None
|
|
198
|
+
path='$.outputs.can_frames'
|
|
199
|
+
raw=object_at(value,path,('format',),('source','scope','window','resampling','output_offset',
|
|
200
|
+
'source_time_reference','capture_date','timezone_offset_minutes'))
|
|
201
|
+
from .input_defaults import source_reference
|
|
202
|
+
source=source_reference(raw,sources,path,can_only=True)
|
|
203
|
+
declared=next((s for s in sources if s.name==source),None)
|
|
204
|
+
if declared is None or declared.source_type not in ('can_blf','can_asc','asc_or_blf','raw_can_csv'):
|
|
205
|
+
raise PlanValidationError(path+'.source','报文导出需要当前已支持的CAN来源')
|
|
206
|
+
_require_frame_direction(declared)
|
|
207
|
+
reference=raw.get('source_time_reference','epoch' if declared.config.timebase.time_type.value=='absolute' else 'relative')
|
|
208
|
+
spec=model_at(FrameExportSpec,path,choice_at(raw['format'],('asc','blf'),path+'.format'),
|
|
209
|
+
coordinate_at(raw.get('output_offset','0s'),path+'.output_offset'),reference,
|
|
210
|
+
raw.get('capture_date'),raw.get('timezone_offset_minutes'))
|
|
211
|
+
scope,window=_scope(raw,path,windows,allow_all=True)
|
|
212
|
+
grid=None; rules=[]
|
|
213
|
+
if raw.get('resampling') is not None:
|
|
214
|
+
res=object_at(raw['resampling'],path+'.resampling',('period','max_gap','messages'),
|
|
215
|
+
('origin','unknown_policy','max_distance'))
|
|
216
|
+
if type(res['period']) is dict:
|
|
217
|
+
choice=object_at(res['period'],path+'.resampling.period',('mode',),())
|
|
218
|
+
if (choice['mode']!='dbc'):
|
|
219
|
+
raise PlanValidationError(path+'.resampling.period','按各报文DBC周期重采样时,period.mode必须为dbc')
|
|
220
|
+
period=None
|
|
221
|
+
origin=coordinate_at(res.get('origin','0s'),path+'.resampling.origin')
|
|
222
|
+
gap=duration_at(res['max_gap'],path+'.resampling.max_gap',positive=True)
|
|
223
|
+
else:
|
|
224
|
+
period,origin,gap=_grid(res,path+'.resampling')
|
|
225
|
+
distance=duration_at(res['max_distance'],path+'.resampling.max_distance',positive=False) if 'max_distance' in res else None
|
|
226
|
+
grid=model_at(FrameGridSpec,path+'.resampling',period,origin,gap,res.get('unknown_policy','passthrough'),distance)
|
|
227
|
+
for index,item in enumerate(array_at(res['messages'],path+'.resampling.messages')):
|
|
228
|
+
where=f'{path}.resampling.messages[{index}]'
|
|
229
|
+
item=object_at(item,where,('frame_id','continuous'),('channel','is_extended','is_fd','protected','same_time_policy'))
|
|
230
|
+
# 省略表示自动识别;显式null不能悄悄取得默认行为。
|
|
231
|
+
for flag in ('is_extended','is_fd'):
|
|
232
|
+
if flag in item and type(item[flag]) is not bool:
|
|
233
|
+
raise PlanValidationError(where+'.'+flag,'填写时需要bool;自动识别请省略该项')
|
|
234
|
+
from .channels import channel_index
|
|
235
|
+
channel = channel_index(item['channel'],where+'.channel') if 'channel' in item else declared.config.channel
|
|
236
|
+
rule=model_at(FrameRebuildRule,where,channel,item['frame_id'],
|
|
237
|
+
tuple(array_at(item['continuous'],where+'.continuous')),item.get('is_extended'),item.get('is_fd'),
|
|
238
|
+
tuple(array_at(item.get('protected',[]),where+'.protected')),item.get('same_time_policy','error'))
|
|
239
|
+
if rule.channel!=declared.config.channel:
|
|
240
|
+
raise PlanValidationError(where+'.channel','重建规则通道必须匹配来源的DBC通道')
|
|
241
|
+
rules.append(rule)
|
|
242
|
+
identities=[(r.channel,r.frame_id,r.is_extended,r.is_fd) for r in rules]
|
|
243
|
+
if len(rules)>4096 or len(set(identities))!=len(rules):
|
|
244
|
+
raise PlanValidationError(path+'.resampling.messages','报文规则重复或超过4096项')
|
|
245
|
+
if not rules and grid.unknown_policy!='nearest':
|
|
246
|
+
raise PlanValidationError(path+'.resampling.messages','重建需明确报文清单或未知报文最近邻策略')
|
|
247
|
+
return CANFramesOutput(source,spec,scope,window,grid,tuple(rules))
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
"""补齐来源的常用声明,只有唯一候选时自动选择引用。
|
|
2
|
+
|
|
3
|
+
输入为已检查JSON结构的配置;输出独立字典或来源名称。不打开数据/DBC,
|
|
4
|
+
不改输入值和时间戳。相对时间缺省采用来源专属基准,不声称多来源已经同步。
|
|
5
|
+
"""
|
|
6
|
+
|
|
7
|
+
# 仅用路径后缀识别自描述的CAN文件;格式正文仍由原读取器严格检查。
|
|
8
|
+
from pathlib import Path
|
|
9
|
+
from .checks import PlanValidationError, array_at, object_at, text_at
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
def source_defaults(raw, index, *, inferred_type=None):
|
|
13
|
+
"""补来源名、ASC/BLF格式及时间默认值,不修改调用方字典。
|
|
14
|
+
|
|
15
|
+
参数: raw为单来源字典,index为零基来源序号;inferred_type为已编译来源类型。
|
|
16
|
+
返回: 新字典;已有计划的调用方可避免重复展开目录。
|
|
17
|
+
异常: PlanValidationError表示未知格式、显式空时间或非法名称。
|
|
18
|
+
"""
|
|
19
|
+
# 自动名只作当前计划内定位,重名由原来源解析器统一拒绝。
|
|
20
|
+
result = dict(raw)
|
|
21
|
+
path = f'$.sources[{index}]'
|
|
22
|
+
result.setdefault('name', f'source_{index + 1}')
|
|
23
|
+
name = text_at(result['name'], path + '.name', identifier=True)
|
|
24
|
+
if inferred_type is not None and ('source_type' not in result or result['source_type'] == 'asc_or_blf'):
|
|
25
|
+
result['source_type'] = inferred_type
|
|
26
|
+
if inferred_type is None and ('source_type' not in result or result['source_type'] == 'asc_or_blf'):
|
|
27
|
+
# 这里只识别明确文件后缀;目录展开由文件输入节点实施,CSV必须声明含义。
|
|
28
|
+
paths = [result['path']] if 'path' in result else array_at(result.get('paths', []), path + '.paths')
|
|
29
|
+
suffixes = {Path(text_at(item, f'{path}.paths[{i}]')).suffix.lower() for i, item in enumerate(paths)}
|
|
30
|
+
if not paths or not suffixes <= {'.asc', '.blf'}:
|
|
31
|
+
raise PlanValidationError(path + '.source_type',
|
|
32
|
+
'无法唯一识别ASC/BLF格式;CSV或内存输入请明确source_type')
|
|
33
|
+
result['source_type'] = ('can_asc' if suffixes == {'.asc'} else
|
|
34
|
+
'can_blf' if suffixes == {'.blf'} and 'offsets' not in result else 'asc_or_blf')
|
|
35
|
+
# 不用“or {}”吞掉显式null;用户输入的错误必须仍然报出。
|
|
36
|
+
clock = dict(object_at(result.get('time', {}), path + '.time', (),
|
|
37
|
+
('time_type', 'unit', 'origin', 'offset', 'timezone', 'timezone_offset_minutes')))
|
|
38
|
+
clock.setdefault('time_type', 'relative')
|
|
39
|
+
if result['source_type'] in ('can_blf', 'can_asc', 'asc_or_blf', 'memory'):
|
|
40
|
+
clock.setdefault('unit', 's')
|
|
41
|
+
if clock['time_type'] == 'relative':
|
|
42
|
+
# 缺省基准带来源名,不让独立采集的来源因共同默认字符串而被视为已同步。
|
|
43
|
+
clock.setdefault('origin', '__source_' + name)
|
|
44
|
+
result['time'] = clock
|
|
45
|
+
return result
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
def source_reference(raw, sources, path, *, can_only=False):
|
|
49
|
+
"""取显式来源名,或选择唯一适用来源;多候选不选第一项。
|
|
50
|
+
|
|
51
|
+
参数: raw为含可选source的对象,sources为来源计划序列,path为对象位置,
|
|
52
|
+
can_only限定原始CAN来源。返回: 来源名称字符串。
|
|
53
|
+
异常: PlanValidationError表示无候选、多候选或非法显式名称。
|
|
54
|
+
"""
|
|
55
|
+
if 'source' in raw:
|
|
56
|
+
# 显式null/空串不表示自动,原名称检查仍生效。
|
|
57
|
+
return text_at(raw['source'], path + '.source', identifier=True)
|
|
58
|
+
candidates = [item.name for item in sources if not can_only or
|
|
59
|
+
item.source_type in ('can_blf', 'can_asc', 'asc_or_blf', 'raw_can_csv')]
|
|
60
|
+
if len(candidates) != 1:
|
|
61
|
+
raise PlanValidationError(path + '.source', '请指定source;适用来源:' + ', '.join(candidates))
|
|
62
|
+
return candidates[0]
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
"""将文件、目录或通配符展开为有序输入,不读取报文内容。
|
|
2
|
+
|
|
3
|
+
明确文件列表保持用户顺序;每个目录或通配符内部采用自然排序。
|
|
4
|
+
只枚举显式请求的目录,不递归追踪子目录;递归必须通过**通配符提出。
|
|
5
|
+
展开最多4096项,空匹配及无效路径报配置错误,不悄悄跳过缺失目录。
|
|
6
|
+
"""
|
|
7
|
+
|
|
8
|
+
from glob import iglob
|
|
9
|
+
from pathlib import Path
|
|
10
|
+
import re
|
|
11
|
+
|
|
12
|
+
from .checks import PlanValidationError, absolute_path, array_at, coordinate_at, object_at, text_at
|
|
13
|
+
|
|
14
|
+
# 明确后缀的文件只做词法定位,保持现有静态配置不访问业务文件的行为。
|
|
15
|
+
FILE_SUFFIXES = frozenset(('.asc', '.blf', '.csv', '.txt'))
|
|
16
|
+
SOURCE_SUFFIXES = {'can_blf': {'.blf'}, 'can_asc': {'.asc'},
|
|
17
|
+
'raw_can_csv': {'.csv', '.txt'}, 'signal_csv': {'.csv', '.txt'}}
|
|
18
|
+
MAX_INPUT_FILES = 4096
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
def natural_path_key(path):
|
|
22
|
+
"""产生稳定自然序键,使file2排在file10前。
|
|
23
|
+
|
|
24
|
+
参数: path为Path。返回: 数字/文字分段键及原路径平局键。
|
|
25
|
+
异常: 无主动异常;不访问文件系统。
|
|
26
|
+
"""
|
|
27
|
+
text = str(path)
|
|
28
|
+
# 类型标签避免数字与文字直接比较;补原文本使01/1及大小写平局可复现。
|
|
29
|
+
parts = tuple((1, int(part)) if part.isdigit() else (0, part.casefold())
|
|
30
|
+
for part in re.split(r'(\d+)', text))
|
|
31
|
+
return parts, text.casefold(), text
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
def expand_source_files(raw, base, where):
|
|
35
|
+
"""按声明展开来源路径;目录只取该来源支持的格式。
|
|
36
|
+
|
|
37
|
+
参数: raw为来源字典,base为配置文件目录,where为来源错误位置。
|
|
38
|
+
返回: (绝对Path元组, 可选逐文件偏移字符串元组)。异常: PlanValidationError表示缺项、空匹配或超限;
|
|
39
|
+
OSError由目录读取产生并转换为带配置位置的错误。
|
|
40
|
+
副作用: 仅目录/通配符声明枚举文件名;明确文件不stat、不读数据内容。
|
|
41
|
+
"""
|
|
42
|
+
if ('path' in raw) == ('paths' in raw):
|
|
43
|
+
raise PlanValidationError(where, 'path与paths必须且只能提供一个')
|
|
44
|
+
key = 'path' if 'path' in raw else 'paths'
|
|
45
|
+
value = raw[key]
|
|
46
|
+
entries = [value] if type(value) in (str, dict) else array_at(value, where + '.' + key)
|
|
47
|
+
if not entries:
|
|
48
|
+
raise PlanValidationError(where + '.' + key, '至少需要一个输入文件或目录')
|
|
49
|
+
allowed = SOURCE_SUFFIXES.get(raw.get('source_type'), {'.asc', '.blf'})
|
|
50
|
+
result, shifts, has_shifts = [], [], False
|
|
51
|
+
for index, entry in enumerate(entries):
|
|
52
|
+
location = f'{where}.{key}[{index}]'
|
|
53
|
+
# 文件自己的偏移跟在同一条声明内,展开目录时该偏移作用于其中各文件。
|
|
54
|
+
shift = '0s'
|
|
55
|
+
if type(entry) is dict:
|
|
56
|
+
item = object_at(entry, location, ('path',), ('offset',))
|
|
57
|
+
text = text_at(item['path'], location + '.path')
|
|
58
|
+
if 'offset' in item:
|
|
59
|
+
coordinate_at(item['offset'], location + '.offset')
|
|
60
|
+
shift = item['offset']
|
|
61
|
+
has_shifts = True
|
|
62
|
+
else:
|
|
63
|
+
text = text_at(entry, location)
|
|
64
|
+
target = absolute_path(text, base, location)
|
|
65
|
+
# 仅*和?启动通配符模式,普通文件名中的方括号保持字面含义。
|
|
66
|
+
wildcard = any(char in text for char in '*?')
|
|
67
|
+
# 常规文件不访问磁盘;目录名像文件时可用末尾分隔符明确目录含义。
|
|
68
|
+
if not wildcard and target.suffix.lower() in FILE_SUFFIXES and not text.endswith(('/', '\\')):
|
|
69
|
+
selected = [target]
|
|
70
|
+
else:
|
|
71
|
+
selected = []
|
|
72
|
+
try:
|
|
73
|
+
candidates = (Path(item) for item in iglob(str(target), recursive='**' in text)) if wildcard else target.iterdir()
|
|
74
|
+
for candidate in candidates:
|
|
75
|
+
if candidate.suffix.lower() in allowed and candidate.is_file():
|
|
76
|
+
selected.append(candidate)
|
|
77
|
+
if len(result) + len(selected) > MAX_INPUT_FILES:
|
|
78
|
+
raise PlanValidationError(location, '输入文件超过4096项')
|
|
79
|
+
except OSError as error:
|
|
80
|
+
raise PlanValidationError(location, '无法枚举输入目录:' + str(error)) from error
|
|
81
|
+
if not selected:
|
|
82
|
+
raise PlanValidationError(location, '目录或通配符没有匹配的输入文件')
|
|
83
|
+
selected.sort(key=natural_path_key)
|
|
84
|
+
# 不重排显式列表、不合并不同声明项,也不因内容相同而删除真实文件。
|
|
85
|
+
result.extend(selected)
|
|
86
|
+
shifts.extend([shift] * len(selected))
|
|
87
|
+
if len(result) > MAX_INPUT_FILES:
|
|
88
|
+
raise PlanValidationError(location, '输入文件超过4096项')
|
|
89
|
+
if has_shifts and 'offsets' in raw:
|
|
90
|
+
raise PlanValidationError(where, '文件内offset与来源offsets不能同时填写')
|
|
91
|
+
return tuple(result), tuple(shifts) if has_shifts else None
|
|
92
|
+
|
|
93
|
+
|
|
94
|
+
def expand_input_paths(raw, base, where):
|
|
95
|
+
"""只取展开文件路径,供无需文件偏移的调用方使用。
|
|
96
|
+
|
|
97
|
+
参数: 来源配置、基准目录、错误位置。返回: Path元组。
|
|
98
|
+
异常: 与expand_source_files一致;目录扫描只执行一次。
|
|
99
|
+
"""
|
|
100
|
+
return expand_source_files(raw, base, where)[0]
|
|
101
|
+
|
|
102
|
+
|
|
103
|
+
def source_path_fields(source, where='$.sources'):
|
|
104
|
+
"""枚举文件声明中的路径文字,供转换/导入工具固定路径基准。
|
|
105
|
+
|
|
106
|
+
参数: source为来源字典,where为错误位置。返回: (容器,键)迭代器。
|
|
107
|
+
异常: PlanValidationError为错误结构。不扫描目录,不改变offset或其他元数据。
|
|
108
|
+
"""
|
|
109
|
+
for key in ('path', 'paths'):
|
|
110
|
+
if key not in source:
|
|
111
|
+
continue
|
|
112
|
+
value = source[key]
|
|
113
|
+
if type(value) is str:
|
|
114
|
+
yield source, key
|
|
115
|
+
continue
|
|
116
|
+
# 每项可以是路径文字或带自己偏移的文件声明,工具不能把对象转成字符串。
|
|
117
|
+
entries = [value] if type(value) is dict else array_at(value, where + '.' + key)
|
|
118
|
+
for index, item in enumerate(entries):
|
|
119
|
+
if type(item) is dict:
|
|
120
|
+
object_at(item, f'{where}.{key}[{index}]', ('path',), ('offset',))
|
|
121
|
+
yield item, 'path'
|
|
122
|
+
else:
|
|
123
|
+
text_at(item, f'{where}.{key}[{index}]')
|
|
124
|
+
yield entries, index
|