jaclang 0.7.32__py3-none-any.whl → 0.7.34__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.

Potentially problematic release.


This version of jaclang might be problematic. Click here for more details.

jaclang/__init__.py CHANGED
@@ -23,7 +23,6 @@ from jaclang.plugin.builtin import dotgen, jid, jobj # noqa: F401
23
23
  from jaclang.plugin.default import JacFeatureImpl
24
24
  from jaclang.plugin.feature import JacFeature as Jac, plugin_manager
25
25
  from jaclang.plugin.spec import EdgeDir
26
- from jaclang.runtimelib.context import ExecutionContext
27
26
 
28
27
  __all__ = [
29
28
  # Jac types.
@@ -173,7 +172,7 @@ class Node(_ArchiTypeBase, metaclass=JacMeta):
173
172
  self,
174
173
  node: "Node | Root | JacList[Node | Root]",
175
174
  edge: "type[Edge] | Edge | None" = None,
176
- unidir: bool = False,
175
+ undir: bool = False,
177
176
  conn_assign: tuple[tuple, tuple] | None = None,
178
177
  edges_only: bool = False,
179
178
  ) -> "JacList[Node | Root| Edge]":
@@ -183,7 +182,7 @@ class Node(_ArchiTypeBase, metaclass=JacMeta):
183
182
  left=self, # type: ignore [arg-type]
184
183
  right=node, # type: ignore [arg-type]
185
184
  edge_spec=Jac.build_edge(
186
- is_undirected=unidir, conn_type=edge, conn_assign=conn_assign # type: ignore [arg-type]
185
+ is_undirected=undir, conn_type=edge, conn_assign=conn_assign # type: ignore [arg-type]
187
186
  ),
188
187
  edges_only=edges_only,
189
188
  )
@@ -244,7 +243,7 @@ class Root(_ArchiTypeBase, metaclass=JacMeta):
244
243
  self,
245
244
  node: "Node | Root | JacList[Node | Root]",
246
245
  edge: "type[Edge] | Edge | None" = None,
247
- unidir: bool = False,
246
+ undir: bool = False,
248
247
  conn_assign: tuple[tuple, tuple] | None = None,
249
248
  edges_only: bool = False,
250
249
  ) -> "JacList[Node | Root| Edge]":
@@ -254,7 +253,7 @@ class Root(_ArchiTypeBase, metaclass=JacMeta):
254
253
  left=self, # type: ignore [arg-type]
255
254
  right=node, # type: ignore [arg-type]
256
255
  edge_spec=Jac.build_edge(
257
- is_undirected=unidir, conn_type=edge, conn_assign=conn_assign # type: ignore [arg-type]
256
+ is_undirected=undir, conn_type=edge, conn_assign=conn_assign # type: ignore [arg-type]
258
257
  ),
259
258
  edges_only=edges_only,
260
259
  )
@@ -416,13 +415,7 @@ def field(
416
415
  jac_test = Jac.create_test
417
416
  static = ClassVar
418
417
 
419
- root = cast(Root, Jac.get_root())
420
418
 
421
-
422
- # Listen to context change and update the above global root here.
423
- def _update_root() -> None:
424
- global root
425
- root = cast(Root, ExecutionContext.get_root())
426
-
427
-
428
- ExecutionContext.on_ctx_change.append(lambda ctx: _update_root())
419
+ def root() -> Root:
420
+ """Get Root."""
421
+ return cast(Root, Jac.get_root())
@@ -945,45 +945,24 @@ class JacParser(Pass):
945
945
  kid=self.cur_nodes,
946
946
  )
947
947
 
948
- def param_var(self, kid: list[ast.AstNode]) -> ast.ParamVar:
948
+ def param_var(self, _: None) -> ast.ParamVar:
949
949
  """Grammar rule.
950
950
 
951
951
  param_var: (STAR_POW | STAR_MUL)? NAME (COLON STRING)? type_tag (EQ expression)?
952
952
  """
