aas-core-codegen 0.0.16__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.
Files changed (604) hide show
  1. aas_core_codegen/__init__.py +6 -0
  2. aas_core_codegen/__main__.py +8 -0
  3. aas_core_codegen/common.py +500 -0
  4. aas_core_codegen/cpp/__init__.py +1 -0
  5. aas_core_codegen/cpp/aas_common/__init__.py +6 -0
  6. aas_core_codegen/cpp/aas_common/_generate.py +713 -0
  7. aas_core_codegen/cpp/common.py +681 -0
  8. aas_core_codegen/cpp/constants/__init__.py +6 -0
  9. aas_core_codegen/cpp/constants/_generate.py +568 -0
  10. aas_core_codegen/cpp/description.py +654 -0
  11. aas_core_codegen/cpp/enhancing/__init__.py +4 -0
  12. aas_core_codegen/cpp/enhancing/_generate.py +993 -0
  13. aas_core_codegen/cpp/iteration/__init__.py +6 -0
  14. aas_core_codegen/cpp/iteration/_generate.py +2332 -0
  15. aas_core_codegen/cpp/jsonization/__init__.py +6 -0
  16. aas_core_codegen/cpp/jsonization/_generate.py +2619 -0
  17. aas_core_codegen/cpp/main.py +694 -0
  18. aas_core_codegen/cpp/naming.py +170 -0
  19. aas_core_codegen/cpp/optionaling.py +557 -0
  20. aas_core_codegen/cpp/pattern/__init__.py +6 -0
  21. aas_core_codegen/cpp/pattern/_generate.py +508 -0
  22. aas_core_codegen/cpp/revm/__init__.py +6 -0
  23. aas_core_codegen/cpp/revm/_generate.py +1149 -0
  24. aas_core_codegen/cpp/stringification/__init__.py +5 -0
  25. aas_core_codegen/cpp/stringification/_generate.py +955 -0
  26. aas_core_codegen/cpp/structure/__init__.py +7 -0
  27. aas_core_codegen/cpp/structure/_generate.py +1503 -0
  28. aas_core_codegen/cpp/transpilation.py +1383 -0
  29. aas_core_codegen/cpp/unrolling.py +159 -0
  30. aas_core_codegen/cpp/verification/__init__.py +6 -0
  31. aas_core_codegen/cpp/verification/_generate.py +3073 -0
  32. aas_core_codegen/cpp/visitation/__init__.py +6 -0
  33. aas_core_codegen/cpp/visitation/_generate.py +521 -0
  34. aas_core_codegen/cpp/wstringification/__init__.py +5 -0
  35. aas_core_codegen/cpp/wstringification/_generate.py +586 -0
  36. aas_core_codegen/cpp/xmlization/__init__.py +6 -0
  37. aas_core_codegen/cpp/xmlization/_generate.py +5373 -0
  38. aas_core_codegen/cpp/yielding.py +201 -0
  39. aas_core_codegen/csharp/__init__.py +1 -0
  40. aas_core_codegen/csharp/common.py +224 -0
  41. aas_core_codegen/csharp/constants/__init__.py +5 -0
  42. aas_core_codegen/csharp/constants/_generate.py +409 -0
  43. aas_core_codegen/csharp/copying/__init__.py +4 -0
  44. aas_core_codegen/csharp/copying/_generate.py +498 -0
  45. aas_core_codegen/csharp/description.py +1103 -0
  46. aas_core_codegen/csharp/enhancing/__init__.py +4 -0
  47. aas_core_codegen/csharp/enhancing/_generate.py +667 -0
  48. aas_core_codegen/csharp/jsonization/__init__.py +4 -0
  49. aas_core_codegen/csharp/jsonization/_generate.py +1630 -0
  50. aas_core_codegen/csharp/main.py +421 -0
  51. aas_core_codegen/csharp/naming.py +157 -0
  52. aas_core_codegen/csharp/reporting/__init__.py +4 -0
  53. aas_core_codegen/csharp/reporting/_generate.py +266 -0
  54. aas_core_codegen/csharp/stringification/__init__.py +4 -0
  55. aas_core_codegen/csharp/stringification/_generate.py +243 -0
  56. aas_core_codegen/csharp/structure/__init__.py +6 -0
  57. aas_core_codegen/csharp/structure/_generate.py +1341 -0
  58. aas_core_codegen/csharp/transpilation.py +990 -0
  59. aas_core_codegen/csharp/unrolling.py +211 -0
  60. aas_core_codegen/csharp/verification/__init__.py +6 -0
  61. aas_core_codegen/csharp/verification/_generate.py +1457 -0
  62. aas_core_codegen/csharp/visitation/__init__.py +5 -0
  63. aas_core_codegen/csharp/visitation/_generate.py +579 -0
  64. aas_core_codegen/csharp/xmlization/__init__.py +4 -0
  65. aas_core_codegen/csharp/xmlization/_generate.py +1980 -0
  66. aas_core_codegen/golang/__init__.py +1 -0
  67. aas_core_codegen/golang/aas_common/__init__.py +4 -0
  68. aas_core_codegen/golang/aas_common/_generate.py +152 -0
  69. aas_core_codegen/golang/common.py +303 -0
  70. aas_core_codegen/golang/constants/__init__.py +5 -0
  71. aas_core_codegen/golang/constants/_generate.py +339 -0
  72. aas_core_codegen/golang/description.py +501 -0
  73. aas_core_codegen/golang/enhancing/__init__.py +4 -0
  74. aas_core_codegen/golang/enhancing/_generate.py +527 -0
  75. aas_core_codegen/golang/jsonization/__init__.py +4 -0
  76. aas_core_codegen/golang/jsonization/_generate.py +1740 -0
  77. aas_core_codegen/golang/main.py +368 -0
  78. aas_core_codegen/golang/naming.py +412 -0
  79. aas_core_codegen/golang/pointering.py +631 -0
  80. aas_core_codegen/golang/reporting/__init__.py +4 -0
  81. aas_core_codegen/golang/reporting/_generate.py +218 -0
  82. aas_core_codegen/golang/stringification/__init__.py +4 -0
  83. aas_core_codegen/golang/stringification/_generate.py +394 -0
  84. aas_core_codegen/golang/structure/__init__.py +6 -0
  85. aas_core_codegen/golang/structure/_generate.py +1493 -0
  86. aas_core_codegen/golang/transpilation.py +1191 -0
  87. aas_core_codegen/golang/unrolling.py +159 -0
  88. aas_core_codegen/golang/verification/__init__.py +6 -0
  89. aas_core_codegen/golang/verification/_generate.py +1513 -0
  90. aas_core_codegen/golang/xmlization/__init__.py +4 -0
  91. aas_core_codegen/golang/xmlization/_generate.py +2507 -0
  92. aas_core_codegen/infer_for_schema/__init__.py +21 -0
  93. aas_core_codegen/infer_for_schema/_inline.py +693 -0
  94. aas_core_codegen/infer_for_schema/_len.py +527 -0
  95. aas_core_codegen/infer_for_schema/_pattern.py +311 -0
  96. aas_core_codegen/infer_for_schema/_set.py +394 -0
  97. aas_core_codegen/infer_for_schema/_stringify.py +201 -0
  98. aas_core_codegen/infer_for_schema/_types.py +135 -0
  99. aas_core_codegen/infer_for_schema/match.py +122 -0
  100. aas_core_codegen/intermediate/__init__.py +78 -0
  101. aas_core_codegen/intermediate/_hierarchy.py +397 -0
  102. aas_core_codegen/intermediate/_stringify.py +989 -0
  103. aas_core_codegen/intermediate/_translate.py +5128 -0
  104. aas_core_codegen/intermediate/_types.py +2901 -0
  105. aas_core_codegen/intermediate/construction.py +750 -0
  106. aas_core_codegen/intermediate/doc.py +344 -0
  107. aas_core_codegen/intermediate/pattern_verification.py +428 -0
  108. aas_core_codegen/intermediate/revm.py +985 -0
  109. aas_core_codegen/intermediate/type_inference.py +2266 -0
  110. aas_core_codegen/java/__init__.py +1 -0
  111. aas_core_codegen/java/common.py +197 -0
  112. aas_core_codegen/java/constants/__init__.py +5 -0
  113. aas_core_codegen/java/constants/_generate.py +334 -0
  114. aas_core_codegen/java/copying/__init__.py +4 -0
  115. aas_core_codegen/java/copying/_generate.py +502 -0
  116. aas_core_codegen/java/description.py +774 -0
  117. aas_core_codegen/java/enhancing/__init__.py +4 -0
  118. aas_core_codegen/java/enhancing/_generate.py +820 -0
  119. aas_core_codegen/java/generation/__init__.py +5 -0
  120. aas_core_codegen/java/generation/_generate.py +285 -0
  121. aas_core_codegen/java/jsonization/__init__.py +4 -0
  122. aas_core_codegen/java/jsonization/_generate.py +1472 -0
  123. aas_core_codegen/java/main.py +438 -0
  124. aas_core_codegen/java/naming.py +187 -0
  125. aas_core_codegen/java/optional.py +514 -0
  126. aas_core_codegen/java/reporting/__init__.py +4 -0
  127. aas_core_codegen/java/reporting/_generate.py +248 -0
  128. aas_core_codegen/java/stringification/__init__.py +4 -0
  129. aas_core_codegen/java/stringification/_generate.py +212 -0
  130. aas_core_codegen/java/structure/__init__.py +6 -0
  131. aas_core_codegen/java/structure/_generate.py +1767 -0
  132. aas_core_codegen/java/transpilation.py +1111 -0
  133. aas_core_codegen/java/verification/__init__.py +6 -0
  134. aas_core_codegen/java/verification/_generate.py +1536 -0
  135. aas_core_codegen/java/visitation/__init__.py +5 -0
  136. aas_core_codegen/java/visitation/_generate.py +689 -0
  137. aas_core_codegen/java/xmlization/__init__.py +4 -0
  138. aas_core_codegen/java/xmlization/_generate.py +2274 -0
  139. aas_core_codegen/jsonld/__init__.py +1 -0
  140. aas_core_codegen/jsonld/main.py +455 -0
  141. aas_core_codegen/jsonschema/__init__.py +1 -0
  142. aas_core_codegen/jsonschema/main.py +982 -0
  143. aas_core_codegen/main.py +245 -0
  144. aas_core_codegen/naming.py +133 -0
  145. aas_core_codegen/opcua/__init__.py +1 -0
  146. aas_core_codegen/opcua/main.py +1525 -0
  147. aas_core_codegen/opcua/naming.py +126 -0
  148. aas_core_codegen/parse/__init__.py +46 -0
  149. aas_core_codegen/parse/_rules.py +796 -0
  150. aas_core_codegen/parse/_stringify.py +532 -0
  151. aas_core_codegen/parse/_translate.py +3940 -0
  152. aas_core_codegen/parse/_types.py +973 -0
  153. aas_core_codegen/parse/retree/__init__.py +46 -0
  154. aas_core_codegen/parse/retree/_fix.py +434 -0
  155. aas_core_codegen/parse/retree/_parse.py +1143 -0
  156. aas_core_codegen/parse/retree/_render.py +298 -0
  157. aas_core_codegen/parse/retree/_stringify.py +199 -0
  158. aas_core_codegen/parse/retree/_types.py +362 -0
  159. aas_core_codegen/parse/retree/_visitor.py +70 -0
  160. aas_core_codegen/parse/tree.py +1303 -0
  161. aas_core_codegen/protobuf/__init__.py +1 -0
  162. aas_core_codegen/protobuf/common.py +225 -0
  163. aas_core_codegen/protobuf/description.py +1102 -0
  164. aas_core_codegen/protobuf/main.py +115 -0
  165. aas_core_codegen/protobuf/naming.py +143 -0
  166. aas_core_codegen/protobuf/structure/__init__.py +6 -0
  167. aas_core_codegen/protobuf/structure/_generate.py +502 -0
  168. aas_core_codegen/py.typed +1 -0
  169. aas_core_codegen/python/__init__.py +1 -0
  170. aas_core_codegen/python/aas_common/__init__.py +4 -0
  171. aas_core_codegen/python/aas_common/_generate.py +63 -0
  172. aas_core_codegen/python/common.py +406 -0
  173. aas_core_codegen/python/constants/__init__.py +5 -0
  174. aas_core_codegen/python/constants/_generate.py +377 -0
  175. aas_core_codegen/python/description.py +508 -0
  176. aas_core_codegen/python/jsonization/__init__.py +4 -0
  177. aas_core_codegen/python/jsonization/_generate.py +1391 -0
  178. aas_core_codegen/python/main.py +323 -0
  179. aas_core_codegen/python/naming.py +255 -0
  180. aas_core_codegen/python/stringification/__init__.py +4 -0
  181. aas_core_codegen/python/stringification/_generate.py +129 -0
  182. aas_core_codegen/python/structure/__init__.py +6 -0
  183. aas_core_codegen/python/structure/_generate.py +1801 -0
  184. aas_core_codegen/python/transpilation.py +958 -0
  185. aas_core_codegen/python/unrolling.py +156 -0
  186. aas_core_codegen/python/verification/__init__.py +6 -0
  187. aas_core_codegen/python/verification/_generate.py +1471 -0
  188. aas_core_codegen/python/xmlization/__init__.py +4 -0
  189. aas_core_codegen/python/xmlization/_generate.py +3003 -0
  190. aas_core_codegen/python_protobuf/__init__.py +1 -0
  191. aas_core_codegen/python_protobuf/main.py +1424 -0
  192. aas_core_codegen/python_protobuf/naming.py +85 -0
  193. aas_core_codegen/rdf_shacl/__init__.py +1 -0
  194. aas_core_codegen/rdf_shacl/_description.py +351 -0
  195. aas_core_codegen/rdf_shacl/common.py +206 -0
  196. aas_core_codegen/rdf_shacl/main.py +114 -0
  197. aas_core_codegen/rdf_shacl/naming.py +145 -0
  198. aas_core_codegen/rdf_shacl/rdf.py +435 -0
  199. aas_core_codegen/rdf_shacl/shacl.py +453 -0
  200. aas_core_codegen/run.py +124 -0
  201. aas_core_codegen/smoke/__init__.py +1 -0
  202. aas_core_codegen/smoke/main.py +219 -0
  203. aas_core_codegen/specific_implementations.py +72 -0
  204. aas_core_codegen/stringify.py +333 -0
  205. aas_core_codegen/typescript/__init__.py +1 -0
  206. aas_core_codegen/typescript/aas_common/__init__.py +4 -0
  207. aas_core_codegen/typescript/aas_common/_generate.py +472 -0
  208. aas_core_codegen/typescript/common.py +340 -0
  209. aas_core_codegen/typescript/constants/__init__.py +5 -0
  210. aas_core_codegen/typescript/constants/_generate.py +347 -0
  211. aas_core_codegen/typescript/description.py +530 -0
  212. aas_core_codegen/typescript/jsonization/__init__.py +4 -0
  213. aas_core_codegen/typescript/jsonization/_generate.py +1510 -0
  214. aas_core_codegen/typescript/main.py +258 -0
  215. aas_core_codegen/typescript/naming.py +189 -0
  216. aas_core_codegen/typescript/stringification/__init__.py +4 -0
  217. aas_core_codegen/typescript/stringification/_generate.py +367 -0
  218. aas_core_codegen/typescript/structure/__init__.py +6 -0
  219. aas_core_codegen/typescript/structure/_generate.py +2500 -0
  220. aas_core_codegen/typescript/transpilation.py +1051 -0
  221. aas_core_codegen/typescript/unrolling.py +159 -0
  222. aas_core_codegen/typescript/verification/__init__.py +6 -0
  223. aas_core_codegen/typescript/verification/_generate.py +1578 -0
  224. aas_core_codegen/xsd/__init__.py +1 -0
  225. aas_core_codegen/xsd/main.py +1187 -0
  226. aas_core_codegen/xsd/naming.py +83 -0
  227. aas_core_codegen/yielding/__init__.py +1 -0
  228. aas_core_codegen/yielding/flow.py +139 -0
  229. aas_core_codegen/yielding/linear.py +754 -0
  230. aas_core_codegen-0.0.16.dist-info/METADATA +211 -0
  231. aas_core_codegen-0.0.16.dist-info/RECORD +604 -0
  232. aas_core_codegen-0.0.16.dist-info/WHEEL +5 -0
  233. aas_core_codegen-0.0.16.dist-info/entry_points.txt +3 -0
  234. aas_core_codegen-0.0.16.dist-info/licenses/AUTHORS +9 -0
  235. aas_core_codegen-0.0.16.dist-info/licenses/LICENSE +23 -0
  236. aas_core_codegen-0.0.16.dist-info/top_level.txt +2 -0
  237. dev/continuous_integration/__init__.py +1 -0
  238. dev/continuous_integration/check_help_in_readme.py +208 -0
  239. dev/continuous_integration/check_init_and_pyproject_consistent.py +154 -0
  240. dev/continuous_integration/precommit.py +400 -0
  241. dev/dev_scripts/__init__.py +1 -0
  242. dev/dev_scripts/compare_rendered_regexes_against_source_py.py +42 -0
  243. dev/dev_scripts/copy_to_aas_core3_cpp.py +100 -0
  244. dev/dev_scripts/copy_to_aas_core3_java.py +90 -0
  245. dev/dev_scripts/download_latest_aas_core_meta_v3.py +114 -0
  246. dev/dev_scripts/draw_bipartite_graph_based_on_lines.py +37 -0
  247. dev/dev_scripts/run_tests_with_rerecord.py +69 -0
  248. dev/dev_scripts/update_to_aas_core_meta.py +174 -0
  249. dev/integration_tests/input/jsonschema/boilerplate/main.py +55 -0
  250. dev/integration_tests/input/meta_model.py +38 -0
  251. dev/integration_tests/input/python/boilerplate/main.py +153 -0
  252. dev/integration_tests/main.py +258 -0
  253. dev/test_data/csharp/test_structure/concrete_class_with_descendants/meta_model.py +15 -0
  254. dev/test_data/csharp/test_structure/constructor_without_arguments/all_properties_optional/meta_model.py +9 -0
  255. dev/test_data/csharp/test_structure/constructor_without_arguments/no_properties/meta_model.py +6 -0
  256. dev/test_data/csharp/test_verification/builtin_functions/len/on_list/meta_model.py +20 -0
  257. dev/test_data/csharp/test_verification/builtin_functions/len/on_str/meta_model.py +16 -0
  258. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/as_prefix/meta_model.py +8 -0
  259. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/as_suffix/meta_model.py +8 -0
  260. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/in_group_with_quantifier/meta_model.py +8 -0
  261. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/in_the_middle/meta_model.py +8 -0
  262. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/in_union/meta_model.py +8 -0
  263. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/single_utf32_literal/meta_model.py +8 -0
  264. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/with_quantifier_within_group/meta_model.py +8 -0
  265. dev/test_data/csharp/test_verification/pattern_verification/utf32_as_literal/with_quantifier_without_group/meta_model.py +8 -0
  266. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/literal/at_the_beginning/meta_model.py +8 -0
  267. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/literal/at_the_end/meta_model.py +8 -0
  268. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/literal/in_the_middle/meta_model.py +8 -0
  269. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/literal/multiple/meta_model.py +8 -0
  270. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/literal/single/meta_model.py +8 -0
  271. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/literal/single_with_quantifier/meta_model.py +8 -0
  272. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/range/mixed_with_non_utf32/meta_model.py +8 -0
  273. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/range/more_than_two_high_surrogates/meta_model.py +8 -0
  274. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/range/multiple_utf32_ranges/meta_model.py +8 -0
  275. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/range/multiple_utf32_ranges_mixed_with_non_utf32/meta_model.py +8 -0
  276. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/range/same_high_surrogate/meta_model.py +8 -0
  277. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/range/same_high_surrogate_with_quantifier/meta_model.py +8 -0
  278. dev/test_data/csharp/test_verification/pattern_verification/utf32_in_character_set/range/two_high_surrogates/meta_model.py +8 -0
  279. dev/test_data/intermediate/expected/class/empty/meta_model.py +6 -0
  280. dev/test_data/intermediate/expected/class/implementation_specific_method/meta_model.py +8 -0
  281. dev/test_data/intermediate/expected/class/inheritance/meta_model.py +41 -0
  282. dev/test_data/intermediate/expected/class/methods_with_contracts/meta_model.py +15 -0
  283. dev/test_data/intermediate/expected/class/only_method_no_property/meta_model.py +7 -0
  284. dev/test_data/intermediate/expected/class/only_property_no_method/meta_model.py +9 -0
  285. dev/test_data/intermediate/expected/constant/constant_set/of_enum/meta_model.py +12 -0
  286. dev/test_data/intermediate/expected/constant/constant_set/of_str/meta_model.py +4 -0
  287. dev/test_data/intermediate/expected/constant/constant_set/with_description/meta_model.py +6 -0
  288. dev/test_data/intermediate/expected/constant/constant_set/with_superset_of/meta_model.py +14 -0
  289. dev/test_data/intermediate/expected/constant/constant_str/only_value/meta_model.py +7 -0
  290. dev/test_data/intermediate/expected/constant/constant_str/with_description/meta_model.py +5 -0
  291. dev/test_data/intermediate/expected/documentation/docstring_with_special_characters_in_literal/meta_model.py +20 -0
  292. dev/test_data/intermediate/expected/documentation/docstring_with_special_characters_outside_literal/meta_model.py +20 -0
  293. dev/test_data/intermediate/expected/empty/meta_model.py +2 -0
  294. dev/test_data/intermediate/expected/enumeration/meta_model.py +9 -0
  295. dev/test_data/intermediate/expected/interface/basic/meta_model.py +14 -0
  296. dev/test_data/intermediate/expected/interface/empty/meta_model.py +7 -0
  297. dev/test_data/intermediate/expected/interface/inheritance/meta_model.py +27 -0
  298. dev/test_data/intermediate/expected/interface/method_signature/meta_model.py +10 -0
  299. dev/test_data/intermediate/expected/interface/only_constructor/meta_model.py +11 -0
  300. dev/test_data/intermediate/expected/method/non_mutating/implementation_specific/meta_model.py +12 -0
  301. dev/test_data/intermediate/expected/method/non_mutating/understood/meta_model.py +11 -0
  302. dev/test_data/intermediate/expected/type_annotation/atomic/meta_model.py +9 -0
  303. dev/test_data/intermediate/expected/type_annotation/subscripted/class/meta_model.py +13 -0
  304. dev/test_data/intermediate/expected/type_annotation/subscripted/primitive/meta_model.py +9 -0
  305. dev/test_data/intermediate/unexpected/constant_set/of_enum/enumeration_literals_in_subset_outside_of_superset/meta_model.py +20 -0
  306. dev/test_data/intermediate/unexpected/constant_set/of_enum/invalid_literal/meta_model.py +11 -0
  307. dev/test_data/intermediate/unexpected/constant_set/of_enum/mismatch_between_enumeration_and_literal/meta_model.py +30 -0
  308. dev/test_data/intermediate/unexpected/constant_set/of_enum/mismatch_in_enumerations_between_subset_and_superset/meta_model.py +21 -0
  309. dev/test_data/intermediate/unexpected/constant_set/of_str/literals_in_subset_outside_of_superset/meta_model.py +18 -0
  310. dev/test_data/intermediate/unexpected/constant_set/of_str/mismatch_between_type_annotation_and_literals/meta_model.py +10 -0
  311. dev/test_data/intermediate/unexpected/constant_set/of_str/superset_and_subset_mismatch_in_type/meta_model.py +12 -0
  312. dev/test_data/intermediate/unexpected/constraints/dangling_constraintref/meta_model.py +18 -0
  313. dev/test_data/intermediate/unexpected/constraints/duplicate_constraints/meta_model.py +20 -0
  314. dev/test_data/intermediate/unexpected/documentation/unexpected_documentation_elements/meta_model.py +34 -0
  315. dev/test_data/intermediate/unexpected/invariant/class_invariant_uses_re/meta_model.py +10 -0
  316. dev/test_data/intermediate/unexpected/invariant/invariant_of_constrained_primitive_uses_re/meta_model.py +7 -0
  317. dev/test_data/intermediate/unexpected/invariant/unexpected_argument_count_to_len/meta_model.py +20 -0
  318. dev/test_data/intermediate/unexpected/invariant/unhandled_built_in_function/meta_model.py +16 -0
  319. dev/test_data/intermediate/unexpected/method_definitions/non_constant_default/meta_model.py +7 -0
  320. dev/test_data/intermediate/unexpected/optional_constructor_arguments_wo_default/default_non_none/meta_model.py +16 -0
  321. dev/test_data/intermediate/unexpected/optional_constructor_arguments_wo_default/no_default/meta_model.py +16 -0
  322. dev/test_data/intermediate/unexpected/properties_and_constructor_arguments_do_not_match/after_inheritance/meta_model.py +58 -0
  323. dev/test_data/intermediate/unexpected/properties_and_constructor_arguments_do_not_match/type_missmatch/meta_model.py +9 -0
  324. dev/test_data/intermediate/unexpected/properties_and_constructor_arguments_do_not_match/within_class/meta_model.py +22 -0
  325. dev/test_data/jsonschema/test_main/regression_when_len_constraints_on_inherited_property/meta_model.py +28 -0
  326. dev/test_data/opcua/test_main/abstract_and_concrete_classes/meta_model.py +37 -0
  327. dev/test_data/opcua/test_main/classes_with_invariants/meta_model.py +21 -0
  328. dev/test_data/opcua/test_main/concrete_class_with_descendant/meta_model.py +27 -0
  329. dev/test_data/opcua/test_main/concrete_class_with_enum/meta_model.py +21 -0
  330. dev/test_data/opcua/test_main/concrete_class_with_list_of_instances/meta_model.py +21 -0
  331. dev/test_data/opcua/test_main/concrete_class_with_primitive_attributes/meta_model.py +41 -0
  332. dev/test_data/opcua/test_main/concrete_class_with_string/meta_model.py +13 -0
  333. dev/test_data/opcua/test_main/constrained_primitive/meta_model.py +20 -0
  334. dev/test_data/opcua/test_main/multiple_inheritance/meta_model.py +25 -0
  335. dev/test_data/parse/expected/constant/constant_set/of_enum/meta_model.py +12 -0
  336. dev/test_data/parse/expected/constant/constant_set/of_str/meta_model.py +4 -0
  337. dev/test_data/parse/expected/constant/constant_set/with_description/meta_model.py +6 -0
  338. dev/test_data/parse/expected/constant/constant_set/with_superset_of/meta_model.py +14 -0
  339. dev/test_data/parse/expected/constant/constant_str/only_value/meta_model.py +7 -0
  340. dev/test_data/parse/expected/constant/constant_str/with_description/meta_model.py +5 -0
  341. dev/test_data/parse/expected/enum/ok/meta_model.py +15 -0
  342. dev/test_data/parse/expected/implementation_specific_class/properties_and_methods_in_implementation_specific_class/meta_model.py +17 -0
  343. dev/test_data/parse/expected/inheritance/basic/meta_model.py +11 -0
  344. dev/test_data/parse/expected/inheritance/diamond/meta_model.py +26 -0
  345. dev/test_data/parse/expected/inheritance/inheritance_from_concrete_class/meta_model.py +10 -0
  346. dev/test_data/parse/expected/invariants/in_relation/meta_model.py +16 -0
  347. dev/test_data/parse/expected/method/arguments/meta_model.py +7 -0
  348. dev/test_data/parse/expected/method/basic/meta_model.py +7 -0
  349. dev/test_data/parse/expected/method/contracts/condition_as_keyword_argument/meta_model.py +8 -0
  350. dev/test_data/parse/expected/method/contracts/condition_as_positional_argument/meta_model.py +8 -0
  351. dev/test_data/parse/expected/method/contracts/description_as_keyword_argument/meta_model.py +8 -0
  352. dev/test_data/parse/expected/method/contracts/description_as_positional_argument/meta_model.py +8 -0
  353. dev/test_data/parse/expected/method/contracts/multiple_contracts_in_order/meta_model.py +17 -0
  354. dev/test_data/parse/expected/method/contracts/postcondition/basic/meta_model.py +10 -0
  355. dev/test_data/parse/expected/method/contracts/postcondition/snapshot/with_keyword_arguments/meta_model.py +9 -0
  356. dev/test_data/parse/expected/method/contracts/postcondition/snapshot/with_positional_arguments/meta_model.py +9 -0
  357. dev/test_data/parse/expected/method/default/meta_model.py +9 -0
  358. dev/test_data/parse/expected/method/description/meta_model.py +8 -0
  359. dev/test_data/parse/expected/method/is_implementation_specific/meta_model.py +8 -0
  360. dev/test_data/parse/expected/method/non_mutating/meta_model.py +11 -0
  361. dev/test_data/parse/expected/method/returns_none/meta_model.py +7 -0
  362. dev/test_data/parse/expected/method/returns_something/meta_model.py +7 -0
  363. dev/test_data/parse/expected/single_class/description/meta_model.py +12 -0
  364. dev/test_data/parse/expected/single_class/empty/meta_model.py +6 -0
  365. dev/test_data/parse/expected/single_class/property/description/meta_model.py +14 -0
  366. dev/test_data/parse/expected/single_class/property/mandatory/meta_model.py +6 -0
  367. dev/test_data/parse/expected/single_class/property/optional/meta_model.py +6 -0
  368. dev/test_data/parse/expected/single_class/property/recursion_to_entity/meta_model.py +6 -0
  369. dev/test_data/parse/unexpected/class_decorators/non_name_decorator/meta_model.py +7 -0
  370. dev/test_data/parse/unexpected/class_decorators/unknown_decorator/meta_model.py +7 -0
  371. dev/test_data/parse/unexpected/class_definitions/is_abstract_and_implementation_specific/meta_model.py +8 -0
  372. dev/test_data/parse/unexpected/class_definitions/unexpected_docstring_before_a_method/meta_model.py +11 -0
  373. dev/test_data/parse/unexpected/class_definitions/unexpected_docstring_for_a_pass/meta_model.py +9 -0
  374. dev/test_data/parse/unexpected/class_definitions/unexpected_double_description_for_a_property/meta_model.py +10 -0
  375. dev/test_data/parse/unexpected/class_inheritances/inheriting_from_implementation_specific_parent/meta_model.py +20 -0
  376. dev/test_data/parse/unexpected/class_inheritances/non_name_super_class/meta_model.py +6 -0
  377. dev/test_data/parse/unexpected/enum/expression_as_assignment_value/meta_model.py +6 -0
  378. dev/test_data/parse/unexpected/enum/non_assignment/meta_model.py +8 -0
  379. dev/test_data/parse/unexpected/enum/non_string_literal/meta_model.py +6 -0
  380. dev/test_data/parse/unexpected/enum/unexpected_inheritance/meta_model.py +6 -0
  381. dev/test_data/parse/unexpected/method_contracts/contract/non_lambda_condition/meta_model.py +8 -0
  382. dev/test_data/parse/unexpected/method_contracts/contract/non_string_literal_description/meta_model.py +8 -0
  383. dev/test_data/parse/unexpected/method_contracts/contract/without_any_arguments/meta_model.py +8 -0
  384. dev/test_data/parse/unexpected/method_contracts/contract/without_condition/meta_model.py +8 -0
  385. dev/test_data/parse/unexpected/method_contracts/postcondition/OLD_in_postcondition_without_snapshot/meta_model.py +8 -0
  386. dev/test_data/parse/unexpected/method_contracts/postcondition/argument_missing_in_function/meta_model.py +8 -0
  387. dev/test_data/parse/unexpected/method_contracts/precondition/argument_missing_in_function/meta_model.py +8 -0
  388. dev/test_data/parse/unexpected/method_contracts/snapshot/argument_missing_in_function/meta_model.py +8 -0
  389. dev/test_data/parse/unexpected/method_contracts/snapshot/capture_not_a_lambda/meta_model.py +8 -0
  390. dev/test_data/parse/unexpected/method_contracts/snapshot/invalid_name/meta_model.py +8 -0
  391. dev/test_data/parse/unexpected/method_contracts/snapshot/name_not_a_string_literal/meta_model.py +8 -0
  392. dev/test_data/parse/unexpected/method_contracts/snapshot/without_a_capture/meta_model.py +8 -0
  393. dev/test_data/parse/unexpected/method_contracts/snapshot/without_a_name/meta_model.py +8 -0
  394. dev/test_data/parse/unexpected/method_decorators/non_mutating/non_mutating_constructor/meta_model.py +8 -0
  395. dev/test_data/parse/unexpected/method_decorators/non_mutating/non_mutating_verification_function/meta_model.py +8 -0
  396. dev/test_data/parse/unexpected/method_decorators/non_name_decorator/meta_model.py +8 -0
  397. dev/test_data/parse/unexpected/method_decorators/unknown_call_decorator/meta_model.py +8 -0
  398. dev/test_data/parse/unexpected/method_decorators/unknown_name_decorator/meta_model.py +8 -0
  399. dev/test_data/parse/unexpected/method_definitions/argument_with_final/meta_model.py +7 -0
  400. dev/test_data/parse/unexpected/method_definitions/argument_without_a_type_annotation/meta_model.py +7 -0
  401. dev/test_data/parse/unexpected/method_definitions/default_for_self/meta_model.py +7 -0
  402. dev/test_data/parse/unexpected/method_definitions/dunder/meta_model.py +7 -0
  403. dev/test_data/parse/unexpected/method_definitions/init_with_return_type/meta_model.py +7 -0
  404. dev/test_data/parse/unexpected/method_definitions/with_keyword_only_arguments/meta_model.py +7 -0
  405. dev/test_data/parse/unexpected/method_definitions/with_positional_arguments/meta_model.py +7 -0
  406. dev/test_data/parse/unexpected/method_definitions/with_type_annotation_for_self/meta_model.py +7 -0
  407. dev/test_data/parse/unexpected/method_definitions/with_variable_arguments/meta_model.py +7 -0
  408. dev/test_data/parse/unexpected/method_definitions/with_variable_keyword_arguments/meta_model.py +7 -0
  409. dev/test_data/parse/unexpected/method_definitions/without_arguments/meta_model.py +7 -0
  410. dev/test_data/parse/unexpected/method_definitions/without_self/meta_model.py +7 -0
  411. dev/test_data/parse/unexpected/method_definitions/without_type_annotation_for_result/meta_model.py +7 -0
  412. dev/test_data/parse/unexpected/property_definitions/final_without_subscript/meta_model.py +6 -0
  413. dev/test_data/parse/unexpected/property_definitions/nested_final/meta_model.py +6 -0
  414. dev/test_data/parse/unexpected/property_definitions/non_simple/meta_model.py +6 -0
  415. dev/test_data/parse/unexpected/property_definitions/unexpected_assignment/meta_model.py +6 -0
  416. dev/test_data/parse/unexpected/property_definitions/unexpected_non_name_property/meta_model.py +6 -0
  417. dev/test_data/parse/unexpected/property_definitions/without_type_annotation/meta_model.py +6 -0
  418. dev/test_data/parse/unexpected/symbol_table/constant_set_with_a_non_set_subset/meta_model.py +6 -0
  419. dev/test_data/parse/unexpected/symbol_table/dangling_inheritance/meta_model.py +6 -0
  420. dev/test_data/parse/unexpected/symbol_table/dangling_reference_in_type_annotation_of_a_property/meta_model.py +6 -0
  421. dev/test_data/parse/unexpected/symbol_table/dangling_reference_in_type_annotation_of_an_argument/meta_model.py +7 -0
  422. dev/test_data/parse/unexpected/symbol_table/dangling_reference_in_type_annotation_of_constant_set/meta_model.py +6 -0
  423. dev/test_data/parse/unexpected/symbol_table/dangling_subset_in_constant_set/meta_model.py +4 -0
  424. dev/test_data/parse/unexpected/symbol_table/inheritance_from_non_class/meta_model.py +10 -0
  425. dev/test_data/parse_retree/expected/character_set/common_escaping/source.py +1 -0
  426. dev/test_data/parse_retree/expected/character_set/complementing/double_caret/source.py +1 -0
  427. dev/test_data/parse_retree/expected/character_set/complementing/multiple_ranges/source.py +1 -0
  428. dev/test_data/parse_retree/expected/character_set/complementing/suffix_dash/source.py +1 -0
  429. dev/test_data/parse_retree/expected/character_set/escape_first_caret/source.py +1 -0
  430. dev/test_data/parse_retree/expected/character_set/literals_which_need_no_escaping_in_characters_set_but_need_escaping_outside/source.py +1 -0
  431. dev/test_data/parse_retree/expected/character_set/multiple_ranges/source.py +1 -0
  432. dev/test_data/parse_retree/expected/character_set/single_literal/source.py +1 -0
  433. dev/test_data/parse_retree/expected/character_set/single_range/source.py +1 -0
  434. dev/test_data/parse_retree/expected/character_set/unescaped_dash/only_dash/source.py +1 -0
  435. dev/test_data/parse_retree/expected/character_set/unescaped_dash/prefix_dash/source.py +1 -0
  436. dev/test_data/parse_retree/expected/character_set/unescaped_dash/suffix_dash/source.py +1 -0
  437. dev/test_data/parse_retree/expected/dot/source.py +1 -0
  438. dev/test_data/parse_retree/expected/empty/group/source.py +1 -0
  439. dev/test_data/parse_retree/expected/empty/group_in_a_group/source.py +1 -0
  440. dev/test_data/parse_retree/expected/empty/group_of_union_of_empty_concatenations/source.py +1 -0
  441. dev/test_data/parse_retree/expected/empty/regex/source.py +1 -0
  442. dev/test_data/parse_retree/expected/empty/union_of_empty_concatenations/source.py +1 -0
  443. dev/test_data/parse_retree/expected/escaped_literals/source.py +1 -0
  444. dev/test_data/parse_retree/expected/formatted_value/at_the_beginning/source.py +1 -0
  445. dev/test_data/parse_retree/expected/formatted_value/at_the_end/source.py +1 -0
  446. dev/test_data/parse_retree/expected/formatted_value/in_the_middle/source.py +1 -0
  447. dev/test_data/parse_retree/expected/formatted_value/single_formatted_value/source.py +1 -0
  448. dev/test_data/parse_retree/expected/literal/source.py +1 -0
  449. dev/test_data/parse_retree/expected/quantifier/greedy/at_least_3/source.py +1 -0
  450. dev/test_data/parse_retree/expected/quantifier/greedy/at_least_one/source.py +1 -0
  451. dev/test_data/parse_retree/expected/quantifier/greedy/at_most_3/source.py +1 -0
  452. dev/test_data/parse_retree/expected/quantifier/greedy/exactly_3/source.py +1 -0
  453. dev/test_data/parse_retree/expected/quantifier/greedy/maybe/source.py +1 -0
  454. dev/test_data/parse_retree/expected/quantifier/greedy/zero_or_more/source.py +1 -0
  455. dev/test_data/parse_retree/expected/quantifier/non_greedy/at_least_3/source.py +1 -0
  456. dev/test_data/parse_retree/expected/quantifier/non_greedy/at_least_one/source.py +1 -0
  457. dev/test_data/parse_retree/expected/quantifier/non_greedy/at_most_3/source.py +1 -0
  458. dev/test_data/parse_retree/expected/quantifier/non_greedy/exactly_3/source.py +1 -0
  459. dev/test_data/parse_retree/expected/quantifier/non_greedy/maybe/source.py +1 -0
  460. dev/test_data/parse_retree/expected/quantifier/non_greedy/zero_or_more/source.py +1 -0
  461. dev/test_data/parse_retree/expected/quantifier/on_a_character_set/source.py +1 -0
  462. dev/test_data/parse_retree/expected/quantifier/on_a_formatted_value/source.py +1 -0
  463. dev/test_data/parse_retree/expected/quantifier/on_a_group/source.py +1 -0
  464. dev/test_data/parse_retree/expected/quantifier/on_a_literal/source.py +1 -0
  465. dev/test_data/parse_retree/expected/start_and_stop_symbols/double_end_symbol/source.py +1 -0
  466. dev/test_data/parse_retree/expected/start_and_stop_symbols/double_start_symbol/source.py +1 -0
  467. dev/test_data/parse_retree/expected/start_and_stop_symbols/end_symbol_in_the_middle/source.py +1 -0
  468. dev/test_data/parse_retree/expected/start_and_stop_symbols/only_start_symbol/source.py +1 -0
  469. dev/test_data/parse_retree/expected/start_and_stop_symbols/only_stop_symbol/source.py +1 -0
  470. dev/test_data/parse_retree/expected/start_and_stop_symbols/start_symbol_at_the_beginning/source.py +1 -0
  471. dev/test_data/parse_retree/expected/start_and_stop_symbols/start_symbol_in_the_middle/source.py +1 -0
  472. dev/test_data/parse_retree/expected/start_and_stop_symbols/stop_symbol_at_the_end/source.py +1 -0
  473. dev/test_data/parse_retree/expected/union/of_character_sets/source.py +1 -0
  474. dev/test_data/parse_retree/expected/union/of_groups/source.py +1 -0
  475. dev/test_data/parse_retree/expected/union/of_string_literals/source.py +1 -0
  476. dev/test_data/parse_retree/expected/union/within_group/source.py +1 -0
  477. dev/test_data/parse_retree/expected/whitespace/source.py +1 -0
  478. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/Uxxxxxxxx_out_of_range/source.py +1 -0
  479. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/only_backslash/source.py +1 -0
  480. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/short_Uxxxxxxxx/source.py +1 -0
  481. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/short_uxxxx/source.py +1 -0
  482. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/short_x/source.py +1 -0
  483. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/unexpected_escaping/source.py +1 -0
  484. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/unhandled/digit/source.py +1 -0
  485. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/unhandled/not_digit/source.py +1 -0
  486. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/unhandled/not_whitespace/source.py +1 -0
  487. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/unhandled/not_word/source.py +1 -0
  488. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/unhandled/whitespace/source.py +1 -0
  489. dev/test_data/parse_retree/unexpected/improper_escaping/character_literal/unhandled/word/source.py +1 -0
  490. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/Uxxxxxxxx_out_of_range/source.py +1 -0
  491. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/only_backslash/source.py +1 -0
  492. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/short_Uxxxxxxxx/source.py +1 -0
  493. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/short_uxxxx/source.py +1 -0
  494. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/short_x/source.py +1 -0
  495. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/unexpected_escaping/source.py +1 -0
  496. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/unhandled/digit/source.py +1 -0
  497. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/unhandled/not_digit/source.py +1 -0
  498. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/unhandled/not_whitespace/source.py +1 -0
  499. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/unhandled/not_word/source.py +1 -0
  500. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/unhandled/whitespace/source.py +1 -0
  501. dev/test_data/parse_retree/unexpected/improper_escaping/range_character/unhandled/word/source.py +1 -0
  502. dev/test_data/parse_retree/unexpected/invalid_character_range/source.py +1 -0
  503. dev/test_data/parse_retree/unexpected/invalid_quantifier/at_least_x/source.py +1 -0
  504. dev/test_data/parse_retree/unexpected/invalid_quantifier/between_3_and_x/source.py +1 -0
  505. dev/test_data/parse_retree/unexpected/invalid_quantifier/exactly_x/source.py +1 -0
  506. dev/test_data/parse_retree/unexpected/unhandled_group_directives/source.py +1 -0
  507. dev/test_data/parse_retree/unexpected/unterminated/character_set/source.py +1 -0
  508. dev/test_data/parse_retree/unexpected/unterminated/group/source.py +1 -0
  509. dev/test_data/parse_retree/unexpected/unterminated/group_of_union_of_empty_concatenations/source.py +1 -0
  510. dev/test_data/parse_retree/unexpected/unterminated/quantifier/source.py +1 -0
  511. dev/test_data/parse_retree/unexpected/unterminated/quantifier_with_comma/source.py +1 -0
  512. dev/test_data/parse_retree/unexpected/unterminated/quantifier_with_number_and_comma/source.py +1 -0
  513. dev/test_data/proto/test_main/expected/abstract_and_concrete_classes/meta_model.py +37 -0
  514. dev/test_data/proto/test_main/expected/concrete_class_with_descendants/meta_model.py +30 -0
  515. dev/test_data/proto/test_main/expected/concrete_class_with_enum/meta_model.py +21 -0
  516. dev/test_data/proto/test_main/expected/concrete_class_with_list_of_instances/meta_model.py +21 -0
  517. dev/test_data/proto/test_main/expected/concrete_class_with_primitive_attributes/meta_model.py +41 -0
  518. dev/test_data/python_protobuf/test_main/abstract_and_concrete_classes/expected_output/pbization.py +532 -0
  519. dev/test_data/python_protobuf/test_main/abstract_and_concrete_classes/meta_model.py +37 -0
  520. dev/test_data/python_protobuf/test_main/concrete_class_with_descendant/expected_output/pbization.py +527 -0
  521. dev/test_data/python_protobuf/test_main/concrete_class_with_descendant/meta_model.py +27 -0
  522. dev/test_data/python_protobuf/test_main/concrete_class_with_enum/expected_output/pbization.py +290 -0
  523. dev/test_data/python_protobuf/test_main/concrete_class_with_enum/meta_model.py +21 -0
  524. dev/test_data/python_protobuf/test_main/concrete_class_with_list_of_instances/expected_output/pbization.py +328 -0
  525. dev/test_data/python_protobuf/test_main/concrete_class_with_list_of_instances/meta_model.py +23 -0
  526. dev/test_data/python_protobuf/test_main/concrete_class_with_primitive_attributes/expected_output/pbization.py +274 -0
  527. dev/test_data/python_protobuf/test_main/concrete_class_with_primitive_attributes/meta_model.py +41 -0
  528. dev/test_data/rdf_shacl/test_main/expected/regression_when_lang_string_class_is_missing/meta_model.py +29 -0
  529. dev/test_data/rdf_shacl/test_main/expected/regression_when_len_constraints_on_inherited_property/meta_model.py +27 -0
  530. dev/test_data/rdf_shacl/test_main/unexpected/regression_len_constraint_on_class_property/meta_model.py +61 -0
  531. dev/test_data/real_meta_models/aas_core_meta.v3.py +5721 -0
  532. dev/test_data/smoke/test_main/unexpected/infer_for_schema_error/meta_model.py +12 -0
  533. dev/test_data/smoke/test_main/unexpected/intermediate_error/meta_model.py +18 -0
  534. dev/test_data/smoke/test_main/unexpected/parse_error/meta_model.py +5 -0
  535. dev/test_data/smoke/test_main/unexpected/pattern_verification_unparsable_regex/direct_match/meta_model.py +8 -0
  536. dev/test_data/smoke/test_main/unexpected/type_error/meta_model.py +18 -0
  537. dev/tests/__init__.py +1 -0
  538. dev/tests/common.py +197 -0
  539. dev/tests/cpp/__init__.py +0 -0
  540. dev/tests/cpp/test_common.py +32 -0
  541. dev/tests/cpp/test_main.py +144 -0
  542. dev/tests/cpp/test_pattern.py +188 -0
  543. dev/tests/cpp/test_verification.py +189 -0
  544. dev/tests/cpp/test_yielding.py +225 -0
  545. dev/tests/csharp/__init__.py +0 -0
  546. dev/tests/csharp/live_test_main.py +109 -0
  547. dev/tests/csharp/test_common.py +28 -0
  548. dev/tests/csharp/test_description.py +684 -0
  549. dev/tests/csharp/test_main.py +129 -0
  550. dev/tests/csharp/test_structure.py +93 -0
  551. dev/tests/csharp/test_verification.py +82 -0
  552. dev/tests/description.py +29 -0
  553. dev/tests/golang/__init__.py +0 -0
  554. dev/tests/golang/test_common.py +78 -0
  555. dev/tests/golang/test_main.py +128 -0
  556. dev/tests/infer_for_schema/__init__.py +0 -0
  557. dev/tests/infer_for_schema/common.py +47 -0
  558. dev/tests/infer_for_schema/test_len_on_properties.py +955 -0
  559. dev/tests/infer_for_schema/test_len_on_self.py +580 -0
  560. dev/tests/infer_for_schema/test_patterns_on_properties.py +686 -0
  561. dev/tests/infer_for_schema/test_patterns_on_self.py +258 -0
  562. dev/tests/infer_for_schema/test_property_in_set_of_enumeration_literals.py +600 -0
  563. dev/tests/infer_for_schema/test_property_in_set_of_primitives.py +549 -0
  564. dev/tests/intermediate/__init__.py +0 -0
  565. dev/tests/intermediate/test_constructor.py +719 -0
  566. dev/tests/intermediate/test_hierarchy.py +221 -0
  567. dev/tests/intermediate/test_revm.py +134 -0
  568. dev/tests/intermediate/test_translate.py +337 -0
  569. dev/tests/intermediate/test_type_inference.py +333 -0
  570. dev/tests/intermediate/test_types.py +169 -0
  571. dev/tests/java/__init__.py +0 -0
  572. dev/tests/java/test_common.py +20 -0
  573. dev/tests/java/test_description.py +128 -0
  574. dev/tests/java/test_main.py +234 -0
  575. dev/tests/jsonld_context/test_main.py +79 -0
  576. dev/tests/opcua/__init__.py +3 -0
  577. dev/tests/opcua/test_main.py +110 -0
  578. dev/tests/our_jsonschema/__init__.py +3 -0
  579. dev/tests/our_jsonschema/test_main.py +232 -0
  580. dev/tests/parse/__init__.py +0 -0
  581. dev/tests/parse/test_parse.py +503 -0
  582. dev/tests/parse/test_retree.py +272 -0
  583. dev/tests/proto/__init__.py +0 -0
  584. dev/tests/proto/test_main.py +112 -0
  585. dev/tests/python/__init__.py +0 -0
  586. dev/tests/python/test_common.py +124 -0
  587. dev/tests/python/test_main.py +126 -0
  588. dev/tests/python/test_xml_playground.py +254 -0
  589. dev/tests/python_protobuf/__init__.py +0 -0
  590. dev/tests/python_protobuf/test_main.py +111 -0
  591. dev/tests/rdf_shacl/__init__.py +0 -0
  592. dev/tests/rdf_shacl/test_common.py +32 -0
  593. dev/tests/rdf_shacl/test_description.py +223 -0
  594. dev/tests/rdf_shacl/test_main.py +194 -0
  595. dev/tests/smoke/__init__.py +0 -0
  596. dev/tests/smoke/test_main.py +83 -0
  597. dev/tests/test_common.py +94 -0
  598. dev/tests/typescript/__init__.py +0 -0
  599. dev/tests/typescript/test_common.py +108 -0
  600. dev/tests/typescript/test_main.py +125 -0
  601. dev/tests/xsd/__init__.py +0 -0
  602. dev/tests/xsd/test_main.py +227 -0
  603. dev/tests/yielding/__init__.py +0 -0
  604. dev/tests/yielding/test_linear.py +558 -0
