@@ -4048,7 +4048,7 @@ and parse_array_exp p =
4048
4048
4049
4049
(* TODO: check attributes in the case of poly type vars,
4050
4050
* might be context dependend: parseFieldDeclaration (see ocaml) *)
4051
- and parse_poly_type_expr p =
4051
+ and parse_poly_type_expr ? current_type_name_path ? inline_types p =
4052
4052
let start_pos = p.Parser. start_pos in
4053
4053
match p.Parser. token with
4054
4054
| SingleQuote -> (
@@ -4075,7 +4075,7 @@ and parse_poly_type_expr p =
4075
4075
return_type
4076
4076
| _ -> Ast_helper.Typ. var ~loc: var.loc var.txt)
4077
4077
| _ -> assert false )
4078
- | _ -> parse_typ_expr p
4078
+ | _ -> parse_typ_expr ?current_type_name_path ?inline_types p
4079
4079
4080
4080
(* 'a 'b 'c *)
4081
4081
and parse_type_var_list p =
@@ -4103,7 +4103,7 @@ and parse_lident_list p =
4103
4103
in
4104
4104
loop p []
4105
4105
4106
- and parse_atomic_typ_expr ~attrs p =
4106
+ and parse_atomic_typ_expr ? current_type_name_path ? inline_types ~attrs p =
4107
4107
Parser. leave_breadcrumb p Grammar. AtomicTypExpr ;
4108
4108
let start_pos = p.Parser. start_pos in
4109
4109
let typ =
@@ -4160,7 +4160,8 @@ and parse_atomic_typ_expr ~attrs p =
4160
4160
let extension = parse_extension p in
4161
4161
let loc = mk_loc start_pos p.prev_end_pos in
4162
4162
Ast_helper.Typ. extension ~attrs ~loc extension
4163
- | Lbrace -> parse_record_or_object_type ~attrs p
4163
+ | Lbrace ->
4164
+ parse_record_or_object_type ?current_type_name_path ?inline_types ~attrs p
4164
4165
| Eof ->
4165
4166
Parser. err p (Diagnostics. unexpected p.Parser. token p.breadcrumbs);
4166
4167
Recover. default_type ()
@@ -4222,7 +4223,7 @@ and parse_package_constraint p =
4222
4223
Some (type_constr, typ)
4223
4224
| _ -> None
4224
4225
4225
- and parse_record_or_object_type ~attrs p =
4226
+ and parse_record_or_object_type ? current_type_name_path ? inline_types ~attrs p =
4226
4227
(* for inline record in constructor *)
4227
4228
let start_pos = p.Parser. start_pos in
4228
4229
Parser. expect Lbrace p;
@@ -4236,20 +4237,39 @@ and parse_record_or_object_type ~attrs p =
4236
4237
Asttypes. Closed
4237
4238
| _ -> Asttypes. Closed
4238
4239
in
4239
- let () =
4240
- match p.token with
4241
- | Lident _ ->
4242
- Parser. err p
4243
- (Diagnostics. message ErrorMessages. forbidden_inline_record_declaration)
4244
- | _ -> ()
4245
- in
4246
- let fields =
4247
- parse_comma_delimited_region ~grammar: Grammar. StringFieldDeclarations
4248
- ~closing: Rbrace ~f: parse_string_field_declaration p
4249
- in
4250
- Parser. expect Rbrace p;
4251
- let loc = mk_loc start_pos p.prev_end_pos in
4252
- Ast_helper.Typ. object_ ~loc ~attrs fields closed_flag
4240
+ match (p.token, inline_types, current_type_name_path) with
4241
+ | Lident _ , Some inline_types , Some current_type_name_path ->
4242
+ let labels =
4243
+ parse_comma_delimited_region ~grammar: Grammar. RecordDecl ~closing: Rbrace
4244
+ ~f:
4245
+ (parse_field_declaration_region ~current_type_name_path ~inline_types )
4246
+ p
4247
+ in
4248
+ Parser. expect Rbrace p;
4249
+ let loc = mk_loc start_pos p.prev_end_pos in
4250
+ let inline_type_name = current_type_name_path |> String. concat " ." in
4251
+ inline_types :=
4252
+ (inline_type_name, loc, Parsetree. Ptype_record labels) :: ! inline_types;
4253
+
4254
+ let lid = Location. mkloc (Longident. Lident inline_type_name) loc in
4255
+ Ast_helper.Typ. constr
4256
+ ~attrs: [(Location. mknoloc " inlineRecordReference" , PStr [] )]
4257
+ ~loc lid []
4258
+ | _ ->
4259
+ let () =
4260
+ match p.token with
4261
+ | Lident _ ->
4262
+ Parser. err p
4263
+ (Diagnostics. message ErrorMessages. forbidden_inline_record_declaration)
4264
+ | _ -> ()
4265
+ in
4266
+ let fields =
4267
+ parse_comma_delimited_region ~grammar: Grammar. StringFieldDeclarations
4268
+ ~closing: Rbrace ~f: parse_string_field_declaration p
4269
+ in
4270
+ Parser. expect Rbrace p;
4271
+ let loc = mk_loc start_pos p.prev_end_pos in
4272
+ Ast_helper.Typ. object_ ~loc ~attrs fields closed_flag
4253
4273
4254
4274
(* TODO: check associativity in combination with attributes *)
4255
4275
and parse_type_alias p typ =
@@ -4458,7 +4478,8 @@ and parse_es6_arrow_type ~attrs p =
4458
4478
* | uident.lident
4459
4479
* | uident.uident.lident --> long module path
4460
4480
*)
4461
- and parse_typ_expr ?attrs ?(es6_arrow = true ) ?(alias = true ) p =
4481
+ and parse_typ_expr ?current_type_name_path ?inline_types ?attrs
4482
+ ?(es6_arrow = true ) ?(alias = true ) p =
4462
4483
(* Parser.leaveBreadcrumb p Grammar.TypeExpression; *)
4463
4484
let start_pos = p.Parser. start_pos in
4464
4485
let attrs =
@@ -4469,7 +4490,9 @@ and parse_typ_expr ?attrs ?(es6_arrow = true) ?(alias = true) p =
4469
4490
let typ =
4470
4491
if es6_arrow && is_es6_arrow_type p then parse_es6_arrow_type ~attrs p
4471
4492
else
4472
- let typ = parse_atomic_typ_expr ~attrs p in
4493
+ let typ =
4494
+ parse_atomic_typ_expr ?current_type_name_path ?inline_types ~attrs p
4495
+ in
4473
4496
parse_arrow_type_rest ~es6_arrow ~start_pos typ p
4474
4497
in
4475
4498
let typ = if alias then parse_type_alias p typ else typ in
@@ -4610,7 +4633,8 @@ and parse_field_declaration p =
4610
4633
let loc = mk_loc start_pos typ.ptyp_loc.loc_end in
4611
4634
Ast_helper.Type. field ~attrs ~loc ~mut ~optional name typ
4612
4635
4613
- and parse_field_declaration_region ?found_object_field p =
4636
+ and parse_field_declaration_region ?current_type_name_path ?inline_types
4637
+ ?found_object_field p =
4614
4638
let start_pos = p.Parser. start_pos in
4615
4639
let attrs = parse_attributes p in
4616
4640
let mut =
@@ -4635,12 +4659,17 @@ and parse_field_declaration_region ?found_object_field p =
4635
4659
| Lident _ ->
4636
4660
let lident, loc = parse_lident p in
4637
4661
let name = Location. mkloc lident loc in
4662
+ let current_type_name_path =
4663
+ match current_type_name_path with
4664
+ | None -> None
4665
+ | Some current_type_name_path -> Some (current_type_name_path @ [name.txt])
4666
+ in
4638
4667
let optional = parse_optional_label p in
4639
4668
let typ =
4640
4669
match p.Parser. token with
4641
4670
| Colon ->
4642
4671
Parser. next p;
4643
- parse_poly_type_expr p
4672
+ parse_poly_type_expr ?current_type_name_path ?inline_types p
4644
4673
| _ ->
4645
4674
Ast_helper.Typ. constr ~loc: name.loc ~attrs
4646
4675
{name with txt = Lident name.txt}
@@ -4666,12 +4695,13 @@ and parse_field_declaration_region ?found_object_field p =
4666
4695
* | { field-decl, field-decl }
4667
4696
* | { field-decl, field-decl, field-decl, }
4668
4697
*)
4669
- and parse_record_declaration p =
4698
+ and parse_record_declaration ? current_type_name_path ? inline_types p =
4670
4699
Parser. leave_breadcrumb p Grammar. RecordDecl ;
4671
4700
Parser. expect Lbrace p;
4672
4701
let rows =
4673
4702
parse_comma_delimited_region ~grammar: Grammar. RecordDecl ~closing: Rbrace
4674
- ~f: parse_field_declaration_region p
4703
+ ~f: (parse_field_declaration_region ?current_type_name_path ?inline_types)
4704
+ p
4675
4705
in
4676
4706
Parser. expect Rbrace p;
4677
4707
Parser. eat_breadcrumb p;
@@ -4914,7 +4944,7 @@ and parse_type_constructor_declarations ?first p =
4914
4944
* ∣ = private record-decl
4915
4945
* | = ..
4916
4946
*)
4917
- and parse_type_representation p =
4947
+ and parse_type_representation ? current_type_name_path ? inline_types p =
4918
4948
Parser. leave_breadcrumb p Grammar. TypeRepresentation ;
4919
4949
(* = consumed *)
4920
4950
let private_flag =
@@ -4925,7 +4955,9 @@ and parse_type_representation p =
4925
4955
match p.Parser. token with
4926
4956
| Bar | Uident _ ->
4927
4957
Parsetree. Ptype_variant (parse_type_constructor_declarations p)
4928
- | Lbrace -> Parsetree. Ptype_record (parse_record_declaration p)
4958
+ | Lbrace ->
4959
+ Parsetree. Ptype_record
4960
+ (parse_record_declaration ?current_type_name_path ?inline_types p)
4929
4961
| DotDot ->
4930
4962
Parser. next p;
4931
4963
Ptype_open
@@ -5117,7 +5149,7 @@ and parse_type_equation_or_constr_decl p =
5117
5149
(* TODO: is this a good idea? *)
5118
5150
(None , Asttypes. Public , Parsetree. Ptype_abstract )
5119
5151
5120
- and parse_record_or_object_decl p =
5152
+ and parse_record_or_object_decl ? current_type_name_path ? inline_types p =
5121
5153
let start_pos = p.Parser. start_pos in
5122
5154
Parser. expect Lbrace p;
5123
5155
match p.Parser. token with
@@ -5173,7 +5205,9 @@ and parse_record_or_object_decl p =
5173
5205
let found_object_field = ref false in
5174
5206
let fields =
5175
5207
parse_comma_delimited_region ~grammar: Grammar. RecordDecl ~closing: Rbrace
5176
- ~f: (parse_field_declaration_region ~found_object_field )
5208
+ ~f:
5209
+ (parse_field_declaration_region ?current_type_name_path
5210
+ ?inline_types ~found_object_field )
5177
5211
p
5178
5212
in
5179
5213
Parser. expect Rbrace p;
@@ -5244,7 +5278,11 @@ and parse_record_or_object_decl p =
5244
5278
match attrs with
5245
5279
| [] ->
5246
5280
parse_comma_delimited_region ~grammar: Grammar. FieldDeclarations
5247
- ~closing: Rbrace ~f: parse_field_declaration_region p
5281
+ ~closing: Rbrace
5282
+ ~f:
5283
+ (parse_field_declaration_region ?current_type_name_path
5284
+ ?inline_types)
5285
+ p
5248
5286
| attr :: _ as attrs ->
5249
5287
let first =
5250
5288
let field = parse_field_declaration p in
@@ -5261,7 +5299,11 @@ and parse_record_or_object_decl p =
5261
5299
in
5262
5300
first
5263
5301
:: parse_comma_delimited_region ~grammar: Grammar. FieldDeclarations
5264
- ~closing: Rbrace ~f: parse_field_declaration_region p
5302
+ ~closing: Rbrace
5303
+ ~f:
5304
+ (parse_field_declaration_region ?current_type_name_path
5305
+ ?inline_types)
5306
+ p
5265
5307
in
5266
5308
Parser. expect Rbrace p;
5267
5309
Parser. eat_breadcrumb p;
@@ -5451,14 +5493,16 @@ and parse_polymorphic_variant_type_args p =
5451
5493
| [typ] -> typ
5452
5494
| types -> Ast_helper.Typ. tuple ~loc ~attrs types
5453
5495
5454
- and parse_type_equation_and_representation p =
5496
+ and parse_type_equation_and_representation ?current_type_name_path ?inline_types
5497
+ p =
5455
5498
match p.Parser. token with
5456
5499
| (Equal | Bar ) as token -> (
5457
5500
if token = Bar then Parser. expect Equal p;
5458
5501
Parser. next p;
5459
5502
match p.Parser. token with
5460
5503
| Uident _ -> parse_type_equation_or_constr_decl p
5461
- | Lbrace -> parse_record_or_object_decl p
5504
+ | Lbrace ->
5505
+ parse_record_or_object_decl ?current_type_name_path ?inline_types p
5462
5506
| Private -> parse_private_eq_or_repr p
5463
5507
| Bar | DotDot ->
5464
5508
let priv, kind = parse_type_representation p in
@@ -5468,7 +5512,9 @@ and parse_type_equation_and_representation p =
5468
5512
match p.Parser. token with
5469
5513
| Equal ->
5470
5514
Parser. next p;
5471
- let priv, kind = parse_type_representation p in
5515
+ let priv, kind =
5516
+ parse_type_representation ?current_type_name_path ?inline_types p
5517
+ in
5472
5518
(manifest, priv, kind)
5473
5519
| _ -> (manifest, Public , Parsetree. Ptype_abstract )))
5474
5520
| _ -> (None , Public , Parsetree. Ptype_abstract )
@@ -5534,9 +5580,13 @@ and parse_type_extension ~params ~attrs ~name p =
5534
5580
let constructors = loop p [first] in
5535
5581
Ast_helper.Te. mk ~attrs ~params ~priv name constructors
5536
5582
5537
- and parse_type_definitions ~attrs ~name ~params ~start_pos p =
5583
+ and parse_type_definitions ?current_type_name_path ?inline_types ~attrs ~name
5584
+ ~params ~start_pos p =
5538
5585
let type_def =
5539
- let manifest, priv, kind = parse_type_equation_and_representation p in
5586
+ let manifest, priv, kind =
5587
+ parse_type_equation_and_representation ?current_type_name_path
5588
+ ?inline_types p
5589
+ in
5540
5590
let cstrs = parse_type_constraints p in
5541
5591
let loc = mk_loc start_pos p.prev_end_pos in
5542
5592
Ast_helper.Type. mk ~loc ~attrs ~priv ~kind ~params ~cstrs ?manifest
@@ -5585,8 +5635,24 @@ and parse_type_definition_or_extension ~attrs p =
5585
5635
(longident |> ErrorMessages. type_declaration_name_longident
5586
5636
|> Diagnostics. message)
5587
5637
in
5588
- let type_defs = parse_type_definitions ~attrs ~name ~params ~start_pos p in
5589
- TypeDef {rec_flag; types = type_defs}
5638
+ let current_type_name_path = Longident. flatten name.txt in
5639
+ let inline_types = ref [] in
5640
+ let type_defs =
5641
+ parse_type_definitions ~inline_types ~current_type_name_path ~attrs ~name
5642
+ ~params ~start_pos p
5643
+ in
5644
+ let rec_flag =
5645
+ if List. length ! inline_types > 0 then Asttypes. Recursive else rec_flag
5646
+ in
5647
+ let inline_types =
5648
+ ! inline_types
5649
+ |> List. map (fun (inline_type_name , loc , kind ) ->
5650
+ Ast_helper.Type. mk
5651
+ ~attrs: [(Location. mknoloc " inlineRecordDefinition" , PStr [] )]
5652
+ ~loc ~kind
5653
+ {name with txt = inline_type_name})
5654
+ in
5655
+ TypeDef {rec_flag; types = inline_types @ type_defs}
5590
5656
5591
5657
(* external value-name : typexp = external-declaration *)
5592
5658
and parse_external_def ~attrs ~start_pos p =
0 commit comments