953
- star = (
954
- kid[0]
955
- if isinstance(kid[0], ast.Token)
956
- and kid[0].name != Tok.NAME
957
- and not isinstance(kid[0], ast.String)
958
- else None
959
- )
960
- name = kid[1] if (star) else kid[0]
961
- value = kid[-1] if isinstance(kid[-1], ast.Expr) else None
962
- type_tag = kid[-3] if value else kid[-1]
963
- semstr = (
964
- kid[3]
965
- if star and len(kid) > 3 and isinstance(kid[3], ast.String)
966
- else (
967
- kid[2]
968
- if len(kid) > 4 and value and isinstance(kid[2], ast.String)
969
- else (
970
- kid[2]
971
- if len(kid) > 2 and isinstance(kid[2], ast.String)
972
- else None
973
- )
974
- )
953
+ star = self.match_token(Tok.STAR_POW) or self.match_token(Tok.STAR_MUL)
954
+ name = self.consume(ast.Name)
955
+ semstr = self.match(ast.String) if self.match_token(Tok.COLON) else None
956
+ type_tag = self.consume(ast.SubTag)
957
+ value = self.consume(ast.Expr) if self.match_token(Tok.EQ) else None
958
+ return ast.ParamVar(
959
+ semstr=semstr,
960
+ name=name,
961
+ type_tag=type_tag,
962
+ value=value,
963
+ unpack=star,
964
+ kid=self.cur_nodes,
975
965
  )
976
- if isinstance(name, ast.Name) and isinstance(type_tag, ast.SubTag):
977
- return ast.ParamVar(
978
- semstr=semstr,
979
- name=name,
980
- type_tag=type_tag,
981
- value=value,
982
- unpack=star,
983
- kid=kid,
984
- )
985
- else:
986
- raise self.ice()
987
966
 
988
967
  def member_block(self, _: None) -> ast.SubNodeList[ast.ArchBlockStmt]:
989
968
  """Grammar rule.
@@ -1002,7 +981,7 @@ class JacParser(Pass):
1002
981
  ret.right_enc = right_enc
1003
982
  return ret
1004
983
 
1005
- def member_stmt(self, kid: list[ast.AstNode]) -> ast.ArchBlockStmt:
984
+ def member_stmt(self, _: None) -> ast.ArchBlockStmt:
1006
985
  """Grammar rule.
1007
986
 
1008
987
  member_stmt: doc_tag? py_code_block
@@ -1011,18 +990,11 @@ class JacParser(Pass):
1011
990
  | doc_tag? architype
1012
991
  | doc_tag? has_stmt
1013
992
  """
1014
- if isinstance(kid[0], ast.ArchBlockStmt):
1015
- ret = kid[0]
1016
- elif (
1017
- isinstance(kid[1], ast.ArchBlockStmt)
1018
- and isinstance(kid[1], ast.AstDocNode)
1019
- and isinstance(kid[0], ast.String)
1020
- ):
1021
- kid[1].doc = kid[0]
1022
- kid[1].add_kids_left([kid[0]])
1023
- ret = kid[1]
1024
- else:
1025
- raise self.ice()
993
+ doc = self.match(ast.String)
994
+ ret = self.consume(ast.ArchBlockStmt)
995
+ if doc and isinstance(ret, ast.AstDocNode):
996
+ ret.doc = doc
997
+ ret.add_kids_left([doc])
1026
998
  if isinstance(ret, ast.Ability):
1027
999
  ret.signature.is_method = True
1028
1000
  return ret
@@ -1072,27 +1044,30 @@ class JacParser(Pass):
1072
1044
  kid=new_kid,
1073
1045
  )
1074
1046
 
1075
- def typed_has_clause(self, kid: list[ast.AstNode]) -> ast.HasVar:
1047
+ def typed_has_clause(self, _: None) -> ast.HasVar:
1076
1048
  """Grammar rule.
1077
1049
 
1078
1050
  typed_has_clause: named_ref (COLON STRING)? type_tag (EQ expression | KW_BY KW_POST_INIT)?
1079
1051
  """
1080
- name = kid[0]
1081
- semstr = kid[2] if len(kid) > 2 and isinstance(kid[2], ast.String) else None
1082
- type_tag = kid[3] if semstr else kid[1]
1083
- defer = isinstance(kid[-1], ast.Token) and kid[-1].name == Tok.KW_POST_INIT
1084
- value = kid[-1] if not defer and isinstance(kid[-1], ast.Expr) else None
1085
- if isinstance(name, ast.Name) and isinstance(type_tag, ast.SubTag):
1086
- return ast.HasVar(
1087
- semstr=semstr,
1088
- name=name,
1089
- type_tag=type_tag,
1090
- defer=defer,
1091
- value=value,
1092
- kid=kid,
1093
- )
1094
- else:
1095
- raise self.ice()
1052
+ semstr: ast.String | None = None
1053
+ value: ast.Expr | None = None
1054
+ defer: bool = False
1055
+ name = self.consume(ast.Name)
1056
+ if self.match_token(Tok.COLON):
1057
+ semstr = self.consume(ast.String)
1058
+ type_tag = self.consume(ast.SubTag)
1059
+ if self.match_token(Tok.EQ):
1060
+ value = self.consume(ast.Expr)
1061
+ elif self.match_token(Tok.KW_BY):
1062
+ defer = bool(self.consume_token(Tok.KW_POST_INIT))
1063
+ return ast.HasVar(
1064
+ semstr=semstr,
1065
+ name=name,
1066
+ type_tag=type_tag,
1067
+ defer=defer,
1068
+ value=value,
1069
+ kid=self.cur_nodes,
1070
+ )
1096
1071
 
1097
1072
  def type_tag(self, _: None) -> ast.SubTag[ast.Expr]:
1098
1073
  """Grammar rule.
@@ -1425,21 +1400,22 @@ class JacParser(Pass):
1425
1400
  kid=self.cur_nodes,
1426
1401
  )
1427
1402
 
1428
- def raise_stmt(self, kid: list[ast.AstNode]) -> ast.RaiseStmt:
1403
+ def raise_stmt(self, _: None) -> ast.RaiseStmt:
1429
1404
  """Grammar rule.
1430
1405
 
1431
1406
  raise_stmt: KW_RAISE (expression (KW_FROM expression)?)?
1432
1407
  """
1433
- chomp = [*kid][1:]
1434
- e_type = (
1435
- chomp[0] if len(chomp) > 0 and isinstance(chomp[0], ast.Expr) else None
1436
- )
1437
- chomp = chomp[2:] if e_type and len(chomp) > 1 else chomp[1:]
1438
- e = chomp[0] if len(chomp) > 0 and isinstance(chomp[0], ast.Expr) else None
1408
+ e_type: ast.Expr | None = None
1409
+ from_target: ast.Expr | None = None
1410
+ self.consume_token(Tok.KW_RAISE)
1411
+ if e_type := self.match(ast.Expr):
1412
+ from_target = (
1413
+ self.consume(ast.Expr) if self.match_token(Tok.KW_FROM) else None
1414
+ )
1439
1415
  return ast.RaiseStmt(
1440
1416
  cause=e_type,
1441
- from_target=e,
1442
- kid=kid,
1417
+ from_target=from_target,
1418
+ kid=self.cur_nodes,
1443
1419
  )
