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,1513 @@
1
+ """Generate the invariant verifiers from the intermediate representation."""
2
+
3
+ import io
4
+ import textwrap
5
+ from typing import (
6
+ Tuple,
7
+ Optional,
8
+ List,
9
+ Sequence,
10
+ Mapping,
11
+ Union,
12
+ )
13
+
14
+ from icontract import ensure, require
15
+
16
+ from aas_core_codegen import intermediate, specific_implementations
17
+ from aas_core_codegen.common import (
18
+ Error,
19
+ Stripped,
20
+ assert_never,
21
+ Identifier,
22
+ indent_but_first_line,
23
+ wrap_text_into_lines,
24
+ assert_union_without_excluded,
25
+ )
26
+ from aas_core_codegen.intermediate import type_inference as intermediate_type_inference
27
+ from aas_core_codegen.parse import tree as parse_tree, retree as parse_retree
28
+ from aas_core_codegen.golang import (
29
+ common as golang_common,
30
+ naming as golang_naming,
31
+ description as golang_description,
32
+ pointering as golang_pointering,
33
+ transpilation as golang_transpilation,
34
+ )
35
+ from aas_core_codegen.golang.common import (
36
+ INDENT as I,
37
+ INDENT2 as II,
38
+ INDENT3 as III,
39
+ INDENT4 as IIII,
40
+ INDENT5 as IIIII,
41
+ )
42
+
43
+
44
+ # region Verify
45
+
46
+
47
+ def verify(
48
+ spec_impls: specific_implementations.SpecificImplementations,
49
+ verification_functions: Sequence[intermediate.Verification],
50
+ ) -> Optional[List[str]]:
51
+ """Verify all the implementation snippets related to verification."""
52
+ errors = [] # type: List[str]
53
+
54
+ expected_keys = [] # type: List[specific_implementations.ImplementationKey]
55
+
56
+ for func in verification_functions:
57
+ if isinstance(func, intermediate.ImplementationSpecificVerification):
58
+ expected_keys.append(
59
+ specific_implementations.ImplementationKey(
60
+ f"Verification/{func.name}.go"
61
+ ),
62
+ )
63
+
64
+ for key in expected_keys:
65
+ if key not in spec_impls:
66
+ errors.append(f"The implementation snippet is missing for: {key}")
67
+
68
+ if len(errors) == 0:
69
+ return None
70
+
71
+ return errors
72
+
73
+
74
+ # endregion
75
+
76
+ # region Generate
77
+
78
+
79
+ class RegexRenderer(parse_retree.Renderer):
80
+ """
81
+ Render the regular expressions for Go.
82
+
83
+ Notably, do not escape character points, but leave them as-are, since that is
84
+ what Go regular expression engine expects.
85
+
86
+ For example:
87
+
88
+ .. code-block ::
89
+
90
+ package main
91
+
92
+ import (
93
+ "fmt"
94
+ "regexp"
95
+ )
96
+
97
+ func main() {
98
+ re := regexp.MustCompile(
99
+ "^[\x09\x0a\x0d\x20-\ud7ff\ue000-\ufffd\U00010000-\U0010ffff]*$",
100
+ )
101
+ text := "\U0001F600"
102
+ fmt.Printf("%v", re.MatchString(text))
103
+ // Prints "true"
104
+ }
105
+
106
+ """
107
+
108
+ def char_to_str_and_escape_or_encode_if_necessary(
109
+ self, node: parse_retree.Char, escaping: Mapping[str, str]
110
+ ) -> List[Union[str, parse_tree.FormattedValue]]:
111
+ if not node.explicitly_encoded:
112
+ escaped = escaping.get(node.character, None)
113
+ if escaped is not None:
114
+ result: List[Union[str, parse_tree.FormattedValue]] = [escaped]
115
+ else:
116
+ result = [node.character]
117
+
118
+ return result
119
+
120
+ return [node.character]
121
+
122
+
123
+ _REGEX_RENDERER = RegexRenderer()
124
+
125
+
126
+ class _PatternVerificationTranspiler(
127
+ parse_tree.RestrictedTransformer[Tuple[Optional[Stripped], Optional[Error]]]
128
+ ):
129
+ """Transpile a statement of a pattern verification into Golang."""
130
+
131
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
132
+ def _transform_joined_str_values(
133
+ self, values: Sequence[Union[str, parse_tree.FormattedValue]]
134
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
135
+ """Transform the values of a joined string to a Golang string literal."""
136
+ # If we do not need interpolation, simply return the string literals
137
+ # joined together.
138
+ needs_interpolation = any(
139
+ isinstance(value, parse_tree.FormattedValue) for value in values
140
+ )
141
+ if not needs_interpolation:
142
+ return (
143
+ Stripped(
144
+ golang_common.string_literal(
145
+ "".join(value for value in values) # type: ignore
146
+ )
147
+ ),
148
+ None,
149
+ )
150
+
151
+ parts = [] # type: List[str]
152
+
153
+ for value in values:
154
+ if isinstance(value, str):
155
+ parts.append(golang_common.string_literal(value))
156
+
157
+ elif isinstance(value, parse_tree.FormattedValue):
158
+ code, error = self.transform(value.value)
159
+ if error is not None:
160
+ return None, error
161
+
162
+ assert code is not None
163
+
164
+ parts.append(code)
165
+ else:
166
+ assert_never(value)
167
+
168
+ if len(parts) > 1:
169
+ parts_joined = "\n".join(f"{part}," for part in parts)
170
+
171
+ return (
172
+ Stripped(
173
+ f"""\
174
+ aascommon.Concat(
175
+ {I}{indent_but_first_line(parts_joined, I)}
176
+ )"""
177
+ ),
178
+ None,
179
+ )
180
+
181
+ assert len(parts) == 1, "At least one part expected in the formatted string"
182
+ return Stripped(parts[0]), None
183
+
184
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
185
+ def transform_constant(
186
+ self, node: parse_tree.Constant
187
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
188
+ if isinstance(node.value, str):
189
+ # NOTE (mristin, 2023-04-12):
190
+ # We assume that all the string constants are valid regular expressions.
191
+ # At this point, we could not find any difference between Golang and
192
+ # Python regex languages which are relevant to the features we currently
193
+ # support.
194
+
195
+ regex, parse_error = parse_retree.parse(values=[node.value])
196
+ if parse_error is not None:
197
+ regex_line, pointer_line = parse_retree.render_pointer(
198
+ parse_error.cursor
199
+ )
200
+
201
+ return (
202
+ None,
203
+ Error(
204
+ node.original_node,
205
+ f"The string constant could not be parsed "
206
+ f"as a regular expression: \n"
207
+ f"{parse_error.message}\n"
208
+ f"{regex_line}\n"
209
+ f"{pointer_line}",
210
+ ),
211
+ )
212
+
213
+ assert regex is not None
214
+
215
+ # NOTE (mristin, 2022-11-04):
216
+ # Strictly speaking, this is a joined string with a single value, a string
217
+ # literal. Thus, do not be confused by the name of the function —
218
+ # this function treats both joined formatted values *and* string literals.
219
+ return self._transform_joined_str_values(
220
+ values=parse_retree.render(regex=regex, renderer=_REGEX_RENDERER)
221
+ )
222
+ else:
223
+ raise AssertionError(f"Unexpected {node=}")
224
+
225
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
226
+ def transform_name(
227
+ self, node: parse_tree.Name
228
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
229
+ return Stripped(golang_naming.variable_name(node.identifier)), None
230
+
231
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
232
+ def transform_joined_str(
233
+ self, node: parse_tree.JoinedStr
234
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
235
+ regex, parse_error = parse_retree.parse(values=node.values)
236
+ if parse_error is not None:
237
+ regex_line, pointer_line = parse_retree.render_pointer(parse_error.cursor)
238
+
239
+ return (
240
+ None,
241
+ Error(
242
+ node.original_node,
243
+ f"The joined string could not be parsed "
244
+ f"as a regular expression: \n"
245
+ f"{parse_error.message}\n"
246
+ f"{regex_line}\n"
247
+ f"{pointer_line}",
248
+ ),
249
+ )
250
+
251
+ assert regex is not None
252
+
253
+ return self._transform_joined_str_values(
254
+ values=parse_retree.render(regex=regex)
255
+ )
256
+
257
+ def transform_assignment(
258
+ self, node: parse_tree.Assignment
259
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
260
+ assert isinstance(node.target, parse_tree.Name)
261
+ variable = golang_naming.variable_name(node.target.identifier)
262
+ code, error = self.transform(node.value)
263
+ if error is not None:
264
+ return None, error
265
+ assert code is not None
266
+
267
+ # NOTE (mristin, 2023-04-12):
268
+ # We assume that the variables won't change in the patterns. If this assumption
269
+ # is broken, fix the code here by first inspecting the scope and deciding
270
+ # which variables need to be first defined and which have been already
271
+ # defined.
272
+ return Stripped(f"{variable} := {code}"), None
273
+
274
+
275
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
276
+ def _transpile_pattern_verification(
277
+ verification: intermediate.PatternVerification,
278
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
279
+ """Generate the verification function that checks the regular expressions."""
280
+ # NOTE (mristin, 2022-11-12):
281
+ # We assume that we performed all the checks at the intermediate stage.
282
+
283
+ construct_name = golang_naming.private_function_name(
284
+ Identifier(f"construct_{verification.name}")
285
+ )
286
+
287
+ blocks = [] # type: List[Stripped]
288
+
289
+ # region Construct block
290
+
291
+ writer = io.StringIO()
292
+ writer.write(
293
+ f"""\
294
+ func {construct_name}() *regexp.Regexp {{
295
+ """
296
+ )
297
+
298
+ transpiler = _PatternVerificationTranspiler()
299
+
300
+ for i, stmt in enumerate(verification.parsed.body):
301
+ if i == len(verification.parsed.body) - 1:
302
+ break
303
+
304
+ code, error = transpiler.transform(stmt)
305
+ if error is not None:
306
+ return None, error
307
+ assert code is not None
308
+
309
+ writer.write(textwrap.indent(code, I))
310
+ writer.write("\n")
311
+
312
+ if len(verification.parsed.body) >= 2:
313
+ writer.write("\n")
314
+
315
+ pattern_expr, error = transpiler.transform(verification.pattern_expr)
316
+ if error is not None:
317
+ return None, error
318
+ assert pattern_expr is not None
319
+
320
+ writer.write(
321
+ textwrap.indent(
322
+ f"""\
323
+ return regexp.MustCompile(
324
+ {I}{pattern_expr},
325
+ )""",
326
+ I,
327
+ )
328
+ )
329
+
330
+ writer.write("\n}")
331
+
332
+ blocks.append(Stripped(writer.getvalue()))
333
+
334
+ # endregion
335
+
336
+ # region Initialize the regex
337
+
338
+ regex_name = golang_naming.private_constant_name(
339
+ Identifier(f"{verification.name}_re")
340
+ )
341
+
342
+ blocks.append(Stripped(f"var {regex_name} = {construct_name}()"))
343
+
344
+ # endregion
345
+
346
+ # region Define the verification function
347
+
348
+ assert len(verification.arguments) == 1
349
+ assert isinstance(
350
+ verification.arguments[0].type_annotation, intermediate.PrimitiveTypeAnnotation
351
+ )
352
+ # noinspection PyUnresolvedReferences
353
+ assert (
354
+ verification.arguments[0].type_annotation.a_type
355
+ == intermediate.PrimitiveType.STR
356
+ )
357
+
358
+ arg_name = golang_naming.argument_name(verification.arguments[0].name)
359
+
360
+ function_name = golang_naming.function_name(verification.name)
361
+
362
+ writer = io.StringIO()
363
+
364
+ if verification.description is not None:
365
+ (comment, comment_errors,) = golang_description.generate_comment_for_signature(
366
+ description=verification.description,
367
+ context=golang_description.Context(
368
+ package=golang_common.VERIFICATION_PACKAGE, cls_or_enum=None
369
+ ),
370
+ )
371
+ if comment_errors is not None:
372
+ return None, Error(
373
+ verification.description.parsed.node,
374
+ f"Failed to generate the documentation comment for {verification.name!r}",
375
+ comment_errors,
376
+ )
377
+
378
+ assert comment is not None
379
+
380
+ writer.write(comment)
381
+ writer.write("\n")
382
+
383
+ writer.write(
384
+ f"""\
385
+ func {function_name}({arg_name} string) bool {{
386
+ {I}return {regex_name}.MatchString(
387
+ {II}{arg_name},
388
+ {I})
389
+ }}"""
390
+ )
391
+
392
+ blocks.append(Stripped(writer.getvalue()))
393
+
394
+ # endregion
395
+
396
+ writer = io.StringIO()
397
+ for i, block in enumerate(blocks):
398
+ if i > 0:
399
+ writer.write("\n\n")
400
+
401
+ writer.write(block)
402
+
403
+ return Stripped(writer.getvalue()), None
404
+
405
+
406
+ class _TranspilableVerificationTranspiler(golang_transpilation.Transpiler):
407
+ """Transpile the body of a :py:class:`TranspilableVerification`."""
408
+
409
+ # fmt: off
410
+ @require(
411
+ lambda environment, verification:
412
+ all(
413
+ environment.find(arg.name) is not None
414
+ for arg in verification.arguments
415
+ ),
416
+ "All arguments defined in the environment"
417
+ )
418
+ # fmt: on
419
+ def __init__(
420
+ self,
421
+ type_map: Mapping[
422
+ parse_tree.Node, intermediate_type_inference.TypeAnnotationUnion
423
+ ],
424
+ is_pointer_map: Mapping[parse_tree.Node, bool],
425
+ environment: intermediate_type_inference.Environment,
426
+ symbol_table: intermediate.SymbolTable,
427
+ verification: intermediate.TranspilableVerification,
428
+ ) -> None:
429
+ """Initialize with the given values."""
430
+ golang_transpilation.Transpiler.__init__(
431
+ self,
432
+ type_map=type_map,
433
+ is_pointer_map=is_pointer_map,
434
+ environment=environment,
435
+ )
436
+
437
+ self._symbol_table = symbol_table
438
+
439
+ self._argument_name_set = frozenset(arg.name for arg in verification.arguments)
440
+
441
+ def _transform_enumeration_literal(
442
+ self, enumeration_name: Identifier, literal_name: Identifier
443
+ ) -> Stripped:
444
+ literal = golang_naming.enum_literal_name(
445
+ enumeration_name=enumeration_name, literal_name=literal_name
446
+ )
447
+ return Stripped(f"aastypes.{literal}")
448
+
449
+ def transform_name(
450
+ self, node: parse_tree.Name
451
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
452
+ if node.identifier in self._variable_name_set:
453
+ return Stripped(golang_naming.variable_name(node.identifier)), None
454
+
455
+ if node.identifier in self._argument_name_set:
456
+ return Stripped(golang_naming.argument_name(node.identifier)), None
457
+
458
+ if node.identifier in self._symbol_table.constants_by_name:
459
+ constant_name = golang_naming.constant_name(node.identifier)
460
+ return Stripped(f"aasconstants.{constant_name}"), None
461
+
462
+ if node.identifier in self._symbol_table.verification_functions_by_name:
463
+ return Stripped(golang_naming.function_name(node.identifier)), None
464
+
465
+ our_type = self._symbol_table.find_our_type(name=node.identifier)
466
+ if isinstance(our_type, intermediate.Enumeration):
467
+ return (
468
+ Stripped(f"aastypes.{golang_naming.enum_name(node.identifier)}"),
469
+ None,
470
+ )
471
+
472
+ return None, Error(
473
+ node.original_node,
474
+ f"We can not determine how to transpile the name {node.identifier!r} "
475
+ f"to Golang. We could not find it neither in the constants, nor in "
476
+ f"verification functions, nor as an enumeration. "
477
+ f"If you expect this name to be transpilable, please contact "
478
+ f"the developers.",
479
+ )
480
+
481
+
482
+ def _transpile_transpilable_verification(
483
+ verification: intermediate.TranspilableVerification,
484
+ symbol_table: intermediate.SymbolTable,
485
+ environment: intermediate_type_inference.Environment,
486
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
487
+ """Transpile a verification function."""
488
+ # fmt: off
489
+ type_inference, error = (
490
+ intermediate_type_inference.infer_for_verification(
491
+ verification=verification,
492
+ base_environment=environment
493
+ )
494
+ )
495
+ # fmt: on
496
+
497
+ if error is not None:
498
+ return None, error
499
+
500
+ assert type_inference is not None
501
+
502
+ pointer_inferrer = golang_pointering.Inferrer(
503
+ environment=type_inference.environment_with_args,
504
+ type_map=type_inference.type_map,
505
+ )
506
+
507
+ for node in verification.parsed.body:
508
+ _ = pointer_inferrer.transform(node)
509
+
510
+ if len(pointer_inferrer.errors) > 0:
511
+ return None, Error(
512
+ verification.parsed.node,
513
+ f"Failed to infer whether a node is a Golang pointer "
514
+ f"in the verification function {verification.name!r}",
515
+ pointer_inferrer.errors,
516
+ )
517
+
518
+ transpiler = _TranspilableVerificationTranspiler(
519
+ type_map=type_inference.type_map,
520
+ is_pointer_map=pointer_inferrer.is_pointer_map,
521
+ environment=type_inference.environment_with_args,
522
+ symbol_table=symbol_table,
523
+ verification=verification,
524
+ )
525
+
526
+ body = [] # type: List[Stripped]
527
+ for node in verification.parsed.body:
528
+ stmt, error = transpiler.transform(node)
529
+ if error is not None:
530
+ return None, Error(
531
+ verification.parsed.node,
532
+ f"Failed to transpile the verification function {verification.name!r}",
533
+ [error],
534
+ )
535
+
536
+ assert stmt is not None
537
+ body.append(stmt)
538
+
539
+ writer = io.StringIO()
540
+
541
+ if verification.description is not None:
542
+ (comment, comment_errors,) = golang_description.generate_comment_for_signature(
543
+ description=verification.description,
544
+ context=golang_description.Context(
545
+ package=golang_common.VERIFICATION_PACKAGE,
546
+ cls_or_enum=None,
547
+ ),
548
+ )
549
+ if comment_errors is not None:
550
+ return None, Error(
551
+ verification.description.parsed.node,
552
+ f"Failed to generate the comment "
553
+ f"for verification function {verification.name!r}",
554
+ comment_errors,
555
+ )
556
+
557
+ assert comment is not None
558
+
559
+ writer.write(comment)
560
+ writer.write("\n")
561
+
562
+ function_name = golang_naming.function_name(verification.name)
563
+
564
+ if verification.returns is None:
565
+ return_type_suffix = ""
566
+ else:
567
+ return_type = golang_common.generate_type(
568
+ type_annotation=verification.returns, types_package=Identifier("aastypes")
569
+ )
570
+ return_type_suffix = f" {return_type}"
571
+
572
+ arg_defs = [] # type: List[Stripped]
573
+ for arg in verification.arguments:
574
+ arg_type = golang_common.generate_type(
575
+ arg.type_annotation, types_package=Identifier("aastypes")
576
+ )
577
+ arg_name = golang_naming.argument_name(arg.name)
578
+ arg_defs.append(Stripped(f"{arg_name} {arg_type}"))
579
+
580
+ if len(arg_defs) == 0:
581
+ writer.write(
582
+ f"""\
583
+ func {function_name}(){return_type_suffix} {{"""
584
+ )
585
+ else:
586
+ arg_defs_joined = "\n".join(f"{arg_def}," for arg_def in arg_defs)
587
+ writer.write(
588
+ f"""\
589
+ func {function_name}(
590
+ {I}{indent_but_first_line(arg_defs_joined, I)}
591
+ ){return_type_suffix} {{"""
592
+ )
593
+
594
+ if len(body) == 0:
595
+ writer.write("\n")
596
+ writer.write("// Intentionally empty.")
597
+ else:
598
+ for stmt in body:
599
+ writer.write("\n")
600
+ writer.write(textwrap.indent(stmt, I))
601
+
602
+ writer.write("\n}")
603
+
604
+ return Stripped(writer.getvalue()), None
605
+
606
+
607
+ class _InvariantTranspiler(golang_transpilation.Transpiler):
608
+ def __init__(
609
+ self,
610
+ type_map: Mapping[
611
+ parse_tree.Node, intermediate_type_inference.TypeAnnotationUnion
612
+ ],
613
+ is_pointer_map: Mapping[parse_tree.Node, bool],
614
+ environment: intermediate_type_inference.Environment,
615
+ symbol_table: intermediate.SymbolTable,
616
+ ) -> None:
617
+ """Initialize with the given values."""
618
+ golang_transpilation.Transpiler.__init__(
619
+ self,
620
+ type_map=type_map,
621
+ is_pointer_map=is_pointer_map,
622
+ environment=environment,
623
+ types_package=Identifier("aastypes"),
624
+ )
625
+
626
+ self._symbol_table = symbol_table
627
+
628
+ def _transform_enumeration_literal(
629
+ self, enumeration_name: Identifier, literal_name: Identifier
630
+ ) -> Stripped:
631
+ literal = golang_naming.enum_literal_name(
632
+ enumeration_name=enumeration_name, literal_name=literal_name
633
+ )
634
+ return Stripped(f"aastypes.{literal}")
635
+
636
+ def transform_name(
637
+ self, node: parse_tree.Name
638
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
639
+ if node.identifier in self._variable_name_set:
640
+ name = Stripped(golang_naming.variable_name(node.identifier))
641
+
642
+ elif node.identifier == "self":
643
+ # The ``that`` refers to the argument of the verification function.
644
+ name = Stripped("that")
645
+
646
+ elif node.identifier in self._symbol_table.constants_by_name:
647
+ constant_name = golang_naming.constant_name(node.identifier)
648
+ name = Stripped(f"aasconstants.{constant_name}")
649
+
650
+ elif node.identifier in self._symbol_table.verification_functions_by_name:
651
+ name = Stripped(golang_naming.function_name(node.identifier))
652
+
653
+ elif (
654
+ our_type := self._symbol_table.find_our_type(name=node.identifier),
655
+ isinstance(our_type, intermediate.Enumeration),
656
+ )[1]:
657
+ name = Stripped(f"aastypes.{golang_naming.enum_name(node.identifier)}")
658
+ else:
659
+ return None, Error(
660
+ node.original_node,
661
+ f"We can not determine how to transpile the name {node.identifier!r} "
662
+ f"to Golang. We could not find it neither in the local variables, "
663
+ f"nor in the global constants, nor in verification functions, "
664
+ f"nor as an enumeration. If you expect this name to be transpilable, "
665
+ f"please contact the developers.",
666
+ )
667
+
668
+ assert name is not None
669
+ return name, None
670
+
671
+
672
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
673
+ def _transpile_invariant(
674
+ invariant: intermediate.Invariant,
675
+ symbol_table: intermediate.SymbolTable,
676
+ environment: intermediate_type_inference.Environment,
677
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
678
+ """Translate the invariant from the meta-model into Golang code."""
679
+ # fmt: off
680
+ type_map, inference_error = (
681
+ intermediate_type_inference.infer_for_invariant(
682
+ invariant=invariant,
683
+ environment=environment
684
+ )
685
+ )
686
+ # fmt: on
687
+
688
+ if inference_error is not None:
689
+ return None, inference_error
690
+
691
+ assert type_map is not None
692
+
693
+ pointer_inferrer = golang_pointering.Inferrer(
694
+ environment=environment, type_map=type_map
695
+ )
696
+
697
+ _ = pointer_inferrer.transform(invariant.body)
698
+
699
+ if len(pointer_inferrer.errors) > 0:
700
+ return None, Error(
701
+ invariant.parsed.node,
702
+ "Failed to infer whether a node is a Golang pointer in the invariant",
703
+ pointer_inferrer.errors,
704
+ )
705
+
706
+ transpiler = _InvariantTranspiler(
707
+ type_map=type_map,
708
+ is_pointer_map=pointer_inferrer.is_pointer_map,
709
+ environment=environment,
710
+ symbol_table=symbol_table,
711
+ )
712
+
713
+ expr, error = transpiler.transform(invariant.parsed.body)
714
+ if error is not None:
715
+ return None, error
716
+
717
+ assert expr is not None
718
+
719
+ writer = io.StringIO()
720
+ if len(expr) > 50 or "\n" in expr:
721
+ writer.write(
722
+ f"""\
723
+ if !(
724
+ {I}{indent_but_first_line(expr, I)}) {{
725
+ """
726
+ )
727
+ else:
728
+ no_parenthesis_type_in_this_context = (
729
+ parse_tree.Index,
730
+ parse_tree.Name,
731
+ parse_tree.Member,
732
+ parse_tree.MethodCall,
733
+ parse_tree.FunctionCall,
734
+ )
735
+
736
+ if isinstance(invariant.parsed.body, no_parenthesis_type_in_this_context):
737
+ not_expr = f"!{expr}"
738
+ else:
739
+ not_expr = f"!({expr})"
740
+
741
+ writer.write(f"if {not_expr} {{\n")
742
+
743
+ new_verification_error_writer = io.StringIO()
744
+
745
+ new_verification_error_writer.write("newVerificationError(\n")
746
+
747
+ # NOTE (mristin, 2023-04-12):
748
+ # We need to wrap the description in multiple literals as a single long
749
+ # string literal is often too much for the readability.
750
+ invariant_description_lines = wrap_text_into_lines(invariant.description)
751
+
752
+ if len(invariant_description_lines) == 1:
753
+ line = invariant_description_lines[0]
754
+ new_verification_error_writer.write(f"{I}{golang_common.string_literal(line)},")
755
+ new_verification_error_writer.write(")")
756
+ else:
757
+ for i, line in enumerate(invariant_description_lines):
758
+ if i == 0:
759
+ new_verification_error_writer.write(
760
+ f"{I}{golang_common.string_literal(line)} +\n"
761
+ )
762
+ elif i < len(invariant_description_lines) - 1:
763
+ new_verification_error_writer.write(
764
+ f"{I}{golang_common.string_literal(line)} +\n"
765
+ )
766
+ else:
767
+ new_verification_error_writer.write(
768
+ f"{I}{golang_common.string_literal(line)},\n"
769
+ )
770
+ new_verification_error_writer.write(")")
771
+
772
+ new_verification_error = Stripped(new_verification_error_writer.getvalue())
773
+
774
+ writer.write(
775
+ f"""\
776
+ {I}abort = onError(
777
+ {II}{indent_but_first_line(new_verification_error, II)},
778
+ {I})
779
+ {I}if abort {{
780
+ {II}return
781
+ {I}}}
782
+ }}"""
783
+ )
784
+
785
+ return Stripped(writer.getvalue()), None
786
+
787
+
788
+ OurTypeExceptEnumeration = Union[
789
+ intermediate.ConstrainedPrimitive,
790
+ intermediate.AbstractClass,
791
+ intermediate.ConcreteClass,
792
+ ]
793
+ assert_union_without_excluded(
794
+ original_union=intermediate.OurType,
795
+ subset_union=OurTypeExceptEnumeration,
796
+ excluded=[intermediate.Enumeration],
797
+ )
798
+
799
+
800
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
801
+ def _generate_verify_property_snippet(
802
+ prop: intermediate.Property,
803
+ ) -> Tuple[Optional[Stripped], Optional[Error]]:
804
+ """
805
+ Generate the snippet to verify a property.
806
+
807
+ Return an empty string if there is nothing to be verified for the given property.
808
+ """
809
+ # NOTE (mristin, 2023-04-12):
810
+ # Instead of writing here a complex but general solution with unrolling we choose
811
+ # to provide a simple, but limited, solution. First, the meta-model is quite
812
+ # limited itself at the moment, so the complexity of the general solution is not
813
+ # warranted. Second, we hope that there will be fewer bugs in the simple solution
814
+ # which is particularly important at this early adoption stage.
815
+ #
816
+ # We anticipate that in the future we will indeed need a general and complex
817
+ # solution. Here are just some thoughts on how to approach it:
818
+ # * Leave the pattern matching to produce more readable code for simple cases,
819
+ # * Unroll only in case of composite types and optional composite types.
820
+
821
+ type_anno = intermediate.beneath_optional(prop.type_annotation)
822
+
823
+ prop_name = golang_naming.property_name(prop.name)
824
+ prop_name_literal = golang_common.string_literal(prop_name)
825
+
826
+ getter_name = golang_naming.getter_name(prop.name)
827
+
828
+ optional = isinstance(prop.type_annotation, intermediate.OptionalTypeAnnotation)
829
+
830
+ block = None # type: Optional[Stripped]
831
+
832
+ if isinstance(type_anno, intermediate.PrimitiveTypeAnnotation):
833
+ if type_anno.a_type is intermediate.PrimitiveType.BYTEARRAY and not optional:
834
+ block = Stripped(
835
+ f"""\
836
+ if that.{getter_name}() == nil {{
837
+ {I}abort = onError(
838
+ {II}newVerificationError(
839
+ {III}"Required property not set: {prop_name}",
840
+ {II}),
841
+ {I})
842
+ {I}if abort {{
843
+ {II}return
844
+ {I}}}
845
+ }}"""
846
+ )
847
+
848
+ elif isinstance(type_anno, intermediate.OurTypeAnnotation):
849
+ our_type = type_anno.our_type
850
+
851
+ if isinstance(our_type, intermediate.Enumeration):
852
+ enum_name = golang_naming.enum_name(our_type.name)
853
+
854
+ # NOTE (mristin, 2023-04-12):
855
+ # The case where we have no literals defined is an edge case where no
856
+ # literal satisfies the condition.
857
+ if len(our_type.literals) == 0:
858
+ block = Stripped(
859
+ f"""\
860
+ err := newVerificationError(
861
+ {I}fmt.Sprintf(
862
+ {II}"The enumeration {enum_name} has no literals defined, " +
863
+ {II}"but you passed in: %v",
864
+ {II}that.{getter_name}()
865
+ {I})
866
+ )
867
+ err.Path.Prepend(
868
+ {I}&aasreporting.NameSegment{{
869
+ {II}Name: {prop_name_literal},
870
+ {I}}},
871
+ )
872
+ abort = onError(err)
873
+ if abort {{
874
+ {I}return
875
+ }}"""
876
+ )
877
+ else:
878
+ first_literal = golang_naming.enum_literal_name(
879
+ enumeration_name=our_type.name,
880
+ literal_name=our_type.literals[0].name,
881
+ )
882
+ last_literal = golang_naming.enum_literal_name(
883
+ enumeration_name=our_type.name,
884
+ literal_name=our_type.literals[-1].name,
885
+ )
886
+
887
+ pointer_prefix = (
888
+ "*"
889
+ if golang_pointering.is_pointer_type(prop.type_annotation)
890
+ else ""
891
+ )
892
+
893
+ block = Stripped(
894
+ f"""\
895
+ if
896
+ {I}{pointer_prefix}that.{getter_name}() < aastypes.{first_literal} ||
897
+ {I}{pointer_prefix}that.{getter_name}() > aastypes.{last_literal} {{
898
+ {I}err := newVerificationError(
899
+ {II}fmt.Sprintf(
900
+ {III}"Invalid literal value for {enum_name}: %v",
901
+ {III}that.{getter_name}(),
902
+ {II}),
903
+ {I})
904
+ {I}err.Path.PrependName(
905
+ {II}&aasreporting.NameSegment{{
906
+ {III}Name: {prop_name_literal},
907
+ {II}}},
908
+ {I})
909
+ {I}abort = onError(err)
910
+ {I}if abort {{
911
+ {II}return
912
+ {I}}}
913
+ }}"""
914
+ )
915
+
916
+ elif isinstance(our_type, intermediate.ConstrainedPrimitive):
917
+ verify_function_name = golang_naming.function_name(
918
+ Identifier(f"verify_{our_type.name}")
919
+ )
920
+
921
+ pointer_prefix = (
922
+ "*" if golang_pointering.is_pointer_type(prop.type_annotation) else ""
923
+ )
924
+
925
+ block = Stripped(
926
+ f"""\
927
+ abort = {verify_function_name}(
928
+ {I}{pointer_prefix}that.{getter_name}(),
929
+ {I}func(err *VerificationError) bool {{
930
+ {II}err.Path.PrependName(
931
+ {III}&aasreporting.NameSegment{{
932
+ {IIII}Name: {prop_name_literal},
933
+ {III}}},
934
+ {II})
935
+ {II}return onError(err)
936
+ {I}}},
937
+ )
938
+ if abort {{
939
+ {I}return
940
+ }}"""
941
+ )
942
+
943
+ elif isinstance(
944
+ our_type, (intermediate.AbstractClass, intermediate.ConcreteClass)
945
+ ):
946
+ block = Stripped(
947
+ f"""\
948
+ abort = Verify(
949
+ {I}that.{getter_name}(),
950
+ {I}func(err *VerificationError) bool {{
951
+ {II}err.Path.PrependName(
952
+ {III}&aasreporting.NameSegment{{
953
+ {IIII}Name: {prop_name_literal},
954
+ {III}}},
955
+ {II})
956
+ {II}return onError(err)
957
+ {I}}},
958
+ )
959
+ if abort {{
960
+ {I}return
961
+ }}"""
962
+ )
963
+ else:
964
+ assert_never(our_type)
965
+
966
+ elif isinstance(type_anno, intermediate.ListTypeAnnotation):
967
+ assert isinstance(
968
+ type_anno.items, intermediate.OurTypeAnnotation
969
+ ) and isinstance(
970
+ type_anno.items.our_type,
971
+ (intermediate.AbstractClass, intermediate.ConcreteClass),
972
+ ), (
973
+ f"NOTE (mristin, 2023-04-12): We expect only lists of classes "
974
+ f"at the moment, but you specified {type_anno}. "
975
+ f"Please contact the developers if you need this feature."
976
+ )
977
+
978
+ block = Stripped(
979
+ f"""\
980
+ for i, v := range that.{getter_name}() {{
981
+ {I}abort = Verify(
982
+ {II}v,
983
+ {II}func(err *VerificationError) bool {{
984
+ {III}err.Path.PrependIndex(
985
+ {IIII}&aasreporting.IndexSegment{{
986
+ {IIIII}Index: i,
987
+ {IIII}}},
988
+ {III})
989
+
990
+ {III}err.Path.PrependName(
991
+ {IIII}&aasreporting.NameSegment{{
992
+ {IIIII}Name: {prop_name_literal},
993
+ {IIII}}},
994
+ {III})
995
+
996
+ {III}return onError(err)
997
+ {II}}},
998
+ {I})
999
+ {I}if abort {{
1000
+ {II}return
1001
+ {I}}}
1002
+ }}"""
1003
+ )
1004
+
1005
+ else:
1006
+ assert_never(type_anno)
1007
+
1008
+ primitive_type = intermediate.try_primitive_type(type_anno)
1009
+
1010
+ is_reference = (
1011
+ optional
1012
+ or primitive_type is intermediate.PrimitiveType.BYTEARRAY
1013
+ or (
1014
+ isinstance(type_anno, intermediate.OurTypeAnnotation)
1015
+ and isinstance(
1016
+ type_anno.our_type,
1017
+ (intermediate.AbstractClass, intermediate.ConcreteClass),
1018
+ )
1019
+ )
1020
+ or isinstance(type_anno, intermediate.ListTypeAnnotation)
1021
+ )
1022
+
1023
+ if not optional and is_reference and block is None:
1024
+ block = Stripped(
1025
+ f"""\
1026
+ if that.{getter_name}() == nil {{
1027
+ {I}abort = onError(
1028
+ {II}newVerificationError(
1029
+ {III}"Required property not set: {prop_name}",
1030
+ {II}),
1031
+ {I})
1032
+ {I}if abort {{
1033
+ {II}return
1034
+ {I}}}
1035
+ }}"""
1036
+ )
1037
+ elif not optional and is_reference and block is not None:
1038
+ block = Stripped(
1039
+ f"""\
1040
+ if that.{getter_name}() == nil {{
1041
+ {I}abort = onError(
1042
+ {II}newVerificationError(
1043
+ {III}"Required property not set: {prop_name}",
1044
+ {II}),
1045
+ {I})
1046
+ {I}if abort {{
1047
+ {II}return
1048
+ {I}}}
1049
+ }} else {{
1050
+ {I}{indent_but_first_line(block, I)}
1051
+ }}"""
1052
+ )
1053
+ elif optional and block is not None:
1054
+ block = Stripped(
1055
+ f"""\
1056
+ if that.{getter_name}() != nil {{
1057
+ {I}{indent_but_first_line(block, I)}
1058
+ }}"""
1059
+ )
1060
+ elif block is None:
1061
+ return Stripped(""), None
1062
+ else:
1063
+ assert AssertionError(f"Unhandled case: {block=}, {optional=}, {is_reference=}")
1064
+
1065
+ return block, None
1066
+
1067
+
1068
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
1069
+ def _generate_verify_class(
1070
+ cls: intermediate.ConcreteClass,
1071
+ symbol_table: intermediate.SymbolTable,
1072
+ base_environment: intermediate_type_inference.Environment,
1073
+ ) -> Tuple[Optional[Stripped], Optional[List[Error]]]:
1074
+ """Generate the verification function for the given concrete class."""
1075
+ errors = [] # type: List[Error]
1076
+ blocks = [] # type: List[Stripped]
1077
+
1078
+ environment = intermediate_type_inference.MutableEnvironment(
1079
+ parent=base_environment
1080
+ )
1081
+
1082
+ assert environment.find(Identifier("self")) is None
1083
+ environment.set(
1084
+ identifier=Identifier("self"),
1085
+ type_annotation=intermediate_type_inference.OurTypeAnnotation(our_type=cls),
1086
+ )
1087
+
1088
+ # region Generate the non-recursive part verifying the invariants
1089
+
1090
+ for invariant in cls.invariants:
1091
+ invariant_code, error = _transpile_invariant(
1092
+ invariant=invariant, symbol_table=symbol_table, environment=environment
1093
+ )
1094
+ if error is not None:
1095
+ errors.append(
1096
+ Error(
1097
+ cls.parsed.node,
1098
+ f"Failed to transpile the invariant of the class {cls.name!r}",
1099
+ [error],
1100
+ )
1101
+ )
1102
+ continue
1103
+
1104
+ assert invariant_code is not None
1105
+
1106
+ blocks.append(invariant_code)
1107
+
1108
+ # endregion
1109
+
1110
+ # region Recurse into properties
1111
+
1112
+ for prop in cls.properties:
1113
+ block, error = _generate_verify_property_snippet(prop=prop)
1114
+ if error is not None:
1115
+ errors.append(
1116
+ Error(
1117
+ cls.parsed.node,
1118
+ f"Failed to generate the verification of the property {prop.name!r} "
1119
+ f"of the class {cls.name!r}",
1120
+ [error],
1121
+ )
1122
+ )
1123
+ continue
1124
+
1125
+ assert block is not None
1126
+
1127
+ if block != "":
1128
+ blocks.append(block)
1129
+
1130
+ # endregion
1131
+
1132
+ if len(errors) > 0:
1133
+ return None, errors
1134
+
1135
+ interface_name = golang_naming.interface_name(cls.name)
1136
+
1137
+ if len(blocks) == 0:
1138
+ blocks.append(
1139
+ Stripped(
1140
+ f"""\
1141
+ // No verification has been defined for {interface_name}."""
1142
+ )
1143
+ )
1144
+
1145
+ function_name = golang_naming.function_name(Identifier(f"verify_{cls.name}"))
1146
+
1147
+ body = "\n\n".join(blocks)
1148
+
1149
+ return (
1150
+ Stripped(
1151
+ f"""\
1152
+ // Verify `that` instance of [aastypes.{interface_name}].
1153
+ //
1154
+ // You have to supply the callback `onError` to iterate over the errors.
1155
+ // If `onError` returns abort `true`, this function will abort
1156
+ // further verification as well, and return abort `true`. Otherwise,
1157
+ // abort `false` is returned.
1158
+ func {function_name}(
1159
+ {I}that aastypes.{interface_name},
1160
+ {I}onError func(*VerificationError) bool,
1161
+ ) (abort bool) {{
1162
+ {I}abort = false
1163
+
1164
+ {I}{indent_but_first_line(body, I)}
1165
+
1166
+ {I}return
1167
+ }}"""
1168
+ ),
1169
+ None,
1170
+ )
1171
+
1172
+
1173
+ def _generate_verify(symbol_table: intermediate.SymbolTable) -> Stripped:
1174
+ """Generate the main entry point for verification."""
1175
+ case_blocks = [] # type: List[Stripped]
1176
+
1177
+ for cls in symbol_table.concrete_classes:
1178
+ literal = golang_naming.enum_literal_name(
1179
+ enumeration_name=Identifier("Model_type"), literal_name=cls.name
1180
+ )
1181
+
1182
+ verification_function = golang_naming.function_name(
1183
+ Identifier(f"verify_{cls.name}")
1184
+ )
1185
+
1186
+ interface_name = golang_naming.interface_name(cls.name)
1187
+
1188
+ case_blocks.append(
1189
+ Stripped(
1190
+ f"""\
1191
+ case aastypes.{literal}:
1192
+ {I}abort = {verification_function}(
1193
+ {II}that.(aastypes.{interface_name}),
1194
+ {II}onError,
1195
+ {I})"""
1196
+ )
1197
+ )
1198
+
1199
+ case_blocks.append(
1200
+ Stripped(
1201
+ f"""\
1202
+ default:
1203
+ {I}abort = onError(
1204
+ {II}newVerificationError(
1205
+ {III}fmt.Sprintf(
1206
+ {IIII}"Unexpected model type literal: %v",
1207
+ {IIII}modelType,
1208
+ {III}),
1209
+ {II}),
1210
+ {I})"""
1211
+ )
1212
+ )
1213
+
1214
+ switch_body = Stripped("\n".join(case_blocks))
1215
+ switch_statement = Stripped(
1216
+ f"""\
1217
+ switch modelType {{
1218
+ {switch_body}
1219
+ }}"""
1220
+ )
1221
+
1222
+ model_type_getter = golang_naming.getter_name(Identifier("model_type"))
1223
+
1224
+ return Stripped(
1225
+ f"""\
1226
+ // Verify ``that`` instance.
1227
+ //
1228
+ // You have to supply the callback `onError` to iterate over the errors.
1229
+ // If `onError` returns abort `true`, this function will abort
1230
+ // further verification as well, and return abort `true`. Otherwise,
1231
+ // abort `false` is returned.
1232
+ func Verify(
1233
+ {I}that aastypes.IClass,
1234
+ {I}onError func(*VerificationError) bool,
1235
+ ) (abort bool) {{
1236
+ {I}modelType := that.{model_type_getter}()
1237
+ {I}{indent_but_first_line(switch_statement, I)}
1238
+ {I}return
1239
+ }}"""
1240
+ )
1241
+
1242
+
1243
+ def _generate_verify_constrained_primitive(
1244
+ constrained_primitive: intermediate.ConstrainedPrimitive,
1245
+ symbol_table: intermediate.SymbolTable,
1246
+ base_environment: intermediate_type_inference.Environment,
1247
+ ) -> Tuple[Optional[Stripped], Optional[List[Error]]]:
1248
+ """Generate the verify function for the constrained primitives."""
1249
+ errors = [] # type: List[Error]
1250
+ blocks = [] # type: List[Stripped]
1251
+
1252
+ environment = intermediate_type_inference.MutableEnvironment(
1253
+ parent=base_environment
1254
+ )
1255
+
1256
+ assert environment.find(Identifier("self")) is None
1257
+ environment.set(
1258
+ identifier=Identifier("self"),
1259
+ type_annotation=intermediate_type_inference.OurTypeAnnotation(
1260
+ our_type=constrained_primitive
1261
+ ),
1262
+ )
1263
+
1264
+ for invariant in constrained_primitive.invariants:
1265
+ invariant_code, error = _transpile_invariant(
1266
+ invariant=invariant, symbol_table=symbol_table, environment=environment
1267
+ )
1268
+ if error is not None:
1269
+ errors.append(
1270
+ Error(
1271
+ constrained_primitive.parsed.node,
1272
+ f"Failed to transpile the invariant of "
1273
+ f"the constrained primitive {constrained_primitive.name!r}",
1274
+ [error],
1275
+ )
1276
+ )
1277
+ continue
1278
+
1279
+ assert invariant_code is not None
1280
+
1281
+ blocks.append(invariant_code)
1282
+
1283
+ if len(errors) > 0:
1284
+ return None, errors
1285
+
1286
+ if len(blocks) == 0:
1287
+ blocks.append(Stripped("// There is no verification specified."))
1288
+
1289
+ body = "\n\n".join(blocks)
1290
+
1291
+ function_name = golang_naming.function_name(
1292
+ Identifier(f"verify_{constrained_primitive.name}")
1293
+ )
1294
+
1295
+ that_type = golang_common.PRIMITIVE_TYPE_MAP[constrained_primitive.constrainee]
1296
+
1297
+ return (
1298
+ Stripped(
1299
+ f"""\
1300
+ // Verify the constraints of `that` value.
1301
+ //
1302
+ // You have to supply the callback `onError` to iterate over the errors.
1303
+ // If `onError` returns abort `true`, this function will abort
1304
+ // further verification as well, and return abort `true`. Otherwise,
1305
+ // abort `false` is returned.
1306
+ func {function_name}(
1307
+ {I}that {that_type},
1308
+ {I}onError func(*VerificationError) bool,
1309
+ ) (abort bool) {{
1310
+ {I}abort = false
1311
+
1312
+ {I}{indent_but_first_line(body, I)}
1313
+
1314
+ {I}return
1315
+ }}"""
1316
+ ),
1317
+ None,
1318
+ )
1319
+
1320
+
1321
+ # fmt: off
1322
+ @ensure(lambda result: (result[0] is not None) ^ (result[1] is not None))
1323
+ @ensure(
1324
+ lambda result:
1325
+ not (result[0] is not None) or result[0].endswith('\n'),
1326
+ "Trailing newline mandatory for valid end-of-files"
1327
+ )
1328
+ # fmt: on
1329
+ def generate(
1330
+ symbol_table: intermediate.SymbolTable,
1331
+ spec_impls: specific_implementations.SpecificImplementations,
1332
+ repo_url: Stripped,
1333
+ ) -> Tuple[Optional[str], Optional[List[Error]]]:
1334
+ """Generate the Golang code for verification based on the symbol table."""
1335
+ errors = [] # type: List[Error]
1336
+
1337
+ aasconstants_url_literal = golang_common.string_literal(f"{repo_url}/constants")
1338
+
1339
+ aascommon_url_literal = golang_common.string_literal(f"{repo_url}/common")
1340
+
1341
+ aasreporting_url_literal = golang_common.string_literal(f"{repo_url}/reporting")
1342
+
1343
+ aastypes_url_literal = golang_common.string_literal(f"{repo_url}/types")
1344
+
1345
+ blocks = [
1346
+ Stripped(
1347
+ """\
1348
+ // Package verification allows you to verify model instances.
1349
+ //
1350
+ // The main function is [Verify].
1351
+ //
1352
+ // Other verification functions (`Verify*`) are left for modularity, in case you want
1353
+ // to be explicit about the typing in your code. However, in the large majority of
1354
+ // the cases, you only want to call [Verify].
1355
+ package verification"""
1356
+ ),
1357
+ golang_common.WARNING,
1358
+ Stripped(
1359
+ f"""\
1360
+ import (
1361
+ {I}"math/big"
1362
+ {I}"fmt"
1363
+ {I}"regexp"
1364
+ {I}"strconv"
1365
+ {I}"strings"
1366
+ {I}aascommon {aascommon_url_literal}
1367
+ {I}aasconstants {aasconstants_url_literal}
1368
+ {I}aasreporting {aasreporting_url_literal}
1369
+ {I}aastypes {aastypes_url_literal}
1370
+ )"""
1371
+ ),
1372
+ Stripped(
1373
+ f"""\
1374
+ // Represent a verification violation.
1375
+ //
1376
+ // Implements `error`.
1377
+ type VerificationError struct{{
1378
+ {I}Path *aasreporting.Path
1379
+ {I}Message string
1380
+ }}"""
1381
+ ),
1382
+ Stripped(
1383
+ f"""\
1384
+ func newVerificationError(message string) *VerificationError {{
1385
+ {I}return &VerificationError{{
1386
+ {II}Path: &aasreporting.Path{{}},
1387
+ {II}Message: message,
1388
+ {I}}}
1389
+ }}"""
1390
+ ),
1391
+ Stripped(
1392
+ f"""\
1393
+ func (ve *VerificationError) Error() string {{
1394
+ {I}return fmt.Sprintf(
1395
+ {II}"%s: %s",
1396
+ {II}ve.PathString(),
1397
+ {II}ve.Message,
1398
+ {I})
1399
+ }}"""
1400
+ ),
1401
+ Stripped(
1402
+ f"""\
1403
+ // Render the path as a string.
1404
+ func (ve *VerificationError) PathString() string {{
1405
+ {I}return aasreporting.ToGolangPath(ve.Path)
1406
+ }}"""
1407
+ ),
1408
+ ] # type: List[Stripped]
1409
+
1410
+ base_environment = intermediate_type_inference.populate_base_environment(
1411
+ symbol_table=symbol_table
1412
+ )
1413
+
1414
+ for verification in symbol_table.verification_functions:
1415
+ if isinstance(verification, intermediate.ImplementationSpecificVerification):
1416
+ implementation_key = specific_implementations.ImplementationKey(
1417
+ f"Verification/{verification.name}.go"
1418
+ )
1419
+
1420
+ implementation = spec_impls.get(implementation_key, None)
1421
+ if implementation is None:
1422
+ errors.append(
1423
+ Error(
1424
+ None,
1425
+ f"The snippet for the verification function "
1426
+ f"{verification.name!r} is missing: {implementation_key}",
1427
+ )
1428
+ )
1429
+ else:
1430
+ blocks.append(implementation)
1431
+
1432
+ elif isinstance(verification, intermediate.PatternVerification):
1433
+ implementation, error = _transpile_pattern_verification(
1434
+ verification=verification
1435
+ )
1436
+
1437
+ if error is not None:
1438
+ errors.append(error)
1439
+ else:
1440
+ assert implementation is not None
1441
+ blocks.append(implementation)
1442
+
1443
+ elif isinstance(verification, intermediate.TranspilableVerification):
1444
+ implementation, error = _transpile_transpilable_verification(
1445
+ verification=verification,
1446
+ symbol_table=symbol_table,
1447
+ environment=base_environment,
1448
+ )
1449
+
1450
+ if error is not None:
1451
+ errors.append(error)
1452
+ else:
1453
+ assert implementation is not None
1454
+ blocks.append(implementation)
1455
+
1456
+ else:
1457
+ assert_never(verification)
1458
+
1459
+ for cls in symbol_table.concrete_classes:
1460
+ block, underlying_errors = _generate_verify_class(
1461
+ cls=cls, symbol_table=symbol_table, base_environment=base_environment
1462
+ )
1463
+ if underlying_errors is not None:
1464
+ errors.append(
1465
+ Error(
1466
+ cls.parsed.node,
1467
+ f"Failed to generate the verification for the class {cls.name!r}",
1468
+ underlying_errors,
1469
+ )
1470
+ )
1471
+ else:
1472
+ assert block is not None
1473
+ blocks.append(block)
1474
+
1475
+ for constrained_primitive in symbol_table.constrained_primitives:
1476
+ block, underlying_errors = _generate_verify_constrained_primitive(
1477
+ constrained_primitive=constrained_primitive,
1478
+ symbol_table=symbol_table,
1479
+ base_environment=base_environment,
1480
+ )
1481
+ if underlying_errors is not None:
1482
+ errors.append(
1483
+ Error(
1484
+ constrained_primitive.parsed.node,
1485
+ f"Failed to generate the verification for "
1486
+ f"the constrained primitive {constrained_primitive.name!r}",
1487
+ underlying_errors,
1488
+ )
1489
+ )
1490
+ else:
1491
+ assert block is not None
1492
+ blocks.append(block)
1493
+
1494
+ blocks.append(_generate_verify(symbol_table=symbol_table))
1495
+
1496
+ blocks.append(golang_common.WARNING)
1497
+
1498
+ if len(errors) > 0:
1499
+ return None, errors
1500
+
1501
+ writer = io.StringIO()
1502
+ for i, block in enumerate(blocks):
1503
+ if i > 0:
1504
+ writer.write("\n\n")
1505
+
1506
+ writer.write(block)
1507
+
1508
+ writer.write("\n")
1509
+
1510
+ return writer.getvalue(), None
1511
+
1512
+
1513
+ # endregion