sysmlpy 0.53.1__tar.gz → 0.55.0__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.
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/PKG-INFO +14 -12
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/README.md +13 -11
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/pyproject.toml +1 -1
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/__init__.py +1 -1
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr_visitor.py +204 -29
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/classes.py +76 -5
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/semantic.py +1635 -4
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/LICENSE +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/__main__.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/README.md +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2Lexer.interp +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2Lexer.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2Lexer.tokens +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2Parser.interp +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2Parser.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2Parser.tokens +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2ParserListener.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/SysMLv2ParserVisitor.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/src/sysmlpy/grammar/antlr4/SysMLv2Lexer.interp +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/src/sysmlpy/grammar/antlr4/SysMLv2Lexer.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr/src/sysmlpy/grammar/antlr4/SysMLv2Lexer.tokens +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/antlr_parser.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/boxes_view.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/definition.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/examples/attribute_values.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/examples/part_attributes.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/examples/tuples_sequences.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/formatting.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/README.md +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Lexer.g4 +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Lexer.interp +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Lexer.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Lexer.tokens +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Parser.g4 +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Parser.interp +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Parser.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2Parser.tokens +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2ParserListener.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/SysMLv2ParserVisitor.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/desc.xml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/examples/camera.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/examples/toaster-system.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/examples/vehicle-model.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/grammar/antlr4/pom.xml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/LICENSE +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/README.md +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/__init__.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Analysis/AnalysisTooling.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Analysis/SampledFunctions.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Analysis/StateSpaceRepresentation.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Analysis/TradeStudies.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Cause and Effect/CausationConnections.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Cause and Effect/CauseAndEffect.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Geometry/ShapeItems.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Geometry/SpatialItems.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Metadata/ImageMetadata.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Metadata/ModelingMetadata.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Metadata/ParametersOfInterestMetadata.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Metadata/RiskMetadata.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQ.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQAcoustics.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQAtomicNuclear.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQBase.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQCharacteristicNumbers.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQChemistryMolecular.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQCondensedMatter.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQElectromagnetism.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQInformation.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQLight.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQMechanics.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQSpaceTime.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/ISQThermodynamics.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/MeasurementRefCalculations.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/MeasurementReferences.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/Quantities.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/QuantityCalculations.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/SI.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/SIPrefixes.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/TensorCalculations.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/Time.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/USCustomaryUnits.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Quantities and Units/VectorCalculations.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Requirement Derivation/DerivationConnections.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/domain/Requirement Derivation/RequirementDerivation.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Base.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/BaseFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/BooleanFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Clocks.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/CollectionFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Collections.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/ComplexFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/ControlFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/ControlPerformances.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/DataFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/FeatureReferencingPerformances.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/IntegerFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/KerML.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Links.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Metaobjects.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/NaturalFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/NumericalFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Objects.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Observation.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/OccurrenceFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Occurrences.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Performances.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/RationalFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/RealFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/ScalarFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/ScalarValues.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/SequenceFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/SpatialFrames.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/StatePerformances.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/StringFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Transfers.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/TransitionPerformances.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/TrigFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/Triggers.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/VectorFunctions.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/kernel/VectorValues.kerml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Actions.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Allocations.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/AnalysisCases.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Attributes.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Calculations.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Cases.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Connections.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Constraints.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Flows.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Interfaces.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Items.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Metadata.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Parts.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Ports.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Requirements.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/StandardViewDefinitions.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/States.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/SysML.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/UseCases.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/VerificationCases.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/library/systems/Views.sysml +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/navigate.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/plantuml.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/project.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/store.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/us_customary_units.txt +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/usage.py +0 -0
- {sysmlpy-0.53.1 → sysmlpy-0.55.0}/src/sysmlpy/validator.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: sysmlpy
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.55.0
|
|
4
4
|
Summary:
|
|
5
5
|
License-File: LICENSE
|
|
6
6
|
Author: Jon R. Fox (mycr0ft)
|
|
@@ -39,19 +39,21 @@ and dropped the textX parser in favor of [an ANTLR4 parser grammar](https://gith
|
|
|
39
39
|
changed our unit library to pint.
|
|
40
40
|
The project had diverged so much from sysml2py that a new name, sysmlpy, was selected.
|
|
41
41
|
|
|
42
|
-
> **⚠️ Constraints are changing.**
|
|
43
|
-
>
|
|
44
|
-
>
|
|
45
|
-
>
|
|
46
|
-
>
|
|
47
|
-
>
|
|
48
|
-
>
|
|
42
|
+
> **⚠️ Constraints are changing.** As of v0.55.0, `analyze()` performs
|
|
43
|
+
> full expression validation: identifiers are **resolved against the
|
|
44
|
+
> symbol table** (v0.54.0) and operators are **type- and
|
|
45
|
+
> unit-checked** — `flag and n`, `"a" + 5`, and `[m] + [kg]` all raise
|
|
46
|
+
> `OPERAND_TYPE_MISMATCH` / `UNIT_DIMENSION_MISMATCH` errors. Deterministic
|
|
47
|
+
> literal expressions can be reduced with `const_fold()`. Coming next
|
|
48
|
+
> (Phase D): parsing performance and graph-store query extensions.
|
|
49
|
+
> Track progress in [docs/DEVELOPMENT_PLAN.md](docs/DEVELOPMENT_PLAN.md).
|
|
49
50
|
|
|
50
51
|
> **Scope reminder** — a green parse result means the file **parsed
|
|
51
|
-
> syntactically**.
|
|
52
|
-
>
|
|
53
|
-
>
|
|
54
|
-
>
|
|
52
|
+
> syntactically**. Expression validation (name resolution, type and
|
|
53
|
+
> unit checks) runs only when you call `analyze(model)` explicitly.
|
|
54
|
+
> Multiplication/division dimension *derivation* (inferring
|
|
55
|
+
> `[N]` from `[kg] * [m/s^2]`) is not yet implemented. See
|
|
56
|
+
> [STATUS.md §Known Issues](STATUS.md#known-issues).
|
|
55
57
|
|
|
56
58
|
For release history, see [CHANGELOG.md](CHANGELOG.md).
|
|
57
59
|
|
|
@@ -14,19 +14,21 @@ and dropped the textX parser in favor of [an ANTLR4 parser grammar](https://gith
|
|
|
14
14
|
changed our unit library to pint.
|
|
15
15
|
The project had diverged so much from sysml2py that a new name, sysmlpy, was selected.
|
|
16
16
|
|
|
17
|
-
> **⚠️ Constraints are changing.**
|
|
18
|
-
>
|
|
19
|
-
>
|
|
20
|
-
>
|
|
21
|
-
>
|
|
22
|
-
>
|
|
23
|
-
>
|
|
17
|
+
> **⚠️ Constraints are changing.** As of v0.55.0, `analyze()` performs
|
|
18
|
+
> full expression validation: identifiers are **resolved against the
|
|
19
|
+
> symbol table** (v0.54.0) and operators are **type- and
|
|
20
|
+
> unit-checked** — `flag and n`, `"a" + 5`, and `[m] + [kg]` all raise
|
|
21
|
+
> `OPERAND_TYPE_MISMATCH` / `UNIT_DIMENSION_MISMATCH` errors. Deterministic
|
|
22
|
+
> literal expressions can be reduced with `const_fold()`. Coming next
|
|
23
|
+
> (Phase D): parsing performance and graph-store query extensions.
|
|
24
|
+
> Track progress in [docs/DEVELOPMENT_PLAN.md](docs/DEVELOPMENT_PLAN.md).
|
|
24
25
|
|
|
25
26
|
> **Scope reminder** — a green parse result means the file **parsed
|
|
26
|
-
> syntactically**.
|
|
27
|
-
>
|
|
28
|
-
>
|
|
29
|
-
>
|
|
27
|
+
> syntactically**. Expression validation (name resolution, type and
|
|
28
|
+
> unit checks) runs only when you call `analyze(model)` explicitly.
|
|
29
|
+
> Multiplication/division dimension *derivation* (inferring
|
|
30
|
+
> `[N]` from `[kg] * [m/s^2]`) is not yet implemented. See
|
|
31
|
+
> [STATUS.md §Known Issues](STATUS.md#known-issues).
|
|
30
32
|
|
|
31
33
|
For release history, see [CHANGELOG.md](CHANGELOG.md).
|
|
32
34
|
|
|
@@ -25,7 +25,7 @@ __all__ = [
|
|
|
25
25
|
"render_state_transition_view_svg", "boxes_view",
|
|
26
26
|
]
|
|
27
27
|
__author__ = "Jon Fox"
|
|
28
|
-
__version__ = "0.
|
|
28
|
+
__version__ = "0.55.0"
|
|
29
29
|
|
|
30
30
|
from sysmlpy.usage import (
|
|
31
31
|
Item, Attribute, Part, Port, Action, Reference, UseCase, Requirement, Interface, Message,
|
|
@@ -11134,45 +11134,109 @@ def _emit_null_coalescing_level(ctx):
|
|
|
11134
11134
|
|
|
11135
11135
|
def _emit_implies_level(ctx):
|
|
11136
11136
|
# orExpression ( IMPLIES orExpression )*
|
|
11137
|
+
# Operator text 'implies' goes into the ImpliesExpression
|
|
11138
|
+
# operator/operand lists (rendered by ImpliesExpression.dump since
|
|
11139
|
+
# v0.55.0).
|
|
11137
11140
|
first, pairs = _split_level_ctx(ctx, "OrExpressionContext")
|
|
11138
|
-
if pairs:
|
|
11139
|
-
return None # 'implies' not dumped by the grammar class -> text
|
|
11140
11141
|
or_expr = _emit_or_level(first)
|
|
11141
11142
|
if or_expr is None:
|
|
11142
11143
|
return None
|
|
11143
|
-
|
|
11144
|
+
ops = []
|
|
11145
|
+
operands = []
|
|
11146
|
+
for op_text, or_ctx in pairs:
|
|
11147
|
+
or_dict = _emit_or_level(or_ctx)
|
|
11148
|
+
if or_dict is None:
|
|
11149
|
+
return None
|
|
11150
|
+
ops.append(op_text)
|
|
11151
|
+
operands.append(or_dict)
|
|
11152
|
+
return {
|
|
11153
|
+
"name": "ImpliesExpression",
|
|
11154
|
+
"operator": ops,
|
|
11155
|
+
"operand": operands,
|
|
11156
|
+
"or": or_expr,
|
|
11157
|
+
}
|
|
11144
11158
|
|
|
11145
11159
|
|
|
11146
11160
|
def _emit_or_level(ctx):
|
|
11147
11161
|
# xorExpression ( ( OR | PIPE ) xorExpression )*
|
|
11162
|
+
# Operator text 'or' or '|' goes into the OrExpression operator/operand
|
|
11163
|
+
# lists (rendered by OrExpression.dump since v0.55.0).
|
|
11148
11164
|
first, pairs = _split_level_ctx(ctx, "XorExpressionContext")
|
|
11149
|
-
if pairs:
|
|
11150
|
-
return None # 'or'/'|' not dumped by the grammar class -> text
|
|
11151
11165
|
xor_expr = _emit_xor_level(first)
|
|
11152
11166
|
if xor_expr is None:
|
|
11153
11167
|
return None
|
|
11154
|
-
|
|
11168
|
+
ops = []
|
|
11169
|
+
operands = []
|
|
11170
|
+
for op_text, xor_ctx in pairs:
|
|
11171
|
+
xor_dict = _emit_xor_level(xor_ctx)
|
|
11172
|
+
if xor_dict is None:
|
|
11173
|
+
return None
|
|
11174
|
+
ops.append(op_text)
|
|
11175
|
+
operands.append(xor_dict)
|
|
11176
|
+
return {
|
|
11177
|
+
"name": "OrExpression",
|
|
11178
|
+
"operator": ops,
|
|
11179
|
+
"operand": operands,
|
|
11180
|
+
"xor": xor_expr,
|
|
11181
|
+
}
|
|
11155
11182
|
|
|
11156
11183
|
|
|
11157
11184
|
def _emit_xor_level(ctx):
|
|
11158
11185
|
# andExpression ( XOR andExpression )*
|
|
11159
11186
|
first, pairs = _split_level_ctx(ctx, "AndExpressionContext")
|
|
11160
|
-
if pairs:
|
|
11161
|
-
return None # 'xor' not dumped by the grammar class -> text
|
|
11162
11187
|
and_expr = _emit_and_level(first)
|
|
11163
11188
|
if and_expr is None:
|
|
11164
11189
|
return None
|
|
11165
|
-
|
|
11190
|
+
ops = []
|
|
11191
|
+
operands = []
|
|
11192
|
+
for op_text, and_ctx in pairs:
|
|
11193
|
+
and_dict = _emit_and_level(and_ctx)
|
|
11194
|
+
if and_dict is None:
|
|
11195
|
+
return None
|
|
11196
|
+
ops.append(op_text)
|
|
11197
|
+
operands.append(and_dict)
|
|
11198
|
+
return {
|
|
11199
|
+
"name": "XorExpression",
|
|
11200
|
+
"operator": ops,
|
|
11201
|
+
"operand": operands,
|
|
11202
|
+
"and": and_expr,
|
|
11203
|
+
}
|
|
11166
11204
|
|
|
11167
11205
|
|
|
11168
11206
|
def _emit_and_level(ctx):
|
|
11169
11207
|
# equalityExpression ( ( AND | AMP ) equalityExpression )*
|
|
11208
|
+
# The 'and' keyword form takes an EqualityExpressionReference (a
|
|
11209
|
+
# membership wrapper) per the XText reference grammar; '&' keeps a
|
|
11210
|
+
# direct EqualityExpression operand.
|
|
11170
11211
|
first, pairs = _split_level_ctx(ctx, "EqualityExpressionContext")
|
|
11171
|
-
if pairs:
|
|
11172
|
-
return None # 'and'/'&' not dumped by the grammar class -> text
|
|
11173
11212
|
eq = _emit_equality_level(first)
|
|
11174
11213
|
if eq is None:
|
|
11175
11214
|
return None
|
|
11215
|
+
ops = []
|
|
11216
|
+
for op_text, cls_ctx in pairs:
|
|
11217
|
+
cls_dict = _emit_equality_level(cls_ctx)
|
|
11218
|
+
if cls_dict is None:
|
|
11219
|
+
return None
|
|
11220
|
+
if op_text == "&":
|
|
11221
|
+
ops.append(
|
|
11222
|
+
{"name": "AndOperand", "operator": "&", "operand": cls_dict}
|
|
11223
|
+
)
|
|
11224
|
+
else:
|
|
11225
|
+
ops.append(
|
|
11226
|
+
{
|
|
11227
|
+
"name": "AndOperand",
|
|
11228
|
+
"operator": "and",
|
|
11229
|
+
"operand": {
|
|
11230
|
+
"name": "EqualityExpressionReference",
|
|
11231
|
+
"ownedRelationship": {
|
|
11232
|
+
"name": "EqualityExpressionMember",
|
|
11233
|
+
"ownedRelatedElement": cls_dict,
|
|
11234
|
+
},
|
|
11235
|
+
},
|
|
11236
|
+
}
|
|
11237
|
+
)
|
|
11238
|
+
if ops:
|
|
11239
|
+
return {"name": "AndExpression", "operation": ops, "equality": eq}
|
|
11176
11240
|
return {"name": "AndExpression", "operation": [], "equality": eq}
|
|
11177
11241
|
|
|
11178
11242
|
|
|
@@ -11292,10 +11356,29 @@ def _emit_multiplicative_level(ctx):
|
|
|
11292
11356
|
|
|
11293
11357
|
def _emit_exponentiation_level(ctx):
|
|
11294
11358
|
# unaryExpression ( ( STAR_STAR | CARET ) exponentiationExpression )?
|
|
11295
|
-
# '**'/'^' are right-associative
|
|
11296
|
-
#
|
|
11359
|
+
# '**'/'^' are right-associative; the rhs of '**' is another
|
|
11360
|
+
# ExponentiationExpression (child layer of the same rule).
|
|
11297
11361
|
if hasattr(ctx, "exponentiationExpression") and ctx.exponentiationExpression():
|
|
11298
|
-
|
|
11362
|
+
rhs_ctx = ctx.exponentiationExpression()
|
|
11363
|
+
unary_ctx = ctx.unaryExpression() if hasattr(ctx, "unaryExpression") else None
|
|
11364
|
+
if unary_ctx is None:
|
|
11365
|
+
return None
|
|
11366
|
+
unary = _emit_unary_level(unary_ctx)
|
|
11367
|
+
if unary is None:
|
|
11368
|
+
return None
|
|
11369
|
+
rhs_dict = _emit_exponentiation_level(rhs_ctx)
|
|
11370
|
+
if rhs_dict is None:
|
|
11371
|
+
return None
|
|
11372
|
+
op_text = "**"
|
|
11373
|
+
for c in (ctx.getChildren() if hasattr(ctx, "getChildren") else []):
|
|
11374
|
+
if type(c).__name__ == "TerminalNodeImpl" and c.getText().strip() in ("**", "^"):
|
|
11375
|
+
op_text = c.getText().strip()
|
|
11376
|
+
return {
|
|
11377
|
+
"name": "ExponentiationExpression",
|
|
11378
|
+
"operator": [op_text],
|
|
11379
|
+
"operand": [rhs_dict],
|
|
11380
|
+
"unary": unary,
|
|
11381
|
+
}
|
|
11299
11382
|
unary_ctx = ctx.unaryExpression() if hasattr(ctx, "unaryExpression") else None
|
|
11300
11383
|
if unary_ctx is None:
|
|
11301
11384
|
return None
|
|
@@ -11312,6 +11395,41 @@ def _emit_unary_level(ctx):
|
|
|
11312
11395
|
# | primaryExpression
|
|
11313
11396
|
prim_ctx = ctx.primaryExpression() if hasattr(ctx, "primaryExpression") else None
|
|
11314
11397
|
if prim_ctx is not None:
|
|
11398
|
+
# Parenthesized primary: baseExpression '(' sequenceExpression ')'
|
|
11399
|
+
# carries a full inner binary chain — recurse through the inner
|
|
11400
|
+
# nullCoalescing level so nested binary ops stay structured.
|
|
11401
|
+
be_ctx = prim_ctx.baseExpression() if hasattr(prim_ctx, "baseExpression") else None
|
|
11402
|
+
if be_ctx is not None and "(" in getattr(be_ctx, "text", "") or (
|
|
11403
|
+
be_ctx is not None and be_ctx.getText().startswith("(")
|
|
11404
|
+
):
|
|
11405
|
+
inner_nce = None
|
|
11406
|
+
sel = (
|
|
11407
|
+
be_ctx.sequenceExpressionList()
|
|
11408
|
+
if hasattr(be_ctx, "sequenceExpressionList")
|
|
11409
|
+
else None
|
|
11410
|
+
)
|
|
11411
|
+
if sel is not None:
|
|
11412
|
+
oe = (
|
|
11413
|
+
sel.ownedExpression()
|
|
11414
|
+
if hasattr(sel, "ownedExpression")
|
|
11415
|
+
else None
|
|
11416
|
+
)
|
|
11417
|
+
# A comma-separated sequence (a, b) is not representable
|
|
11418
|
+
# in the paren-structured shape — let it fall back to text.
|
|
11419
|
+
if isinstance(oe, list) and len(oe) != 1:
|
|
11420
|
+
return None
|
|
11421
|
+
while isinstance(oe, list):
|
|
11422
|
+
oe = oe[0] if oe else None
|
|
11423
|
+
nce = (
|
|
11424
|
+
oe.nullCoalescingExpression()
|
|
11425
|
+
if oe is not None and hasattr(oe, "nullCoalescingExpression")
|
|
11426
|
+
else None
|
|
11427
|
+
)
|
|
11428
|
+
if isinstance(nce, list):
|
|
11429
|
+
nce = nce[0] if nce else None
|
|
11430
|
+
if nce is not None:
|
|
11431
|
+
inner_nce = _emit_null_coalescing_level(nce)
|
|
11432
|
+
return None # parens carry grouping — text fallback preserves them
|
|
11315
11433
|
primary = _emit_primary_level(prim_ctx)
|
|
11316
11434
|
if primary is None:
|
|
11317
11435
|
return None
|
|
@@ -11330,9 +11448,9 @@ def _emit_unary_level(ctx):
|
|
|
11330
11448
|
if children and type(children[0]).__name__ == "TerminalNodeImpl":
|
|
11331
11449
|
op_text = children[0].getText().strip()
|
|
11332
11450
|
if op_text in ("+", "-", "~", "not"):
|
|
11333
|
-
# operand must be a unaryExpression
|
|
11334
|
-
#
|
|
11335
|
-
#
|
|
11451
|
+
# operand must be a unaryExpression; nested unary prefixes are
|
|
11452
|
+
# not representable in the chain shape, but a plain
|
|
11453
|
+
# primaryExpression (possibly parenthesized additive) is.
|
|
11336
11454
|
operand_ctx = None
|
|
11337
11455
|
for c in children[1:]:
|
|
11338
11456
|
if type(c).__name__ == "UnaryExpressionContext":
|
|
@@ -11345,25 +11463,64 @@ def _emit_unary_level(ctx):
|
|
|
11345
11463
|
if hasattr(operand_ctx, "primaryExpression")
|
|
11346
11464
|
else None
|
|
11347
11465
|
)
|
|
11348
|
-
if
|
|
11466
|
+
if (
|
|
11467
|
+
inner_prim is not None
|
|
11468
|
+
and "(" not in getattr(operand_ctx, "text", "")
|
|
11469
|
+
):
|
|
11470
|
+
primary = _emit_primary_level(inner_prim)
|
|
11471
|
+
if primary is not None:
|
|
11472
|
+
return {
|
|
11473
|
+
"name": "UnaryExpression",
|
|
11474
|
+
"operator": op_text,
|
|
11475
|
+
"operand": [],
|
|
11476
|
+
"extent": {
|
|
11477
|
+
"name": "ExtentExpression",
|
|
11478
|
+
"operator": "",
|
|
11479
|
+
"operand": [],
|
|
11480
|
+
"primary": primary,
|
|
11481
|
+
},
|
|
11482
|
+
}
|
|
11483
|
+
# Parenthesized operand: primary is '(' sequenceExpression ')'
|
|
11484
|
+
# whose additive/multiplicative chain is representable — emit
|
|
11485
|
+
# the inner chain as a nested UnaryExpression extent.
|
|
11486
|
+
inner = _emit_unary_level(operand_ctx)
|
|
11487
|
+
if inner is not None and not isinstance(inner.get("extent"), dict):
|
|
11349
11488
|
return None
|
|
11350
|
-
primary
|
|
11351
|
-
|
|
11489
|
+
# inner may be a primary-only unary; wrap so the outer '-'
|
|
11490
|
+
# sits above the inner (parenthesized) chain
|
|
11491
|
+
if inner is None:
|
|
11352
11492
|
return None
|
|
11353
11493
|
return {
|
|
11354
11494
|
"name": "UnaryExpression",
|
|
11355
11495
|
"operator": op_text,
|
|
11356
11496
|
"operand": [],
|
|
11357
|
-
"extent":
|
|
11358
|
-
"name": "ExtentExpression",
|
|
11359
|
-
"operator": "",
|
|
11360
|
-
"operand": [],
|
|
11361
|
-
"primary": primary,
|
|
11362
|
-
},
|
|
11497
|
+
"extent": inner.get("extent"),
|
|
11363
11498
|
}
|
|
11364
11499
|
return None # '@'/'@@'/'all' typeReference forms -> text
|
|
11365
11500
|
|
|
11366
11501
|
|
|
11502
|
+
def _chain_has_binary_operator(node):
|
|
11503
|
+
"""True if an expression-layer dict contains any emitted binary operator."""
|
|
11504
|
+
if not isinstance(node, dict):
|
|
11505
|
+
return False
|
|
11506
|
+
for key in ("operation", "operator", "operand"):
|
|
11507
|
+
val = node.get(key)
|
|
11508
|
+
if key == "operation" and isinstance(val, list) and val:
|
|
11509
|
+
return True
|
|
11510
|
+
if key == "operator":
|
|
11511
|
+
if isinstance(val, str) and val not in (None, "") and node.get("name") != "ExponentiationExpression" or isinstance(val, list) and val:
|
|
11512
|
+
return True
|
|
11513
|
+
if key == "operand" and isinstance(val, list) and val and node.get("name") == "ExponentiationExpression":
|
|
11514
|
+
return True
|
|
11515
|
+
for child_key in ("implies", "or", "xor", "and", "equality", "classification",
|
|
11516
|
+
"relational", "range", "additive", "multiplicitive",
|
|
11517
|
+
"exponential", "unary", "extent", "primary"):
|
|
11518
|
+
child = node.get(child_key)
|
|
11519
|
+
if isinstance(child, dict) and _chain_has_binary_operator(child):
|
|
11520
|
+
return True
|
|
11521
|
+
return False
|
|
11522
|
+
|
|
11523
|
+
|
|
11367
11524
|
def _base_feature_names(be_ctx):
|
|
11368
11525
|
"""Return the qualified-name parts of a baseExpression that is a
|
|
11369
11526
|
plain feature reference, or None for any other base form."""
|
|
@@ -11479,9 +11636,27 @@ def _emit_base_primary(be_ctx):
|
|
|
11479
11636
|
pass
|
|
11480
11637
|
if lit_text.startswith('"') and lit_text.endswith('"'):
|
|
11481
11638
|
return _make_literal_string_primary(lit_text)
|
|
11482
|
-
#
|
|
11483
|
-
#
|
|
11484
|
-
|
|
11639
|
+
# Boolean literal: captured as a LiteralBoolean primary so the
|
|
11640
|
+
# type checker can classify it; the grammar class round-trips
|
|
11641
|
+
# the keyword text via the value field.
|
|
11642
|
+
if lit_text in ("true", "false"):
|
|
11643
|
+
return {
|
|
11644
|
+
"name": "PrimaryExpression",
|
|
11645
|
+
"operator": [],
|
|
11646
|
+
"operand": [],
|
|
11647
|
+
"base": {
|
|
11648
|
+
"name": "BaseExpression",
|
|
11649
|
+
"ownedRelationship": {
|
|
11650
|
+
"name": "LiteralBoolean",
|
|
11651
|
+
"value": lit_text,
|
|
11652
|
+
},
|
|
11653
|
+
},
|
|
11654
|
+
"ownedRelationship1": [],
|
|
11655
|
+
"ownedRelationship2": [],
|
|
11656
|
+
}
|
|
11657
|
+
# null has no dedicated grammar class; keep it as a feature
|
|
11658
|
+
# reference so the text round-trips
|
|
11659
|
+
if lit_text == "null":
|
|
11485
11660
|
return _make_feature_reference_primary(lit_text)
|
|
11486
11661
|
return None
|
|
11487
11662
|
names = _base_feature_names(be_ctx)
|
|
@@ -5754,6 +5754,18 @@ class ImpliesExpression:
|
|
|
5754
5754
|
self.operator = definition.get("operator", [])
|
|
5755
5755
|
|
|
5756
5756
|
def dump(self):
|
|
5757
|
+
if self.orexpression is not None and self.operator and self.operand:
|
|
5758
|
+
output = [self.orexpression.dump()]
|
|
5759
|
+
for op, rhs in zip(self.operator, self.operand):
|
|
5760
|
+
output.append(op)
|
|
5761
|
+
if isinstance(rhs, dict):
|
|
5762
|
+
try:
|
|
5763
|
+
output.append(OrExpression(rhs).dump())
|
|
5764
|
+
except Exception:
|
|
5765
|
+
output.append(str(rhs))
|
|
5766
|
+
else:
|
|
5767
|
+
output.append(str(rhs))
|
|
5768
|
+
return " ".join(output)
|
|
5757
5769
|
if self.orexpression is not None:
|
|
5758
5770
|
return self.orexpression.dump()
|
|
5759
5771
|
return ""
|
|
@@ -5781,6 +5793,18 @@ class OrExpression:
|
|
|
5781
5793
|
self.operator = definition.get("operator", [])
|
|
5782
5794
|
|
|
5783
5795
|
def dump(self):
|
|
5796
|
+
if self.xor is not None and self.operator and self.operand:
|
|
5797
|
+
output = [self.xor.dump()]
|
|
5798
|
+
for op, rhs in zip(self.operator, self.operand):
|
|
5799
|
+
output.append(op)
|
|
5800
|
+
if isinstance(rhs, dict):
|
|
5801
|
+
try:
|
|
5802
|
+
output.append(XorExpression(rhs).dump())
|
|
5803
|
+
except Exception:
|
|
5804
|
+
output.append(str(rhs))
|
|
5805
|
+
else:
|
|
5806
|
+
output.append(str(rhs))
|
|
5807
|
+
return " ".join(output)
|
|
5784
5808
|
if self.xor is not None:
|
|
5785
5809
|
return self.xor.dump()
|
|
5786
5810
|
return ""
|
|
@@ -5808,13 +5832,27 @@ class XorExpression:
|
|
|
5808
5832
|
self.operator = definition.get("operator", [])
|
|
5809
5833
|
|
|
5810
5834
|
def dump(self):
|
|
5811
|
-
|
|
5835
|
+
if self.andexpression is not None and self.operator and self.operand:
|
|
5836
|
+
output = [self.andexpression.dump()]
|
|
5837
|
+
for op, rhs in zip(self.operator, self.operand):
|
|
5838
|
+
output.append(op)
|
|
5839
|
+
if isinstance(rhs, dict):
|
|
5840
|
+
try:
|
|
5841
|
+
output.append(AndExpression(rhs).dump())
|
|
5842
|
+
except Exception:
|
|
5843
|
+
output.append(str(rhs))
|
|
5844
|
+
else:
|
|
5845
|
+
output.append(str(rhs))
|
|
5846
|
+
return " ".join(output)
|
|
5847
|
+
if self.andexpression is not None:
|
|
5848
|
+
return self.andexpression.dump()
|
|
5849
|
+
return ""
|
|
5812
5850
|
|
|
5813
5851
|
def get_definition(self):
|
|
5814
5852
|
output = {
|
|
5815
5853
|
"name": self.__class__.__name__,
|
|
5816
|
-
"operator":
|
|
5817
|
-
"operand":
|
|
5854
|
+
"operator": self.operator,
|
|
5855
|
+
"operand": self.operand,
|
|
5818
5856
|
"and": self.andexpression.get_definition(),
|
|
5819
5857
|
}
|
|
5820
5858
|
return output
|
|
@@ -6149,6 +6187,18 @@ class ExponentiationExpression:
|
|
|
6149
6187
|
self.operator = definition.get("operator", [])
|
|
6150
6188
|
|
|
6151
6189
|
def dump(self):
|
|
6190
|
+
if self.unary is not None and self.operator and self.operand:
|
|
6191
|
+
output = [self.unary.dump()]
|
|
6192
|
+
for op, rhs in zip(self.operator, self.operand):
|
|
6193
|
+
output.append(op)
|
|
6194
|
+
if isinstance(rhs, dict):
|
|
6195
|
+
try:
|
|
6196
|
+
output.append(ExponentiationExpression(rhs).dump())
|
|
6197
|
+
except Exception:
|
|
6198
|
+
output.append(str(rhs))
|
|
6199
|
+
else:
|
|
6200
|
+
output.append(str(rhs))
|
|
6201
|
+
return " ".join(output)
|
|
6152
6202
|
if self.unary is not None:
|
|
6153
6203
|
return self.unary.dump()
|
|
6154
6204
|
return ""
|
|
@@ -6200,15 +6250,21 @@ class UnaryExpression:
|
|
|
6200
6250
|
class ExtentExpression:
|
|
6201
6251
|
def __init__(self, definition):
|
|
6202
6252
|
self.primary = None
|
|
6253
|
+
self.nested = None
|
|
6203
6254
|
self.operator = ""
|
|
6204
6255
|
if valid_definition(definition, self.__class__.__name__):
|
|
6205
|
-
if definition
|
|
6256
|
+
if definition.get("primary") is not None:
|
|
6206
6257
|
self.primary = PrimaryExpression(definition["primary"])
|
|
6258
|
+
nested = definition.get("ownedRelationship")
|
|
6259
|
+
if isinstance(nested, dict):
|
|
6260
|
+
self.nested = globals()[nested["name"]](nested)
|
|
6207
6261
|
self.operator = definition.get("operator", "")
|
|
6208
6262
|
|
|
6209
6263
|
def dump(self):
|
|
6210
6264
|
if self.primary is not None:
|
|
6211
6265
|
return self.primary.dump()
|
|
6266
|
+
if self.nested is not None:
|
|
6267
|
+
return self.nested.dump()
|
|
6212
6268
|
return ""
|
|
6213
6269
|
|
|
6214
6270
|
def get_definition(self):
|
|
@@ -6219,7 +6275,8 @@ class ExtentExpression:
|
|
|
6219
6275
|
}
|
|
6220
6276
|
if self.primary is not None:
|
|
6221
6277
|
output["primary"] = self.primary.get_definition()
|
|
6222
|
-
|
|
6278
|
+
if self.nested is not None:
|
|
6279
|
+
output["ownedRelationship"] = self.nested.get_definition()
|
|
6223
6280
|
return output
|
|
6224
6281
|
|
|
6225
6282
|
|
|
@@ -6455,6 +6512,8 @@ class BaseExpression:
|
|
|
6455
6512
|
self.relationship = LiteralString(definition["ownedRelationship"])
|
|
6456
6513
|
elif definition["ownedRelationship"]["name"] == "LiteralReal":
|
|
6457
6514
|
self.relationship = LiteralReal(definition["ownedRelationship"])
|
|
6515
|
+
elif definition["ownedRelationship"]["name"] == "LiteralBoolean":
|
|
6516
|
+
self.relationship = LiteralBoolean(definition["ownedRelationship"])
|
|
6458
6517
|
elif definition["ownedRelationship"]["name"] == "SequenceExpression":
|
|
6459
6518
|
self.relationship = SequenceExpression(definition["ownedRelationship"])
|
|
6460
6519
|
elif definition["ownedRelationship"]["name"] == "InvocationExpression":
|
|
@@ -8437,6 +8496,18 @@ class LiteralString:
|
|
|
8437
8496
|
return {"name": self.__class__.__name__, "value": self.element}
|
|
8438
8497
|
|
|
8439
8498
|
|
|
8499
|
+
class LiteralBoolean:
|
|
8500
|
+
def __init__(self, definition):
|
|
8501
|
+
if valid_definition(definition, self.__class__.__name__):
|
|
8502
|
+
self.element = definition["value"]
|
|
8503
|
+
|
|
8504
|
+
def dump(self):
|
|
8505
|
+
return self.element
|
|
8506
|
+
|
|
8507
|
+
def get_definition(self):
|
|
8508
|
+
return {"name": self.__class__.__name__, "value": self.element}
|
|
8509
|
+
|
|
8510
|
+
|
|
8440
8511
|
class LiteralInteger:
|
|
8441
8512
|
def __init__(self, definition):
|
|
8442
8513
|
if valid_definition(definition, "LiteralInteger"):
|