1444
1420
 
1445
1421
  def assert_stmt(self, _: None) -> ast.AssertStmt:
@@ -2233,23 +2209,19 @@ class JacParser(Pass):
2233
2209
  kid=valid_parts,
2234
2210
  )
2235
2211
 
2236
- def list_val(self, kid: list[ast.AstNode]) -> ast.ListVal:
2212
+ def list_val(self, _: None) -> ast.ListVal:
2237
2213
  """Grammar rule.
2238
2214
 
2239
2215
  list_val: LSQUARE (expr_list COMMA?)? RSQUARE
2240
2216
  """
2241
- if len(kid) == 2:
2242
- return ast.ListVal(
2243
- values=None,
2244
- kid=kid,
2245
- )
2246
- elif isinstance(kid[1], ast.SubNodeList):
2247
- return ast.ListVal(
2248
- values=kid[1],
2249
- kid=kid,
2250
- )
2251
- else:
2252
- raise self.ice()
2217
+ self.consume_token(Tok.LSQUARE)
2218
+ values = self.match(ast.SubNodeList)
2219
+ self.match_token(Tok.COMMA)
2220
+ self.consume_token(Tok.RSQUARE)
2221
+ return ast.ListVal(
2222
+ values=values,
2223
+ kid=self.cur_nodes,
2224
+ )
2253
2225
 
2254
2226
  def tuple_val(self, _: None) -> ast.TupleVal:
2255
2227
  """Grammar rule.
@@ -2283,17 +2255,12 @@ class JacParser(Pass):
2283
2255
 
2284
2256
  expr_list: (expr_list COMMA)? expression
2285
2257
  """
2286
- consume = None
2287
- expr = None
2288
- comma = None
2289
- if isinstance(kid[0], ast.SubNodeList):
2290
- consume = kid[0]
2291
- comma = kid[1]
2292
- expr = kid[2]
2293
- new_kid = [*consume.kid, comma, expr]
2294
- else:
2295
- expr = kid[0]
2296
- new_kid = [expr]
2258
+ new_kid: list = []
2259
+ if consume := self.match(ast.SubNodeList):
2260
+ comma = self.consume_token(Tok.COMMA)
2261
+ new_kid.extend([*consume.kid, comma])
2262
+ expr = self.consume(ast.Expr)
2263
+ new_kid.extend([expr])
2297
2264
  valid_kid = [i for i in new_kid if isinstance(i, ast.Expr)]
2298
2265
  return ast.SubNodeList[ast.Expr](
2299
2266
  items=valid_kid,
@@ -2320,40 +2287,36 @@ class JacParser(Pass):
2320
2287
  kid=new_kid,
2321
2288
  )
2322
2289
 
2323
- def kw_expr(self, kid: list[ast.AstNode]) -> ast.KWPair:
2290
+ def kw_expr(self, _: None) -> ast.KWPair:
2324
2291
  """Grammar rule.
2325
2292
 
2326
2293
  kw_expr: named_ref EQ expression | STAR_POW expression
2327
2294
  """
2328
- if (
2329
- len(kid) == 3
2330
- and isinstance(kid[0], ast.NameAtom)
2331
- and isinstance(kid[2], ast.Expr)
2332
- ):
2333
- return ast.KWPair(
2334
- key=kid[0],
2335
- value=kid[2],
2336
- kid=kid,
2337
- )
2338
- elif len(kid) == 2 and isinstance(kid[1], ast.Expr):
2339
- return ast.KWPair(
2340
- key=None,
2341
- value=kid[1],
2342
- kid=kid,
2343
- )
2295
+ if self.match_token(Tok.STAR_POW):
2296
+ value = self.consume(ast.Expr)
2297
+ key = None
2344
2298
  else:
2345
- raise self.ice()
2299
+ key = self.consume(ast.Name)
2300
+ self.consume_token(Tok.EQ)
2301
+ value = self.consume(ast.Expr)
2302
+ return ast.KWPair(
2303
+ key=key,
2304
+ value=value,
2305
+ kid=self.cur_nodes,
2306
+ )
2346
2307
 
2347
- def name_list(self, kid: list[ast.AstNode]) -> ast.SubNodeList[ast.Name]:
2308
+ def name_list(self, _: None) -> ast.SubNodeList[ast.Name]:
2348
2309
  """Grammar rule.
2349
2310
 
2350
2311
  name_list: (named_ref COMMA)* named_ref
2351
2312
  """
2352
- valid_kid = [i for i in kid if isinstance(i, ast.Name)]
2313
+ valid_kid = [self.consume(ast.Name)]
2314
+ while self.match_token(Tok.COMMA):
2315
+ valid_kid.append(self.consume(ast.Name))
2353
2316
  return ast.SubNodeList[ast.Name](
2354
2317
  items=valid_kid,
2355
2318
  delim=Tok.COMMA,
2356
- kid=kid,
2319
+ kid=self.cur_nodes,
2357
2320
  )
2358
2321
 
2359
2322
  def tuple_list(self, _: None) -> ast.SubNodeList[ast.Expr | ast.KWPair]:
@@ -2536,23 +2499,17 @@ class JacParser(Pass):
2536
2499
  expr_list.kid.append(ends_comma)
2537
2500
  return expr_list
2538
2501
 
2539
- def assignment_list(
2540
- self, kid: list[ast.AstNode]
2541
- ) -> ast.SubNodeList[ast.Assignment]:
2502
+ def assignment_list(self, _: None) -> ast.SubNodeList[ast.Assignment]:
2542
2503
  """Grammar rule.
2543
2504
 
2544
2505
  assignment_list: assignment_list COMMA assignment | assignment
2545
2506
  """
2546
- consume = None
2547
- assign = None
2548
- comma = None
2549
- if isinstance(kid[0], ast.SubNodeList):
2550
- consume = kid[0]
2551
- comma = kid[1]
2552
- assign = kid[2]
2507
+ if consume := self.match(ast.SubNodeList):
2508
+ comma = self.consume_token(Tok.COMMA)
2509
+ assign = self.consume(ast.Assignment)
2553
2510
  new_kid = [*consume.kid, comma, assign]
2554
2511
  else:
2555
- assign = kid[0]
2512
+ assign = self.consume(ast.Assignment)
2556
2513
  new_kid = [assign]
2557
2514
  valid_kid = [i for i in new_kid if isinstance(i, ast.Assignment)]
2558
2515
  return ast.SubNodeList[ast.Assignment](
@@ -2685,93 +2642,79 @@ class JacParser(Pass):
2685
2642
  name = self.consume(ast.ArchRef)
2686
2643
  new_kid = [*consume.kid, name] if consume else [name]
2687
2644
  valid_kid = [i for i in new_kid if isinstance(i, ast.ArchRef)]
2688
- if len(valid_kid) == len(new_kid):
2689
- return ast.ArchRefChain(
2690
- archs=valid_kid,
2691
- kid=new_kid,
2692
- )
2693
- else:
2694
- raise self.ice()
2645
+ return ast.ArchRefChain(
2646
+ archs=valid_kid,
2647
+ kid=new_kid,
2648
+ )
2695
2649
 
2696
- def abil_to_arch_chain(self, kid: list[ast.AstNode]) -> ast.ArchRefChain:
2650
+ def abil_to_arch_chain(self, _: None) -> ast.ArchRefChain:
2697
2651
  """Grammar rule.
2698
2652
 
2699
2653
  abil_to_arch_chain: arch_or_ability_chain? arch_ref
2700
2654
  """
2701
- if len(kid) == 2:
2702
- if isinstance(kid[1], ast.ArchRef) and isinstance(
2703
- kid[0], ast.ArchRefChain
2704
- ):
2705
- return ast.ArchRefChain(
2706
- archs=[*(kid[0].archs), kid[1]],
2707
- kid=[*(kid[0].kid), kid[1]],
2708
- )
2709
- else:
2710
- raise self.ice()
2711
- elif isinstance(kid[0], ast.ArchRef):
2655
+ arch_chain = self.match(ast.ArchRefChain)
2656
+ arch_ref = self.consume(ast.ArchRef)
2657
+ if arch_chain:
2712
2658
  return ast.ArchRefChain(
2713
- archs=[kid[0]],
2714
- kid=kid,
2659
+ archs=[*arch_chain.archs, arch_ref],
2660
+ kid=[*arch_chain.kid, arch_ref],
2715
2661
  )
2716
- else:
2717
- raise self.ice()
2662
+ return ast.ArchRefChain(
2663
+ archs=[arch_ref],
2664
+ kid=[arch_ref],
2665
+ )
2718
2666
 
2719
- def arch_to_abil_chain(self, kid: list[ast.AstNode]) -> ast.ArchRefChain:
2667
+ def arch_to_abil_chain(self, _: None) -> ast.ArchRefChain:
2720
2668
  """Grammar rule.
2721
2669
 
2722
2670
  arch_to_abil_chain: arch_or_ability_chain? ability_ref
2723
2671
  """
2724
- if len(kid) == 2:
2725
- if isinstance(kid[1], ast.ArchRef) and isinstance(
2726
- kid[0], ast.ArchRefChain
2727
- ):
2728
- return ast.ArchRefChain(
2729
- archs=[*(kid[0].archs), kid[1]],
2730
- kid=[*(kid[0].kid), kid[1]],
2731
- )
2732
- else:
2733
- raise self.ice()
2734
- elif isinstance(kid[0], ast.ArchRef):
2672
+ arch_chain = self.match(ast.ArchRefChain)
2673
+ abil_ref = self.consume(ast.ArchRef)
2674
+ if arch_chain:
2735
2675
  return ast.ArchRefChain(
2736
- archs=[kid[0]],
2737
- kid=kid,
2676
+ archs=[*arch_chain.archs, abil_ref],
2677
+ kid=[*arch_chain.kid, abil_ref],
2738
2678
  )
2739
- else:
2740
- raise self.ice()
2679
+ return ast.ArchRefChain(
2680
+ archs=[abil_ref],
2681
+ kid=[abil_ref],
2682
+ )
2741
2683
 
2742
- def arch_to_enum_chain(self, kid: list[ast.AstNode]) -> ast.ArchRefChain:
2684
+ def arch_to_enum_chain(self, _: None) -> ast.ArchRefChain:
2743
2685
  """Grammar rule.
2744
2686
 
2745
2687
  arch_to_enum_chain: arch_or_ability_chain? enum_ref
2746
2688
  """
2747
- if len(kid) == 2:
2748
- if isinstance(kid[1], ast.ArchRef) and isinstance(
2749
- kid[0], ast.ArchRefChain
2750
- ):
2751
- return ast.ArchRefChain(
2752
- archs=[*(kid[0].archs), kid[1]],
2753
- kid=[*(kid[0].kid), kid[1]],
2754
- )
2755
- else:
2756
- raise self.ice()
2757
- elif isinstance(kid[0], ast.ArchRef):
2689
+ arch_chain = self.match(ast.ArchRefChain)
2690
+ enum_ref = self.consume(ast.ArchRef)
2691
+ if arch_chain:
2758
2692
  return ast.ArchRefChain(
2759
- archs=[kid[0]],
2760
- kid=kid,
2693
+ archs=[*arch_chain.archs, enum_ref],
2694
+ kid=[*arch_chain.kid, enum_ref],
2761
2695
  )
2762
- else:
2763
- raise self.ice()
2696
+ return ast.ArchRefChain(
2697
+ archs=[enum_ref],
2698
+ kid=[enum_ref],
2699
+ )
2764
2700
 
2765
- def edge_ref_chain(self, kid: list[ast.AstNode]) -> ast.EdgeRefTrailer:
2701
+ def edge_ref_chain(self, _: None) -> ast.EdgeRefTrailer:
2766
2702
  """Grammar rule.
2767
2703
 
2768
2704
  (EDGE_OP|NODE_OP)? LSQUARE expression? (edge_op_ref (filter_compr | expression)?)+ RSQUARE
2769
2705
  """
2770
- valid_chain = [i for i in kid if isinstance(i, (ast.Expr, ast.FilterCompr))]
2706
+ edges_only = bool(self.match_token(Tok.EDGE_OP))
2707
+ self.match_token(Tok.NODE_OP)
2708
+ self.consume_token(Tok.LSQUARE)
2709
+ valid_chain = []
2710
+ if expr := self.match(ast.Expr):
2711
+ valid_chain.append(expr)
2712
+ valid_chain.extend(self.match_many(ast.Expr))
2713
+ self.consume_token(Tok.RSQUARE)
2771
2714
  return ast.EdgeRefTrailer(
2772
2715
  chain=valid_chain,
2773
- edges_only=isinstance(kid[0], ast.Token) and kid[0].name == Tok.EDGE_OP,
2774
- kid=kid,
2716
+ edges_only=edges_only,
2717
+ kid=self.cur_nodes,
2775
2718
  )
2776
2719
 
2777
2720
  def edge_op_ref(self, kid: list[ast.AstNode]) -> ast.EdgeOpRef:
@@ -2987,27 +2930,16 @@ class JacParser(Pass):
2987
2930
  kid=new_kid,
2988
2931
  )