@@ -0,0 +1,1424 @@
1
+ """Generate the code for conversion from and to Protocol Buffers."""
2
+
3
+ import io
4
+ import os
5
+ import pathlib
6
+ from typing import Tuple, Optional, List, TextIO
7
+
8
+ from icontract import ensure, require
9
+
10
+ import aas_core_codegen.python.common as python_common
11
+ import aas_core_codegen.python.description as python_description
12
+ import aas_core_codegen.python.naming as python_naming
13
+ import aas_core_codegen.python_protobuf
14
+ from aas_core_codegen import intermediate, run, specific_implementations
15
+ from aas_core_codegen.common import (
16
+ Error,
17
+ Stripped,
18
+ assert_never,
19
+ Identifier,
20
+ indent_but_first_line,
21
+ )
22
+ from aas_core_codegen.python.common import INDENT as I, INDENT2 as II, INDENT3 as III
23
+ from aas_core_codegen.python_protobuf import naming as python_protobuf_naming
24
+
25
+ assert aas_core_codegen.python_protobuf.__doc__ == __doc__
26
+
27
+
28
+ # region From-protobuf
29
+
30
+
31
+ def _generate_from_pb_for_enum(
32
+ enum: intermediate.Enumeration, aas_pb_module: python_common.QualifiedModuleName
33
+ ) -> List[Stripped]:
34
+ """
35
+ Generate the code to convert an enum back from a protocol buffer.
36
+
37
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
38
+ """
39
+ literal_to_literal_items = [] # type: List[str]
40
+
41
+ py_enum_name = python_naming.enum_name(enum.name)
42
+ pb_enum_name = python_protobuf_naming.enum_name(enum.name)
43
+
44
+ for literal in enum.literals:
45
+ py_literal_name = python_naming.enum_literal_name(literal.name)
46
+ pb_constant_name = python_protobuf_naming.enum_literal_constant_name(
47
+ enumeration_name=enum.name, literal_name=literal.name
48
+ )
49
+
50
+ literal_to_literal_items.append(
51
+ f"types_pb.{pb_enum_name}.{pb_constant_name}:\n"
52
+ f"{I}types.{py_enum_name}.{py_literal_name}"
53
+ )
54
+
55
+ literal_to_literal_items_joined = ",\n".join(literal_to_literal_items)
56
+
57
+ map_name = python_naming.private_constant_name(
58
+ Identifier(f"{enum.name}_from_pb_map")
59
+ )
60
+
61
+ func_name = python_naming.function_name(Identifier(f"{enum.name}_from_pb"))
62
+
63
+ if len(enum.literals) > 0:
64
+ first_literal = enum.literals[0]
65
+ first_literal_pb_constant = python_protobuf_naming.enum_literal_constant_name(
66
+ enumeration_name=enum.name, literal_name=first_literal.name
67
+ )
68
+ first_literal_py_name = python_naming.enum_literal_name(first_literal.name)
69
+
70
+ docstring = Stripped(
71
+ f"""\
72
+ Parse ``that`` enum back from its Protocol Buffer representation.
73
+
74
+ >>> import {aas_pb_module}.types_pb2 as types_pb
75
+ >>> from {aas_pb_module}.pbization import {func_name}
76
+ >>> {func_name}(
77
+ ... types_pb.{pb_enum_name}.{first_literal_pb_constant}
78
+ ... )
79
+ <{py_enum_name}.{first_literal_py_name}: {first_literal.value!r}>"""
80
+ )
81
+ else:
82
+ docstring = Stripped(
83
+ "Parse ``that`` enum back from its Protocol Buffer representation."
84
+ )
85
+
86
+ quoted_docstring = python_description.docstring(docstring)
87
+
88
+ return [
89
+ Stripped(
90
+ f"""\
91
+ # fmt: off
92
+ {map_name} = {{
93
+ {I}{indent_but_first_line(literal_to_literal_items_joined, I)}
94
+ }} # type: Mapping[types_pb.{pb_enum_name}, types.{py_enum_name}]
95
+ # fmt: on"""
96
+ ),
97
+ Stripped(
98
+ f"""\
99
+ def {func_name}(
100
+ {I}that: types_pb.{pb_enum_name}
101
+ ) -> types.{py_enum_name}:
102
+ {I}{indent_but_first_line(quoted_docstring, I)}
103
+ {I}return {map_name}[that]"""
104
+ ),
105
+ ]
106
+
107
+
108
+ def _determine_function_name_from_pb_for_class(
109
+ cls: intermediate.ClassUnion,
110
+ ) -> Identifier:
111
+ """Determine from-pb function to use to parse the Protocol Buffer to a class."""
112
+ if len(cls.concrete_descendants) > 0:
113
+ convert_func_name = python_naming.function_name(
114
+ Identifier(f"{cls.name}_from_pb_choice")
115
+ )
116
+ else:
117
+ convert_func_name = python_naming.function_name(
118
+ Identifier(f"{cls.name}_from_pb")
119
+ )
120
+
121
+ return convert_func_name
122
+
123
+
124
+ def _generate_concrete_from_pb_for_class(
125
+ cls: intermediate.ConcreteClass, aas_pb_module: python_common.QualifiedModuleName
126
+ ) -> Stripped:
127
+ """
128
+ Generate the function to convert an instance of ``cls`` back from a Protocol Buffer.
129
+
130
+ This function performs explicitly no dispatch and directly converts back properties
131
+ from the Protocol Buffer fields.
132
+
133
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
134
+ """
135
+ constructor_kwargs = [] # type: List[Stripped]
136
+
137
+ assert set(cls.properties_by_name.keys()) == set(
138
+ cls.constructor.arguments_by_name.keys()
139
+ ), "(mristin) We assume that the properties match the constructor arguments."
140
+
141
+ for prop in cls.properties:
142
+ type_anno = intermediate.beneath_optional(prop.type_annotation)
143
+
144
+ is_optional = isinstance(
145
+ prop.type_annotation, intermediate.OptionalTypeAnnotation
146
+ )
147
+
148
+ pb_prop_name = python_protobuf_naming.property_name(prop.name)
149
+ py_prop_name = python_naming.property_name(prop.name)
150
+
151
+ primitive_type = intermediate.try_primitive_type(type_anno)
152
+ if primitive_type is not None:
153
+ if (
154
+ primitive_type is intermediate.PrimitiveType.BOOL
155
+ or primitive_type is intermediate.PrimitiveType.INT
156
+ or primitive_type is intermediate.PrimitiveType.FLOAT
157
+ or primitive_type is intermediate.PrimitiveType.STR
158
+ ):
159
+ constructor_kwargs.append(
160
+ Stripped(
161
+ f"""\
162
+ {py_prop_name}=(
163
+ {I}that.{pb_prop_name}
164
+ {I}if that.HasField({pb_prop_name!r})
165
+ {I}else None
166
+ )"""
167
+ )
168
+ if is_optional
169
+ else Stripped(f"{py_prop_name}=that.{pb_prop_name}")
170
+ )
171
+ elif primitive_type is intermediate.PrimitiveType.BYTEARRAY:
172
+ constructor_kwargs.append(
173
+ Stripped(
174
+ f"""\
175
+ {py_prop_name}=(
176
+ {I}bytearray(that.{pb_prop_name})
177
+ {I}if that.HasField({pb_prop_name!r})
178
+ {I}else None
179
+ )"""
180
+ )
181
+ if is_optional
182
+ else Stripped(f"{py_prop_name}=bytearray(that.{pb_prop_name})")
183
+ )
184
+ else:
185
+ assert_never(primitive_type)
186
+
187
+ else:
188
+ if isinstance(type_anno, intermediate.PrimitiveTypeAnnotation):
189
+ raise AssertionError("Expected to be handled before")
190
+
191
+ elif isinstance(type_anno, intermediate.OurTypeAnnotation):
192
+ if isinstance(type_anno.our_type, intermediate.Enumeration):
193
+ convert_func_name = python_naming.function_name(
194
+ Identifier(f"{type_anno.our_type.name}_from_pb")
195
+ )
196
+
197
+ constructor_kwargs.append(
198
+ Stripped(
199
+ f"""\
200
+ {py_prop_name}=(
201
+ {I}{convert_func_name}(
202
+ {II}that.{pb_prop_name}
203
+ {I})
204
+ {I}if that.HasField({pb_prop_name!r})
205
+ {I}else None
206
+ )"""
207
+ )
208
+ if is_optional
209
+ else Stripped(
210
+ f"""\
211
+ {py_prop_name}={convert_func_name}(
212
+ {I}that.{pb_prop_name}
213
+ )"""
214
+ )
215
+ )
216
+
217
+ elif isinstance(type_anno.our_type, intermediate.ConstrainedPrimitive):
218
+ raise AssertionError("Expected to be handled before")
219
+
220
+ elif isinstance(
221
+ type_anno.our_type,
222
+ (intermediate.AbstractClass, intermediate.ConcreteClass),
223
+ ):
224
+ convert_func_name = _determine_function_name_from_pb_for_class(
225
+ cls=type_anno.our_type
226
+ )
227
+
228
+ constructor_kwargs.append(
229
+ Stripped(
230
+ f"""\
231
+ {py_prop_name}=(
232
+ {I}{convert_func_name}(
233
+ {II}that.{pb_prop_name}
234
+ {I})
235
+ {I}if that.HasField({pb_prop_name!r})
236
+ {I}else None
237
+ )"""
238
+ )
239
+ if is_optional
240
+ else Stripped(
241
+ f"""\
242
+ {py_prop_name}={convert_func_name}(
243
+ {I}that.{pb_prop_name}
244
+ )"""
245
+ )
246
+ )
247
+
248
+ else:
249
+ assert_never(type_anno.our_type)
250
+
251
+ elif isinstance(type_anno, intermediate.ListTypeAnnotation):
252
+ assert isinstance(
253
+ type_anno.items, intermediate.OurTypeAnnotation
254
+ ) and isinstance(
255
+ type_anno.items.our_type,
256
+ (intermediate.AbstractClass, intermediate.ConcreteClass),
257
+ ), (
258
+ f"NOTE (mristin): We expect only lists of classes "
259
+ f"at the moment, but you specified {type_anno}. "
260
+ f"Please contact the developers if you need this feature."
261
+ )
262
+
263
+ convert_func_name = _determine_function_name_from_pb_for_class(
264
+ cls=type_anno.items.our_type
265
+ )
266
+
267
+ # NOTE (mristin):
268
+ # Protocol Buffers 3 do not support ``HasField`` on repeated fields,
269
+ # see: https://github.com/protocolbuffers/protobuf/issues/10489
270
+ #
271
+ # We decide here to interpret empty repeated list containers as None
272
+ # if the model property is optional, and as an empty list if the model
273
+ # property is required.
274
+ constructor_kwargs.append(
275
+ Stripped(
276
+ f"""\
277
+ {py_prop_name}=(
278
+ {I}list(map(
279
+ {II}{convert_func_name},
280
+ {II}that.{pb_prop_name}
281
+ {I}))
282
+ {I}if len(that.{pb_prop_name}) > 0
283
+ {I}else None
284
+ )"""
285
+ )
286
+ if is_optional
287
+ else Stripped(
288
+ f"""\
289
+ {py_prop_name}=list(map(
290
+ {I}{convert_func_name},
291
+ {I}that.{pb_prop_name}
292
+ ))"""
293
+ )
294
+ )
295
+ else:
296
+ assert_never(type_anno)
297
+
298
+ func_name = python_naming.function_name(Identifier(f"{cls.name}_from_pb"))
299
+
300
+ pb_cls_name = python_protobuf_naming.class_name(cls.name)
301
+ py_cls_name = python_naming.class_name(cls.name)
302
+
303
+ constructor_kwargs_joined = ",\n".join(constructor_kwargs)
304
+
305
+ py_var = python_naming.variable_name(cls.name)
306
+ pb_var = python_naming.variable_name(Identifier(cls.name + "_pb"))
307
+
308
+ return Stripped(
309
+ f'''\
310
+ def {func_name}(
311
+ {I}that: types_pb.{pb_cls_name}
312
+ ) -> types.{py_cls_name}:
313
+ {I}"""
314
+ {I}Parse ``that`` Protocol Buffer to an instance of a concrete class.
315
+
316
+ {I}Example usage:
317
+
318
+ {I}.. code-block::
319
+
320
+ {II}import {aas_pb_module}.types_pb2 as types_pb
321
+ {II}from {aas_pb_module}.pbization import {func_name}
322
+
323
+ {II}some_bytes = b'... serialized types_pb.{pb_cls_name} ...'
324
+ {II}{pb_var} = types_pb.{pb_cls_name}()
325
+ {II}{pb_var}.FromString(
326
+ {III}some_bytes
327
+ {II})
328
+
329
+ {II}{py_var} = {func_name}(
330
+ {III}{pb_var}
331
+ {II})
332
+ {II}# Do something with the {py_var}...
333
+
334
+ {I}"""
335
+ {I}return types.{py_cls_name}(
336
+ {II}{indent_but_first_line(constructor_kwargs_joined, II)}
337
+ {I})'''
338
+ )
339
+
340
+
341
+ @require(
342
+ lambda cls: len(cls.concrete_descendants) > 0,
343
+ "Dispatch only possible with concrete descendants.",
344
+ )
345
+ def _generate_from_pb_for_class_choice(
346
+ cls: intermediate.ClassUnion, aas_pb_module: python_common.QualifiedModuleName
347
+ ) -> List[Stripped]:
348
+ """
349
+ Generate the function to parse an instance of ``cls`` where a dispatch is necessary.
350
+
351
+ If the class has concrete descendants, the generated function needs to determine
352
+ the concrete runtime type of the Protocol Buffer, and dispatch it to
353
+ the corresponding concrete from-pb function.
354
+
355
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
356
+ """
357
+ blocks = [] # type: List[Stripped]
358
+
359
+ # region Dispatch map
360
+ items = [] # type: List[Stripped]
361
+
362
+ concrete_classes = [] # type: List[intermediate.ConcreteClass]
363
+ if isinstance(cls, intermediate.ConcreteClass):
364
+ concrete_classes.append(cls)
365
+
366
+ concrete_classes.extend(cls.concrete_descendants)
367
+
368
+ for concrete_cls in concrete_classes:
369
+ pb_which_one_of = python_protobuf_naming.property_name(concrete_cls.name)
370
+
371
+ concrete_from_pb_name = python_naming.function_name(
372
+ Identifier(f"{concrete_cls.name}_from_pb")
373
+ )
374
+
375
+ property_name = python_protobuf_naming.property_name(concrete_cls.name)
376
+
377
+ items.append(
378
+ Stripped(
379
+ f"""\
380
+ {pb_which_one_of!r}:
381
+ {I}lambda that: {concrete_from_pb_name}(
382
+ {II}that.{property_name}
383
+ {I})"""
384
+ )
385
+ )
386
+
387
+ map_name = python_naming.private_constant_name(
388
+ Identifier(f"{cls.name}_from_pb_choice_map")
389
+ )
390
+
391
+ items_joined = ",\n".join(items)
392
+ blocks.append(
393
+ Stripped(
394
+ f"""\
395
+ # fmt: off
396
+ {map_name} = {{
397
+ {I}{indent_but_first_line(items_joined, I)}
398
+ }}
399
+ # fmt: on"""
400
+ )
401
+ )
402
+
403
+ # endregion Dispatch map
404
+
405
+ # region Function
406
+
407
+ pb_cls_name = python_protobuf_naming.choice_class_name(cls.name)
408
+
409
+ func_name = python_naming.function_name(Identifier(f"{cls.name}_from_pb_choice"))
410
+
411
+ py_cls_name = python_naming.class_name(cls.name)
412
+
413
+ pb_var = python_naming.variable_name(Identifier(cls.name + "_choice_pb"))
414
+ py_var = python_naming.variable_name(cls.name)
415
+
416
+ blocks.append(
417
+ Stripped(
418
+ f'''\
419
+ def {func_name}(
420
+ {I}that: types_pb.{pb_cls_name}
421
+ ) -> types.{py_cls_name}:
422
+ {I}"""
423
+ {I}Parse ``that`` Protocol Buffer based on its runtime ``WhichOneof``.
424
+
425
+ {I}Example usage:
426
+
427
+ {I}.. code-block::
428
+
429
+ {II}import {aas_pb_module}.types_pb2 as types_pb
430
+ {II}from {aas_pb_module}.pbization import {func_name}
431
+
432
+ {II}some_bytes = b'... serialized types_pb.{pb_cls_name} ...'
433
+ {II}{pb_var} = types_pb.{pb_cls_name}()
434
+ {II}{pb_var}.FromString(
435
+ {III}some_bytes
436
+ {II})
437
+
438
+ {II}{py_var} = {func_name}(
439
+ {III}{pb_var}
440
+ {II})
441
+ {II}# Do something with the {py_var}...
442
+ {I}"""
443
+ {I}get_concrete_instance_from_pb = (
444
+ {II}{map_name}[
445
+ {III}that.WhichOneof("value")
446
+ {II}]
447
+ {I})
448
+
449
+ {I}result = get_concrete_instance_from_pb(that) # type: ignore
450
+
451
+ {I}assert isinstance(result, types.{py_cls_name})
452
+ {I}return result'''
453
+ )
454
+ )
455
+
456
+ return blocks
457
+
458
+
459
+ def _generate_general_from_pb(
460
+ symbol_table: intermediate.SymbolTable,
461
+ aas_pb_module: python_common.QualifiedModuleName,
462
+ ) -> List[Stripped]:
463
+ """
464
+ Generate the parsing from a Protocol Buffer based on its runtime type.
465
+
466
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
467
+ """
468
+ map_items = [] # type: List[Stripped]
469
+ for cls in symbol_table.classes:
470
+ if len(cls.concrete_descendants) > 0:
471
+ pb_cls_name = python_protobuf_naming.choice_class_name(cls.name)
472
+
473
+ from_pb_func = python_naming.function_name(
474
+ Identifier(f"{cls.name}_from_pb_choice")
475
+ )
476
+ else:
477
+ pb_cls_name = python_protobuf_naming.class_name(cls.name)
478
+
479
+ from_pb_func = python_naming.function_name(
480
+ Identifier(f"{cls.name}_from_pb")
481
+ )
482
+
483
+ map_items.append(
484
+ Stripped(
485
+ f"""\
486
+ types_pb.{pb_cls_name}:
487
+ {I}{from_pb_func}"""
488
+ )
489
+ )
490
+
491
+ map_items_joined = ",\n".join(map_items)
492
+
493
+ # NOTE (mristin):
494
+ # We had to put this message outside since black formatter struggled with it. This
495
+ # is most probably a bug in the black formatter.
496
+ key_class_not_found_message = '''\
497
+ f"We do not know how to parse the protocol buffer "
498
+ f"of type {that.__class__} into a model instance."'''
499
+
500
+ first_cls_name = symbol_table.concrete_classes[0].name
501
+ pb_first_cls_name = python_protobuf_naming.class_name(first_cls_name)
502
+
503
+ return [
504
+ Stripped(
505
+ f"""\
506
+ # fmt: off
507
+ _FROM_PB_MAP = {{
508
+ {I}{indent_but_first_line(map_items_joined, I)}
509
+ }}
510
+ # fmt: on"""
511
+ ),
512
+ Stripped(
513
+ f'''\
514
+ def from_pb(
515
+ {I}that: google.protobuf.message.Message
516
+ ) -> types.Class:
517
+ {I}"""
518
+ {I}Parse ``that`` Protocol Buffer into a model instance.
519
+
520
+ {I}The concrete parsing is determined based on the runtime type of ``that``
521
+ {I}Protocol Buffer. It is assumed that ``that`` is an instance of a message
522
+ {I}coming from the Protocol Buffer definitions corresponding to the meta-model.
523
+
524
+ {I}Example usage:
525
+
526
+ {I}.. code-block::
527
+
528
+ {II}import {aas_pb_module}.types_pb2 as types_pb
529
+ {II}from {aas_pb_module}.pbization import from_pb
530
+
531
+ {II}some_bytes = b'... serialized types_pb.{pb_first_cls_name} ...'
532
+ {II}instance_pb = types_pb.{pb_first_cls_name}()
533
+ {II}instance_pb.FromString(
534
+ {III}some_bytes
535
+ {II})
536
+
537
+ {II}instance = from_pb(
538
+ {III}instance_pb
539
+ {II})
540
+ {II}# Do something with the instance...
541
+ {I}"""
542
+ {I}from_pb_func = _FROM_PB_MAP.get(that.__class__, None)
543
+
544
+ {I}if from_pb_func is None:
545
+ {II}raise ValueError(
546
+ {III}{indent_but_first_line(key_class_not_found_message, III)}
547
+ {II})
548
+
549
+ {I}result = from_pb_func(that) # type: ignore
550
+ {I}assert isinstance(result, types.Class)
551
+ {I}return result'''
552
+ ),
553
+ ]
554
+
555
+
556
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
557
+ def _generate_from_pb(
558
+ symbol_table: intermediate.SymbolTable,
559
+ aas_pb_module: python_common.QualifiedModuleName,
560
+ ) -> Tuple[Optional[List[Stripped]], Optional[List[Error]]]:
561
+ """
562
+ Generate all the code for the conversion from protocol buffers.
563
+
564
+ The ``aas_module`` indicates the fully-qualified name of the base SDK module.
565
+
566
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
567
+ """
568
+ blocks = [] # type: List[Stripped]
569
+ errors = [] # type: List[Error]
570
+
571
+ for our_type in symbol_table.our_types:
572
+ if isinstance(our_type, intermediate.Enumeration):
573
+ blocks.extend(
574
+ _generate_from_pb_for_enum(enum=our_type, aas_pb_module=aas_pb_module)
575
+ )
576
+
577
+ elif isinstance(our_type, intermediate.ConstrainedPrimitive):
578
+ # NOTE (mristin):
579
+ # We do not represent constrained primitives in Protocol Buffer types.
580
+ pass
581
+
582
+ elif isinstance(
583
+ our_type, (intermediate.AbstractClass, intermediate.ConcreteClass)
584
+ ):
585
+ if len(our_type.concrete_descendants) > 0:
586
+ blocks.extend(
587
+ _generate_from_pb_for_class_choice(
588
+ cls=our_type, aas_pb_module=aas_pb_module
589
+ )
590
+ )
591
+
592
+ if isinstance(our_type, intermediate.ConcreteClass):
593
+ blocks.append(
594
+ _generate_concrete_from_pb_for_class(
595
+ cls=our_type, aas_pb_module=aas_pb_module
596
+ )
597
+ )
598
+
599
+ else:
600
+ assert_never(our_type)
601
+
602
+ blocks.extend(
603
+ _generate_general_from_pb(
604
+ symbol_table=symbol_table, aas_pb_module=aas_pb_module
605
+ )
606
+ )
607
+
608
+ if len(errors) > 0:
609
+ return None, errors
610
+
611
+ return blocks, None
612
+
613
+
614
+ # endregion
615
+
616
+
617
+ # region To-protobuf
618
+
619
+
620
+ def _generate_partial_visitor(symbol_table: intermediate.SymbolTable) -> Stripped:
621
+ """Generate the transformer where all methods return assertion errors."""
622
+ methods = [] # type: List[Stripped]
623
+
624
+ for cls in symbol_table.concrete_classes:
625
+ method_name = python_naming.method_name(
626
+ Identifier(f"visit_{cls.name}_with_context")
627
+ )
628
+
629
+ cls_name = python_naming.class_name(cls.name)
630
+
631
+ methods.append(
632
+ Stripped(
633
+ f"""\
634
+ def {method_name}(
635
+ {I}self,
636
+ {I}that: types.{cls_name},
637
+ {I}context: T
638
+ ) -> None:
639
+ {I}raise AssertionError(f"Unexpected visitation of {{that.__class__}}")"""
640
+ )
641
+ )
642
+ body = "\n\n".join(methods)
643
+ return Stripped(
644
+ f'''\
645
+ class _PartialVisitorWithContext(types.AbstractVisitorWithContext[T]):
646
+ {I}"""
647
+ {I}Visit instances in context with double-dispatch.
648
+
649
+ {I}This class is meant to be inherited from. If you do not override a method,
650
+ {I}it will raise an exception. This is a partial visitor, meaning that some
651
+ {I}visits are unexpected by design.
652
+ {I}"""
653
+ {I}# pylint: disable=missing-docstring
654
+
655
+ {I}{indent_but_first_line(body, I)}'''
656
+ )
657
+
658
+
659
+ def _generate_to_pb_for_enum(
660
+ enum: intermediate.Enumeration,
661
+ aas_module: python_common.QualifiedModuleName,
662
+ aas_pb_module: python_common.QualifiedModuleName,
663
+ ) -> List[Stripped]:
664
+ """
665
+ Generate the code to convert an enum to a protocol buffer.
666
+
667
+ The ``aas_module`` indicates the fully-qualified name of the base SDK module.
668
+
669
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
670
+ """
671
+ literal_to_literal_items = [] # type: List[str]
672
+
673
+ py_enum_name = python_naming.enum_name(enum.name)
674
+ pb_enum_name = python_protobuf_naming.enum_name(enum.name)
675
+
676
+ for literal in enum.literals:
677
+ py_literal_name = python_naming.enum_literal_name(literal.name)
678
+ pb_constant_name = python_protobuf_naming.enum_literal_constant_name(
679
+ enumeration_name=enum.name, literal_name=literal.name
680
+ )
681
+
682
+ literal_to_literal_items.append(
683
+ f"types.{py_enum_name}.{py_literal_name}:\n"
684
+ f"{I}types_pb.{pb_enum_name}.{pb_constant_name}"
685
+ )
686
+
687
+ literal_to_literal_items_joined = ",\n".join(literal_to_literal_items)
688
+
689
+ map_name = python_naming.private_constant_name(Identifier(f"{enum.name}_to_pb_map"))
690
+
691
+ func_name = python_naming.function_name(Identifier(f"{enum.name}_to_pb"))
692
+
693
+ if len(enum.literals) > 0:
694
+ first_literal = enum.literals[0]
695
+ first_literal_py_name = python_naming.enum_literal_name(first_literal.name)
696
+
697
+ docstring = Stripped(
698
+ f"""\
699
+ Convert ``that`` enum to its Protocol Buffer representation.
700
+
701
+ >>> from {aas_pb_module}.pbization import {func_name}
702
+ >>> import {aas_module}.types as types
703
+ >>> {func_name}(
704
+ ... types.{py_enum_name}.{first_literal_py_name}
705
+ ... )
706
+ 1"""
707
+ )
708
+ else:
709
+ docstring = Stripped(
710
+ "Convert ``that`` enum to its Protocol Buffer representation."
711
+ )
712
+
713
+ quoted_docstring = python_description.docstring(docstring)
714
+
715
+ return [
716
+ Stripped(
717
+ f"""\
718
+ # fmt: off
719
+ {map_name} = {{
720
+ {I}{indent_but_first_line(literal_to_literal_items_joined, I)}
721
+ }} # type: Mapping[types.{py_enum_name}, types_pb.{pb_enum_name}]
722
+ # fmt: on"""
723
+ ),
724
+ Stripped(
725
+ f"""\
726
+ def {func_name}(
727
+ {I}that: types.{py_enum_name}
728
+ ) -> types_pb.{pb_enum_name}:
729
+ {I}{indent_but_first_line(quoted_docstring, I)}
730
+ {I}return {map_name}[that]"""
731
+ ),
732
+ ]
733
+
734
+
735
+ def _generate_concrete_to_pb_for_class(
736
+ cls: intermediate.ConcreteClass,
737
+ aas_module: python_common.QualifiedModuleName,
738
+ aas_pb_module: python_common.QualifiedModuleName,
739
+ ) -> Stripped:
740
+ """
741
+ Generate the code to convert an instance to a protocol buffer without dispatch.
742
+
743
+ There are two situations when this generated function will be called:
744
+
745
+ 1) ``cls`` is a concrete class without descendants (no dispatch necessary), and
746
+ 2) ``cls`` is a concrete class with descendants. In this case, we will dispatch
747
+ to this generated function if the runtime type equals exactly ``cls``.
748
+
749
+ The ``aas_module`` indicates the fully-qualified name of the base SDK module.
750
+
751
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
752
+ """
753
+ set_blocks = [] # type: List[Stripped]
754
+
755
+ for prop in cls.properties:
756
+ type_anno = intermediate.beneath_optional(prop.type_annotation)
757
+
758
+ py_prop_name = python_naming.property_name(prop.name)
759
+ pb_prop_name = python_protobuf_naming.property_name(prop.name)
760
+
761
+ set_block: Stripped
762
+
763
+ primitive_type = intermediate.try_primitive_type(type_anno)
764
+ if primitive_type is not None:
765
+ if (
766
+ primitive_type is intermediate.PrimitiveType.BOOL
767
+ or primitive_type is intermediate.PrimitiveType.INT
768
+ or primitive_type is intermediate.PrimitiveType.FLOAT
769
+ or primitive_type is intermediate.PrimitiveType.STR
770
+ ):
771
+ set_block = Stripped(f"target.{pb_prop_name} = that.{py_prop_name}")
772
+
773
+ elif primitive_type is intermediate.PrimitiveType.BYTEARRAY:
774
+ set_block = Stripped(
775
+ f"target.{pb_prop_name} = bytes(that.{py_prop_name})"
776
+ )
777
+
778
+ else:
779
+ assert_never(primitive_type)
780
+ else:
781
+ if isinstance(type_anno, intermediate.PrimitiveTypeAnnotation):
782
+ raise AssertionError("Expected to be handled before")
783
+
784
+ elif isinstance(type_anno, intermediate.OurTypeAnnotation):
785
+ if isinstance(type_anno.our_type, intermediate.Enumeration):
786
+ to_pb_func_for_enum = python_naming.function_name(
787
+ Identifier(f"{type_anno.our_type.name}_to_pb")
788
+ )
789
+
790
+ set_block = Stripped(
791
+ f"""\
792
+ target.{pb_prop_name} = {to_pb_func_for_enum}(
793
+ {I}that.{py_prop_name}
794
+ )"""
795
+ )
796
+
797
+ elif isinstance(type_anno.our_type, intermediate.ConstrainedPrimitive):
798
+ raise AssertionError("Expected to be handled before")
799
+
800
+ elif isinstance(
801
+ type_anno.our_type,
802
+ (intermediate.AbstractClass, intermediate.ConcreteClass),
803
+ ):
804
+ if len(type_anno.our_type.concrete_descendants) > 0:
805
+ to_pb_choice_func = python_naming.function_name(
806
+ Identifier(f"{type_anno.our_type.name}_to_pb_choice")
807
+ )
808
+
809
+ set_block = Stripped(
810
+ f"""\
811
+ {to_pb_choice_func}(
812
+ {I}that.{py_prop_name},
813
+ {I}target.{pb_prop_name}
814
+ )"""
815
+ )
816
+ else:
817
+ to_pb_func = python_naming.function_name(
818
+ Identifier(f"{type_anno.our_type.name}_to_pb")
819
+ )
820
+
821
+ set_block = Stripped(
822
+ f"""\
823
+ # We clear so that the field is set even if all the properties are None.
824
+ target.{pb_prop_name}.Clear()
825
+
826
+ {to_pb_func}(
827
+ {I}that.{py_prop_name},
828
+ {I}target.{pb_prop_name}
829
+ )"""
830
+ )
831
+
832
+ else:
833
+ assert_never(type_anno.our_type)
834
+
835
+ elif isinstance(type_anno, intermediate.ListTypeAnnotation):
836
+ assert isinstance(
837
+ type_anno.items, intermediate.OurTypeAnnotation
838
+ ) and isinstance(
839
+ type_anno.items.our_type,
840
+ (intermediate.AbstractClass, intermediate.ConcreteClass),
841
+ ), (
842
+ f"NOTE (mristin): We expect only lists of classes "
843
+ f"at the moment, but you specified {type_anno}. "
844
+ f"Please contact the developers if you need this feature."
845
+ )
846
+
847
+ if len(type_anno.items.our_type.concrete_descendants) > 0:
848
+ to_pb_func_for_items_cls = python_naming.function_name(
849
+ Identifier(f"{type_anno.items.our_type.name}_to_pb_choice")
850
+ )
851
+ else:
852
+ to_pb_func_for_items_cls = python_naming.function_name(
853
+ Identifier(f"{type_anno.items.our_type.name}_to_pb")
854
+ )
855
+
856
+ item_var = python_naming.variable_name(Identifier(f"{prop.name}_item"))
857
+ set_block = Stripped(
858
+ f"""\
859
+ for {item_var} in that.{py_prop_name}:
860
+ {I}{item_var}_pb = target.{pb_prop_name}.add()
861
+ {I}{to_pb_func_for_items_cls}(
862
+ {II}{item_var},
863
+ {II}{item_var}_pb)"""
864
+ )
865
+
866
+ else:
867
+ assert_never(type_anno)
868
+
869
+ if isinstance(prop.type_annotation, intermediate.OptionalTypeAnnotation):
870
+ set_block = Stripped(
871
+ f"""\
872
+ if that.{py_prop_name} is not None:
873
+ {I}{indent_but_first_line(set_block, I)}"""
874
+ )
875
+
876
+ set_blocks.append(set_block)
877
+
878
+ func_name = python_naming.function_name(Identifier(f"{cls.name}_to_pb"))
879
+
880
+ py_cls_name = python_naming.class_name(cls.name)
881
+ pb_cls_name = python_protobuf_naming.class_name(cls.name)
882
+
883
+ set_blocks_joined = "\n\n".join(set_blocks)
884
+
885
+ pb_var = python_naming.variable_name(Identifier(cls.name + "_pb"))
886
+ py_var = python_naming.variable_name(cls.name)
887
+
888
+ return Stripped(
889
+ f'''\
890
+ def {func_name}(
891
+ {I}that: types.{py_cls_name},
892
+ {I}target: types_pb.{pb_cls_name}
893
+ ) -> None:
894
+ {I}"""
895
+ {I}Set fields in ``target`` based on ``that`` instance.
896
+
897
+ {I}Example usage:
898
+
899
+ {I}.. code-block::
900
+
901
+ {II}import {aas_module}.types as types
902
+
903
+ {II}import {aas_pb_module}.types_pb2 as types_pb
904
+ {II}from {aas_pb_module}.pbization import {func_name}
905
+
906
+ {II}{py_var} = types.{py_cls_name}(
907
+ {III}... # some constructor arguments
908
+ {II})
909
+
910
+ {II}{pb_var} = types_pb.{pb_cls_name}()
911
+ {II}{func_name}(
912
+ {III}{py_var},
913
+ {III}{pb_var}
914
+ {II})
915
+
916
+ {II}some_bytes = {pb_var}.SerializeToString()
917
+ {II}# Do something with some_bytes. For example, transfer them
918
+ {II}# over the wire.
919
+ {I}"""
920
+ {I}{indent_but_first_line(set_blocks_joined, I)}'''
921
+ )
922
+
923
+
924
+ @require(
925
+ lambda cls: len(cls.concrete_descendants) > 0,
926
+ "Dispatch needs concrete descendants.",
927
+ )
928
+ def _generate_to_pb_choice(
929
+ cls: intermediate.ClassUnion,
930
+ aas_module: python_common.QualifiedModuleName,
931
+ aas_pb_module: python_common.QualifiedModuleName,
932
+ ) -> List[Stripped]:
933
+ """
934
+ Generate the code to dispatch the serialization to a concrete serializer.
935
+
936
+ The ``aas_module`` indicates the fully-qualified name of the base SDK module.
937
+
938
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
939
+ """
940
+ blocks = [] # type: List[Stripped]
941
+
942
+ pb_choice_cls_name = python_protobuf_naming.choice_class_name(cls.name)
943
+
944
+ # region Visitor
945
+
946
+ methods = [] # type: List[Stripped]
947
+
948
+ concrete_classes = [] # type: List[intermediate.ConcreteClass]
949
+ if isinstance(cls, intermediate.ConcreteClass):
950
+ concrete_classes.append(cls)
951
+
952
+ concrete_classes.extend(cls.concrete_descendants)
953
+
954
+ for concrete_cls in concrete_classes:
955
+ py_concrete_cls_name = python_naming.class_name(concrete_cls.name)
956
+ pb_property = python_protobuf_naming.property_name(concrete_cls.name)
957
+
958
+ conversion_func = python_naming.function_name(
959
+ Identifier(f"{concrete_cls.name}_to_pb")
960
+ )
961
+
962
+ method_name = python_naming.method_name(
963
+ Identifier(f"visit_{concrete_cls.name}_with_context")
964
+ )
965
+
966
+ methods.append(
967
+ Stripped(
968
+ f'''\
969
+ def {method_name}(
970
+ {I}self,
971
+ {I}that: types.{py_concrete_cls_name},
972
+ {I}context: types_pb.{pb_choice_cls_name}
973
+ ) -> None:
974
+ {I}"""
975
+ {I}Set the fields of ``context.{pb_property}``
976
+ {I}according to ``that`` instance.
977
+ {I}"""
978
+ {I}{conversion_func}(
979
+ {II}that,
980
+ {II}context.{pb_property}
981
+ {I})'''
982
+ )
983
+ )
984
+
985
+ visitor_class_name = python_naming.private_class_name(
986
+ Identifier(f"{cls.name}_to_pb_choice")
987
+ )
988
+ body = "\n\n".join(methods)
989
+ blocks.append(
990
+ Stripped(
991
+ f'''\
992
+ class {visitor_class_name}(
993
+ {I}_PartialVisitorWithContext[
994
+ {II}types_pb.{pb_choice_cls_name}
995
+ {I}]
996
+ ):
997
+ {I}"""Set the fields of the corresponding one-of value."""
998
+ {I}{indent_but_first_line(body, I)}'''
999
+ )
1000
+ )
1001
+
1002
+ visitor_name = python_naming.private_constant_name(
1003
+ Identifier(f"{cls.name}_to_pb_choice")
1004
+ )
1005
+ blocks.append(Stripped(f"{visitor_name} = {visitor_class_name}()"))
1006
+
1007
+ # endregion Visitor
1008
+
1009
+ func_name = python_naming.function_name(Identifier(f"{cls.name}_to_pb_choice"))
1010
+
1011
+ py_cls_name = python_naming.class_name(cls.name)
1012
+
1013
+ py_concrete_descendant_cls_name = python_naming.class_name(
1014
+ cls.concrete_descendants[0].name
1015
+ )
1016
+
1017
+ py_var = python_naming.variable_name(cls.name)
1018
+ pb_var = python_naming.variable_name(Identifier(cls.name + "_choice_pb"))
1019
+
1020
+ blocks.append(
1021
+ Stripped(
1022
+ f'''\
1023
+ def {func_name}(
1024
+ {I}that: types.{py_cls_name},
1025
+ {I}target: types_pb.{pb_choice_cls_name}
1026
+ ) -> None:
1027
+ {I}"""
1028
+ {I}Set the chosen value in ``target`` based on ``that`` instance.
1029
+
1030
+ {I}The chosen value in ``target`` is determined based on the runtime type of ``that``
1031
+ {I}instance. All the fields of the value are recursively set according to ``that``
1032
+ {I}instance.
1033
+
1034
+ {I}Example usage:
1035
+
1036
+ {I}.. code-block::
1037
+
1038
+ {II}import {aas_module}.types as types
1039
+
1040
+ {II}import {aas_pb_module}.types_pb2 as types_pb
1041
+ {II}from {aas_pb_module}.pbization import {func_name}
1042
+
1043
+ {II}{py_var} = types.{py_concrete_descendant_cls_name}(
1044
+ {III}... # some constructor arguments
1045
+ {II})
1046
+
1047
+ {II}{pb_var} = types_pb.{pb_choice_cls_name}()
1048
+ {II}{func_name}(
1049
+ {III}{py_var},
1050
+ {III}{pb_var}
1051
+ {II})
1052
+
1053
+ {II}some_bytes = {pb_var}.SerializeToString()
1054
+ {II}# Do something with some_bytes. For example, transfer them
1055
+ {II}# over the wire.
1056
+
1057
+ {I}"""
1058
+ {I}{visitor_name}.visit_with_context(
1059
+ {II}that,
1060
+ {II}target
1061
+ {I})'''
1062
+ )
1063
+ )
1064
+
1065
+ return blocks
1066
+
1067
+
1068
+ @require(
1069
+ lambda symbol_table: len(symbol_table.concrete_classes) > 0,
1070
+ "At least one concrete class in the meta-model expected if you generate "
1071
+ "a general to-pb function",
1072
+ )
1073
+ def _generate_general_to_pb(
1074
+ symbol_table: intermediate.SymbolTable,
1075
+ aas_module: python_common.QualifiedModuleName,
1076
+ aas_pb_module: python_common.QualifiedModuleName,
1077
+ ) -> List[Stripped]:
1078
+ """
1079
+ Generate a dispatch to the concrete to-pb function.
1080
+
1081
+ The ``aas_module`` indicates the fully-qualified name of the base SDK module.
1082
+
1083
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
1084
+ """
1085
+ methods = [] # type: List[Stripped]
1086
+
1087
+ for cls in symbol_table.concrete_classes:
1088
+ if len(cls.concrete_descendants) > 0:
1089
+ conversion_func_name = python_naming.function_name(
1090
+ Identifier(f"{cls.name}_to_pb_choice")
1091
+ )
1092
+ pb_cls_name = python_protobuf_naming.choice_class_name(cls.name)
1093
+ else:
1094
+ conversion_func_name = python_naming.function_name(
1095
+ Identifier(f"{cls.name}_to_pb")
1096
+ )
1097
+ pb_cls_name = python_protobuf_naming.class_name(cls.name)
1098
+
1099
+ method_name = python_naming.function_name(Identifier(f"transform_{cls.name}"))
1100
+
1101
+ py_cls_name = python_naming.class_name(cls.name)
1102
+
1103
+ methods.append(
1104
+ Stripped(
1105
+ f'''\
1106
+ def {method_name}(
1107
+ {I}self,
1108
+ {I}that: types.{py_cls_name}
1109
+ ) -> google.protobuf.message.Message:
1110
+ {I}"""
1111
+ {I}Convert ``that`` instance
1112
+ {I}to a :py:class:`types_pb.{pb_cls_name}`.
1113
+ {I}"""
1114
+ {I}result = types_pb.{pb_cls_name}()
1115
+ {I}{conversion_func_name}(that, result)
1116
+ {I}return result'''
1117
+ )
1118
+ )
1119
+
1120
+ body = "\n\n".join(methods)
1121
+
1122
+ first_cls = symbol_table.concrete_classes[0]
1123
+ py_first_cls_name = python_naming.class_name(first_cls.name)
1124
+
1125
+ return [
1126
+ Stripped(
1127
+ f'''\
1128
+ class _ToPbTransformer(
1129
+ {I}types.AbstractTransformer[google.protobuf.message.Message]
1130
+ ):
1131
+ {I}"""
1132
+ {I}Dispatch to-pb conversion to the concrete functions.
1133
+
1134
+ {I}The classes with descendants (i.e., subtypes) are always going to be converted
1135
+ {I}to their concrete Protocol Buffer instead of the choice (union) Protocol Buffer
1136
+ {I}class. We made this decision with the compactness of messages in mind.
1137
+ {I}"""
1138
+ {I}{indent_but_first_line(body, I)}'''
1139
+ ),
1140
+ Stripped("_TO_PB_TRANSFORMER = _ToPbTransformer()"),
1141
+ Stripped(
1142
+ f'''\
1143
+ def to_pb(
1144
+ {I}that: types.Class,
1145
+ ) -> google.protobuf.message.Message:
1146
+ {I}"""
1147
+ {I}Dispatch to-pb conversion to the concrete functions.
1148
+
1149
+ {I}The classes with descendants (i.e., subtypes) are always going to be converted
1150
+ {I}to their concrete Protocol Buffer message type instead of the choice (union) type.
1151
+ {I}We made this decision with the compactness of messages in mind as choice types
1152
+ {I}would occupy a tiny bit more space.
1153
+
1154
+ {I}Example usage:
1155
+
1156
+ {I}.. code-block::
1157
+
1158
+ {II}import {aas_module}.types as types
1159
+
1160
+ {II}from {aas_pb_module}.pbization import to_pb
1161
+
1162
+ {II}instance = types.{py_first_cls_name}(
1163
+ {III}... # some constructor arguments
1164
+ {II})
1165
+
1166
+ {II}instance_pb = to_pb(
1167
+ {III}instance
1168
+ {II})
1169
+
1170
+ {II}some_bytes = instance_pb.SerializeToString()
1171
+ {II}# Do something with some_bytes. For example, transfer them
1172
+ {II}# over the wire.
1173
+ {I}"""
1174
+ {I}return _TO_PB_TRANSFORMER.transform(that)'''
1175
+ ),
1176
+ ]
1177
+
1178
+
1179
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
1180
+ def _generate_to_pb(
1181
+ symbol_table: intermediate.SymbolTable,
1182
+ aas_module: python_common.QualifiedModuleName,
1183
+ aas_pb_module: python_common.QualifiedModuleName,
1184
+ ) -> Tuple[Optional[List[Stripped]], Optional[List[Error]]]:
1185
+ """
1186
+ Generate all the code for the conversion to protocol buffers.
1187
+
1188
+ The ``aas_module`` indicates the fully-qualified name of the base SDK module.
1189
+
1190
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
1191
+ """
1192
+ blocks = [
1193
+ Stripped('T = TypeVar("T")'),
1194
+ _generate_partial_visitor(symbol_table=symbol_table),
1195
+ ] # type: List[Stripped]
1196
+ errors = [] # type: List[Error]
1197
+
1198
+ for our_type in symbol_table.our_types:
1199
+ if isinstance(our_type, intermediate.Enumeration):
1200
+ enum_blocks = _generate_to_pb_for_enum(
1201
+ enum=our_type, aas_module=aas_module, aas_pb_module=aas_pb_module
1202
+ )
1203
+ blocks.extend(enum_blocks)
1204
+ elif isinstance(our_type, intermediate.ConstrainedPrimitive):
1205
+ # NOTE (mristin):
1206
+ # We do not represent constrained primitives in Python types.
1207
+ pass
1208
+ elif isinstance(
1209
+ our_type, (intermediate.AbstractClass, intermediate.ConcreteClass)
1210
+ ):
1211
+ if len(our_type.concrete_descendants) > 0:
1212
+ blocks.extend(
1213
+ _generate_to_pb_choice(
1214
+ cls=our_type, aas_module=aas_module, aas_pb_module=aas_pb_module
1215
+ )
1216
+ )
1217
+
1218
+ if isinstance(our_type, intermediate.ConcreteClass):
1219
+ blocks.append(
1220
+ _generate_concrete_to_pb_for_class(
1221
+ cls=our_type, aas_module=aas_module, aas_pb_module=aas_pb_module
1222
+ )
1223
+ )
1224
+ else:
1225
+ assert_never(our_type)
1226
+
1227
+ blocks.extend(
1228
+ _generate_general_to_pb(
1229
+ symbol_table=symbol_table,
1230
+ aas_module=aas_module,
1231
+ aas_pb_module=aas_pb_module,
1232
+ )
1233
+ )
1234
+
1235
+ if len(errors) > 0:
1236
+ return None, errors
1237
+
1238
+ return blocks, None
1239
+
1240
+
1241
+ # endregion
1242
+
1243
+ _THIS_PATH = pathlib.Path(os.path.realpath(__file__))
1244
+
1245
+
1246
+ @ensure(lambda result: not (result[0] is not None) or (result[0].endswith("\n")))
1247
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
1248
+ def _generate(
1249
+ symbol_table: intermediate.SymbolTable,
1250
+ spec_impls: specific_implementations.SpecificImplementations,
1251
+ ) -> Tuple[Optional[str], Optional[List[Error]]]:
1252
+ """
1253
+ Generate the content of the pbization module.
1254
+
1255
+ The ``aas_module`` indicates the fully-qualified name of the base SDK module.
1256
+
1257
+ The ``aas_pb_module`` indicates the fully-qualified name of this base module.
1258
+ """
1259
+ aas_module_key = specific_implementations.ImplementationKey(
1260
+ "base_qualified_module_name.txt"
1261
+ )
1262
+
1263
+ aas_module_text = spec_impls.get(aas_module_key, None)
1264
+ if aas_module_text is None:
1265
+ return None, [
1266
+ Error(
1267
+ None,
1268
+ f"The implementation snippet for the base qualified module name "
1269
+ f"is missing: {aas_module_key}",
1270
+ )
1271
+ ]
1272
+
1273
+ if not python_common.QUALIFIED_MODULE_NAME_RE.fullmatch(aas_module_text):
1274
+ return None, [
1275
+ Error(
1276
+ None,
1277
+ f"The text from the snippet {aas_module_key} "
1278
+ f"is not a valid qualified module name: {aas_module_text!r}\n",
1279
+ )
1280
+ ]
1281
+
1282
+ aas_module = python_common.QualifiedModuleName(aas_module_text)
1283
+
1284
+ aas_pb_module_key = specific_implementations.ImplementationKey(
1285
+ "qualified_module_name_for_protobuf_library.txt"
1286
+ )
1287
+
1288
+ aas_pb_module_text = spec_impls.get(aas_pb_module_key, None)
1289
+ if aas_pb_module_text is None:
1290
+ return None, [
1291
+ Error(
1292
+ None,
1293
+ f"The implementation snippet for the qualified name of the protobuf "
1294
+ f"library is missing: {aas_pb_module_key}",
1295
+ )
1296
+ ]
1297
+
1298
+ if not python_common.QUALIFIED_MODULE_NAME_RE.fullmatch(aas_pb_module_text):
1299
+ return None, [
1300
+ Error(
1301
+ None,
1302
+ f"The text from the snippet {aas_pb_module_key} "
1303
+ f"is not a valid qualified module name: {aas_pb_module_text!r}\n",
1304
+ )
1305
+ ]
1306
+
1307
+ aas_pb_module = python_common.QualifiedModuleName(aas_pb_module_text)
1308
+
1309
+ warning = Stripped(
1310
+ f"""\
1311
+ # Automatically generated with {_THIS_PATH.parent.name}/{_THIS_PATH.name}.
1312
+ # Do NOT edit or append."""
1313
+ )
1314
+
1315
+ blocks = [
1316
+ warning,
1317
+ Stripped('"""Convert instances from and to Protocol Buffers."""'),
1318
+ Stripped(
1319
+ f"""\
1320
+ from typing import Mapping, TypeVar
1321
+
1322
+ import google.protobuf.message
1323
+
1324
+ from {aas_module} import types
1325
+ import {aas_pb_module}.types_pb2 as types_pb""",
1326
+ ),
1327
+ Stripped("# region From Protocol Buffers"),
1328
+ ] # type: List[Stripped]
1329
+
1330
+ errors = [] # type: List[Error]
1331
+
1332
+ from_pb_blocks, from_pb_errors = _generate_from_pb(
1333
+ symbol_table=symbol_table, aas_pb_module=aas_pb_module
1334
+ )
1335
+ if from_pb_errors is not None:
1336
+ errors.append(
1337
+ Error(
1338
+ None,
1339
+ "Failed to generate one or more from-protobuf conversion",
1340
+ underlying=errors,
1341
+ )
1342
+ )
1343
+ else:
1344
+ assert from_pb_blocks is not None
1345
+ blocks.extend(from_pb_blocks)
1346
+
1347
+ blocks.extend(
1348
+ [
1349
+ Stripped("# endregion From Protocol Buffers"),
1350
+ Stripped("# region To Protocol Buffers"),
1351
+ ]
1352
+ )
1353
+
1354
+ to_pb_blocks, to_pb_errors = _generate_to_pb(
1355
+ symbol_table=symbol_table, aas_module=aas_module, aas_pb_module=aas_pb_module
1356
+ )
1357
+ if to_pb_errors is not None:
1358
+ errors.append(
1359
+ Error(
1360
+ None,
1361
+ "Failed to generate one or more to-protobuf conversion",
1362
+ underlying=errors,
1363
+ )
1364
+ )
1365
+ else:
1366
+ assert to_pb_blocks is not None
1367
+ blocks.extend(to_pb_blocks)
1368
+
1369
+ blocks.append(
1370
+ Stripped("# endregion To Protocol Buffers"),
1371
+ )
1372
+
1373
+ blocks.append(warning)
1374
+
1375
+ out = io.StringIO()
1376
+ for i, block in enumerate(blocks):
1377
+ if i > 0:
1378
+ out.write("\n\n\n")
1379
+
1380
+ out.write(block)
1381
+
1382
+ out.write("\n")
1383
+
1384
+ return out.getvalue(), None
1385
+
1386
+
1387
+ def execute(
1388
+ context: run.Context,
1389
+ stdout: TextIO,
1390
+ stderr: TextIO,
1391
+ ) -> int:
1392
+ """
1393
+ Execute the generation with the given parameters.
1394
+
1395
+ Return the error code, or 0 if no errors.
1396
+ """
1397
+ code, errors = _generate(
1398
+ symbol_table=context.symbol_table, spec_impls=context.spec_impls
1399
+ )
1400
+ if errors is not None:
1401
+ run.write_error_report(
1402
+ message=f"Failed to generate the Python-Protobuf library "
1403
+ f"based on {context.model_path}",
1404
+ errors=[context.lineno_columner.error_message(error) for error in errors],
1405
+ stderr=stderr,
1406
+ )
1407
+ return 1
1408
+
1409
+ assert code is not None
1410
+
1411
+ pth = context.output_dir / "pbization.py"
1412
+ try:
1413
+ pth.write_text(code, encoding="utf-8")
1414
+ except Exception as exception:
1415
+ run.write_error_report(
1416
+ message=f"Failed to write the Python-Protobuf library to {pth}",
1417
+ errors=[str(exception)],
1418
+ stderr=stderr,
1419
+ )
1420
+ return 1
1421
+
1422
+ stdout.write(f"Code generated to: {context.output_dir}\n")
1423
+
1424
+ return 0