2989
2932
 
2990
- def typed_filter_compare_list(self, kid: list[ast.AstNode]) -> ast.FilterCompr:
2933
+ def typed_filter_compare_list(self, _: None) -> ast.FilterCompr:
2991
2934
  """Grammar rule.
2992
2935
 
2993
2936
  typed_filter_compare_list: expression (COLON filter_compare_list)?
2994
2937
  """
2995
- chomp = [*kid]
2996
- expr = chomp[0]
2997
- chomp = chomp[1:]
2998
- compares = (
2999
- chomp[1]
3000
- if len(chomp)
3001
- and isinstance(chomp[0], ast.Token)
3002
- and chomp[0].name == Tok.COLON
3003
- else None
3004
- )
3005
- if isinstance(expr, ast.Expr) and (
3006
- (isinstance(compares, ast.SubNodeList)) or compares is None
3007
- ):
3008
- return ast.FilterCompr(compares=compares, f_type=expr, kid=kid)
3009
- else:
3010
- raise self.ice()
2938
+ compares: ast.SubNodeList | None = None
2939
+ expr = self.consume(ast.Expr)
2940
+ if self.match_token(Tok.COLON):
2941
+ compares = self.consume(ast.SubNodeList)
2942
+ return ast.FilterCompr(compares=compares, f_type=expr, kid=self.cur_nodes)
3011
2943
 
3012
2944
  def filter_compare_item(self, _: None) -> ast.CompareExpr:
3013
2945
  """Grammar rule.
@@ -2937,7 +2937,15 @@ class PyastGenPass(Pass):
2937
2937
  )
2938
2938
  ]
2939
2939
  elif node.name == Tok.KW_ROOT:
2940
- node.gen.py_ast = [self.jaclib_obj("root")]
2940
+ node.gen.py_ast = [
2941
+ self.sync(
2942
+ ast3.Call(
2943
+ func=self.jaclib_obj("root"),
2944
+ args=[],
2945
+ keywords=[],
2946
+ )
2947
+ )
2948
+ ]
2941
2949
 
2942
2950
  else:
2943
2951
  node.gen.py_ast = [
@@ -3118,7 +3126,7 @@ class PyastGenPass(Pass):
3118
3126
  self.sync(
3119
3127
  ast3.keyword(
3120
3128
  arg="target",
3121
- value=self.sync(ast3.Constant(value=None)),
3129
+ value=targ,
3122
3130
  )
3123
3131
  )
3124
3132
  )
@@ -5,7 +5,7 @@ from __future__ import annotations
5
5
  import unittest
6
6
  from contextvars import ContextVar
7
7
  from dataclasses import MISSING
8
- from typing import Any, Callable, ClassVar, Optional, cast
8
+ from typing import Any, Callable, Optional, cast
9
9
  from uuid import UUID
10
10
 
11
11
  from .architype import NodeAnchor, Root
@@ -26,9 +26,6 @@ class ExecutionContext:
26
26
  root: NodeAnchor
27
27
  entry_node: NodeAnchor
28
28
 
29
- # A context change event subscription list, those who want to listen ctx change will register here.
30
- on_ctx_change: ClassVar[list[Callable[[ExecutionContext | None], None]]] = []
31
-
32
29
  def init_anchor(
33
30
  self,
34
31
  anchor_id: str | None,
@@ -49,8 +46,6 @@ class ExecutionContext:
49
46
  """Close current ExecutionContext."""
50
47
  self.mem.close()
51
48
  EXECUTION_CONTEXT.set(None)
52
- for func in ExecutionContext.on_ctx_change:
53
- func(EXECUTION_CONTEXT.get(None))
54
49
 
55
50
  @staticmethod
56
51
  def create(
@@ -80,8 +75,6 @@ class ExecutionContext:
80
75
  old_ctx.close()
81
76
 
82
77
  EXECUTION_CONTEXT.set(ctx)
83
- for func in ExecutionContext.on_ctx_change:
84
- func(EXECUTION_CONTEXT.get(None))
85
78
 
86
79
  return ctx
87
80
 
@@ -16,7 +16,7 @@ with entry{
16
16
  x=[a(aa=x) for x in range(0,3)];
17
17
  y=[b(bb=x) for x in range(0,3)];
18
18
  z=[c(cc=x) for x in range(0,3)];
19
- x++>y;
19
+ x<++>y; # just adding one trigger of undirected connect
20
20
  y++>z;
21
21
  apple: int;
22
22
  # print(x -:aaa:-> );
@@ -0,0 +1,17 @@
1
+
2
+ node a { has val:int=0; }
3
+ node b { has val:int=0; }
4
+ node c { has val:int=0; }
5
+
6
+ with entry {
7
+
8
+ x = [a(val=i) for i in range(0,3)];
9
+ y = [b(val=i) for i in range(0,3)];
10
+ z = [c(val=i) for i in range(0,3)];
11
+
12
+ x ++> y;
13
+ y ++> z;
14
+
15
+ print([x-->y-->z]); # [c(val=0), c(val=1), c(val=2)]
16
+ print([x-->y[:1]-->z[:1]]); # [c(val=0)]
17
+ }
@@ -694,6 +694,19 @@ class JacLanguageTests(TestCase):
694
694
  self.assertIn(" case Point(x = int(_), y = 0):\n", output)
695
695
  self.assertIn("class Sample {\n can init", output)
696
696
 
697
+ def test_refs_target(self) -> None:
698
+ """
699
+ This test added after a bug in jaclib Node.refs() wasn't code gen as expected and it
700
+ wasn't captured with the tests.
701
+ """
702
+ captured_output = io.StringIO()
703
+ sys.stdout = captured_output
704
+ jac_import("refs_target", base_path=self.fixture_abs_path("./"))
705
+ sys.stdout = sys.__stdout__
706
+ stdout_value = captured_output.getvalue()
707
+ self.assertIn("[c(val=0), c(val=1), c(val=2)]", stdout_value)
708
+ self.assertIn("[c(val=0)]", stdout_value)
709
+
697
710
  def test_py_kw_as_name_disallowed(self) -> None:
698
711
  """Basic precedence test."""
699
712
  prog = jac_str_to_pass("with entry {print.is.not.True(4-5-4);}", "test.jac")
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.3
2
2
  Name: jaclang
3
- Version: 0.7.32
3
+ Version: 0.7.34
4
4
  Summary: Jac is a unique and powerful programming language that runs on top of Python, offering an unprecedented level of intelligence and intuitive understanding.
5
5
  License: MIT
6
6
  Keywords: jac,jaclang,jaseci,python,programming-language,machine-learning,artificial-intelligence
@@ -1,4 +1,4 @@
1
- jaclang/__init__.py,sha256=bx1J_RA6dyXlj6jp7hSjTvbm_xO4MV7ZSW82mg0qxqs,13112
1
+ jaclang/__init__.py,sha256=IuVtsbIpKPtdlV_EE-UjXLGxI3go-y3-sJ3slLGxOSY,12866
2
2
  jaclang/cli/.gitignore,sha256=NYuons2lzuCpCdefMnztZxeSMgtPVJF6R6zSgVDOV20,27
3
3
  jaclang/cli/__init__.py,sha256=7aaPgYddIAHBvkdv36ngbfwsimMnfGaTDcaHYMg_vf4,23
4
4
  jaclang/cli/cli.md,sha256=4BPJGdcyvs_rXgd_DPEGjkKSGe5ureXXYaQsf-_z_LU,5939
@@ -11,7 +11,7 @@ jaclang/compiler/codeloc.py,sha256=clz7ofOE0Rgf7eqco3zEO31mCbG3Skj9-rLooliBeik,2
11
11
  jaclang/compiler/compile.py,sha256=FD3jxK8zoxdpQrYRJvwO3CoPWjYL3bbW2WhPRzj3hz8,3796
12
12
  jaclang/compiler/constant.py,sha256=4aS0haM9X7WI0mJmzsWuEecF1yWHadC1lOLGOOUyNY0,8994
13
13
  jaclang/compiler/jac.lark,sha256=SzEc1Ae6Q8QUtBzW1R3OnPTQMpiQGrN-PE25TL_psAs,19848
14
- jaclang/compiler/parser.py,sha256=3OG4H43kMCSufKoy4EBoIKiuEj5fFk7QOwqJb-lMJFU,121426
14
+ jaclang/compiler/parser.py,sha256=-gqlJLUA2oXCj4BvnGu7UvKlELZLcJtUAKmWx6yhB08,119268
15
15
  jaclang/compiler/passes/__init__.py,sha256=0Tw0d130ZjzA05jVcny9cf5NfLjlaM70PKqFnY4zqn4,69
16
16
  jaclang/compiler/passes/ir_pass.py,sha256=CgtuBrVjfG7PgTCLNSjxgFffYR5naTC3tIjOjsXx5gk,5597
17
17
  jaclang/compiler/passes/main/__init__.py,sha256=m5ukLwMcdoi85Ee80-A-zDLbg81z0ztT2IKhOCegNpE,973
@@ -22,7 +22,7 @@ jaclang/compiler/passes/main/fuse_typeinfo_pass.py,sha256=bjxeE_90AFy9jN9VomOsoy
22
22
  jaclang/compiler/passes/main/import_pass.py,sha256=ouOuVzA_wloNG_t3Ec9gTEu6JuPZtwXiL6Kgtoan6gc,23090
23
23
  jaclang/compiler/passes/main/inheritance_pass.py,sha256=IDzfMSezJmNdBwN_dwguu1qYL8YzwBuNPFrk6HEkTco,5586
24
24
  jaclang/compiler/passes/main/py_collect_dep_pass.py,sha256=TE4h6HLYRE5YdHZK9gtbPPaBJBLOg0g0xSlT_oPzwzY,2874
25
- jaclang/compiler/passes/main/pyast_gen_pass.py,sha256=jeBpx-vxo0_OODMm82iCF6Fl1xNgQKFa1gt63AWw8zY,133057
25
+ jaclang/compiler/passes/main/pyast_gen_pass.py,sha256=Qk6xW95Dkb-WStEyiq8ZEGVST61eJdcSEdvez1BxFyo,133237
26
26
  jaclang/compiler/passes/main/pyast_load_pass.py,sha256=VmlR1j0iY60nFF9DrWVwWrvpUDZpXamkfoyF7miqysA,94697
27
27
  jaclang/compiler/passes/main/pybc_gen_pass.py,sha256=CjA9AqyMO3Pv_b5Hh0YI6JmCqIru2ASonO6rhrkau-M,1336
28
28
  jaclang/compiler/passes/main/pyjac_ast_link_pass.py,sha256=snbqUIPtPcD9ZKsItOlKGVnujoMGFwF8XNP0GvxS9AI,8628
@@ -188,7 +188,7 @@ jaclang/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
188
188
  jaclang/runtimelib/__init__.py,sha256=jDDYBCV82qPhmcDVk3NIvHbhng0ebSrXD3xrojg0-eo,34
189
189
  jaclang/runtimelib/architype.py,sha256=rcxXe34Vtoz-tNQPqPHmmnh2-G_iJJCjfdXDO5k9kQc,8474
190
190
  jaclang/runtimelib/constructs.py,sha256=1ARnsPrDi1UvyaFRhGRhO0kj0fnIZ2HbHF7O3itB-ZQ,796
191
- jaclang/runtimelib/context.py,sha256=xYg1DT85YIN0AhH16mTYYoQDjqUSPHmr9As611NITRI,6303
191
+ jaclang/runtimelib/context.py,sha256=rO-eqBcT4tVWPcraa17IKyMkyY8NDk6cvPBQVK-0Sdg,5910
192
192
  jaclang/runtimelib/importer.py,sha256=A2YIoPTPaRYvIrj3JZL7bDOyxFpU25Ld-V_fWQMsTbE,15650
193
193
  jaclang/runtimelib/machine.py,sha256=JvJiuh_QSFmqHIwWsOXb1pRPdAmM7sadUzWkNpb6jJc,11571
194
194
  jaclang/runtimelib/memory.py,sha256=LrVTo6Cac0q-YG1wug-Fgc8O2Tue9zRHnxSulDw3ZQ4,5656
@@ -233,7 +233,7 @@ jaclang/tests/fixtures/deep_convo.py,sha256=sxU9RYsFIDlsbgNIQv6FBNgQHYEQ0Dwvx1f_
233
233
  jaclang/tests/fixtures/deep_import.jac,sha256=3VokNO4A_cjz4ZbRnJdaVAGwdRbbVL65m9jM3Cm2eEo,115
234
234
  jaclang/tests/fixtures/deep_import_mods.jac,sha256=MBGytfHfyVA9GjH9wKJ1iLyAdNkRj6uPzFF9fv11iWk,260
235
235
  jaclang/tests/fixtures/deferred_field.jac,sha256=pOO6YT7vwkGr4frOSvWzGx3pO5jyZxeQInuEukcVF_Q,177
236
- jaclang/tests/fixtures/disconn.jac,sha256=gRbNh6R6t-cTdB6lT4M7HW7cdGoYoGV5Bnp3NhW7DX4,517
236
+ jaclang/tests/fixtures/disconn.jac,sha256=vFBCpj089FTpzIBGuy6HC6YXE2L8lLixKvkLx4477DE,566
237
237
  jaclang/tests/fixtures/dynamic_architype.jac,sha256=jt74XfBZc5A6yWdk_DOTUhAg__TM_l6biHOxzTWQXq8,1015
238
238
  jaclang/tests/fixtures/edge_node_walk.jac,sha256=x_eD24TBYFv9xLgaDevE-7klwJT9oj0dpCOeZe72wNs,959
239
239
  jaclang/tests/fixtures/edge_ops.jac,sha256=b6XsApxIQUelPPAfReQor3ha2iDtAbNVpcihxTOyTgs,967
@@ -299,6 +299,7 @@ jaclang/tests/fixtures/pygame_mock/inner/__init__.py,sha256=47DEQpj8HBSa-_TImW-5
299
299
  jaclang/tests/fixtures/pygame_mock/inner/iner_mod.py,sha256=6_vik8u9cHHQKWMtzRegqOtVdXsTP72Obh4K0M98KDY,38
300
300
  jaclang/tests/fixtures/random_check.jac,sha256=o8MxWK9_QjxQh9nxBQKYUdsaxIPxlzUJFpxPr-lU588,1523
301
301
  jaclang/tests/fixtures/raw_byte_string.jac,sha256=y5FA0rtLC5do8vqXfCxCF1TP7l8L20nI56WRFdu8x9k,337
302
+ jaclang/tests/fixtures/refs_target.jac,sha256=Whexw4-xErg7vlV-1NB3cp0bNOP8u0df0QSrupTkJEY,347
302
303
  jaclang/tests/fixtures/registry.jac,sha256=huAQGtL_5wtpiP4C675hU6mWFNrrACY_Oc0n5IV0YdI,1450
303
304
  jaclang/tests/fixtures/run_test.jac,sha256=kR-kwJQ-UiRpJOZnhXws3Vqa4eK64-85rz72t9Zr94k,164
304
305
  jaclang/tests/fixtures/semstr.jac,sha256=hC7oSmHIkPOHzS7r3lv8VkiBAmi2D525uKIugo_XL9I,739
@@ -321,7 +322,7 @@ jaclang/tests/foo/__init__.jac,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuF
321
322
  jaclang/tests/main.jac,sha256=UJ4dASLCMA3wW78Rq3AHcq5GfXVY5QBm2S16OCrR1hQ,13
322
323
  jaclang/tests/test_bugs.py,sha256=tBPsIlSPqZDIz4QaScNRT-WdGIdJ0uU-aRBWq1XUZ6o,555
323
324
  jaclang/tests/test_cli.py,sha256=j79-e3lVk_oBuy6pAwfjE8D-q5UsUQxEF5yoexWj8Jg,20040
324
- jaclang/tests/test_language.py,sha256=znQDqixddJMGS5MYr7FZIbdQ4uO41yqermdVbcmAdFI,51745
325
+ jaclang/tests/test_language.py,sha256=gwQx7lFqhJ9deCzFNzjbJwri3928zZVO8ECm3iqyh5c,52299
325
326
  jaclang/tests/test_man_code.py,sha256=ZdNarlZVfT_-8Jv3FjLplHw76tsvkCuISyfX3M4qxPg,5027
326
327
  jaclang/tests/test_reference.py,sha256=vZC0P1zptbxzc9CwgbhqA2tGVML_ptL8tON9Czh_dJg,3359
327
328
  jaclang/tests/test_settings.py,sha256=TIX5uiu8H9IpZN2__uFiclcdCpBpPpcAwtlEHyFC4kk,1999
@@ -1556,7 +1557,7 @@ jaclang/vendor/typing_extensions-4.12.2.dist-info/METADATA,sha256=BeUQIa8cnYbrjW
1556
1557
  jaclang/vendor/typing_extensions-4.12.2.dist-info/RECORD,sha256=XS4fBVrPI7kaNZ56Ggl2RGa76jySWLqTzcrUpZIQTVM,418
1557
1558
  jaclang/vendor/typing_extensions-4.12.2.dist-info/WHEEL,sha256=EZbGkh7Ie4PoZfRQ8I0ZuP9VklN_TvcZ6DSE5Uar4z4,81
1558
1559
  jaclang/vendor/typing_extensions.py,sha256=gwekpyG9DVG3lxWKX4ni8u7nk3We5slG98mA9F3DJQw,134451
1559
- jaclang-0.7.32.dist-info/METADATA,sha256=ceJwm1Seys2lWaURbPqWVexHsrF0sZT6fZBczWy97ro,4977
1560
- jaclang-0.7.32.dist-info/WHEEL,sha256=XbeZDeTWKc1w7CSIyre5aMDU_-PohRwTQceYnisIYYY,88
1561
- jaclang-0.7.32.dist-info/entry_points.txt,sha256=8sMi4Tvi9f8tQDN2QAXsSA2icO27zQ4GgEdph6bNEZM,49
1562
- jaclang-0.7.32.dist-info/RECORD,,
1560
+ jaclang-0.7.34.dist-info/METADATA,sha256=VHuSrkugGMvGwf6FMEnETskGUAKWWmyMpz00WBXrQC8,4977
1561
+ jaclang-0.7.34.dist-info/WHEEL,sha256=XbeZDeTWKc1w7CSIyre5aMDU_-PohRwTQceYnisIYYY,88
1562
+ jaclang-0.7.34.dist-info/entry_points.txt,sha256=8sMi4Tvi9f8tQDN2QAXsSA2icO27zQ4GgEdph6bNEZM,49
1563
+ jaclang-0.7.34.dist-info/RECORD,,