Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Nested record definitions #7241

Merged
merged 18 commits into from
Mar 20, 2025
Merged
10 changes: 0 additions & 10 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -109,8 +109,6 @@ jobs:
# Verify that the compiler still builds with older OCaml versions
- os: ubuntu-24.04
ocaml_compiler: ocaml-variants.5.2.1+options,ocaml-option-static
# Reanalyze does not work on OCaml 5.3.0 anymore, therefore run it on 5.2.1
run_reanalyze: true
- os: ubuntu-24.04
ocaml_compiler: ocaml-variants.5.0.0+options,ocaml-option-static
- os: ubuntu-24.04
Expand Down Expand Up @@ -191,10 +189,6 @@ jobs:
if: steps.cache-opam-env.outputs.cache-hit != 'true'
run: opam install . --deps-only --with-test

- name: "Install reanalyze"
if: steps.cache-opam-env.outputs.cache-hit != 'true' && matrix.run_reanalyze
run: opam install reanalyze

- name: Cache OPAM environment
if: steps.cache-opam-env.outputs.cache-hit != 'true'
uses: actions/cache/save@v4
Expand Down Expand Up @@ -305,10 +299,6 @@ jobs:
if: ${{ runner.os == 'Windows' }}
run: opam exec -- make test-syntax

- name: "Syntax: Run reanalyze"
if: matrix.run_reanalyze
run: opam exec -- make reanalyze

- name: Build runtime/stdlib
run: ./scripts/buildRuntime.sh
shell: bash
Expand Down
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
- Add `inert` attribute to `JsxDOM.domProps`. https://github.com/rescript-lang/rescript/pull/7326
- Make reanalyze exception tracking work with the new stdlib. https://github.com/rescript-lang/rescript/pull/7328
- Fix Pervasive.max using boolean comparison for floats. https://github.com/rescript-lang/rescript/pull/7333
- Experimental: Support nested/inline record types - records defined inside of other records, without needing explicit separate type definitions. https://github.com/rescript-lang/rescript/pull/7241

#### :boom: Breaking Change

Expand Down
67 changes: 47 additions & 20 deletions analysis/src/Hover.ml
Original file line number Diff line number Diff line change
Expand Up @@ -101,26 +101,50 @@ let findRelevantTypesFromType ~file ~package typ =
constructors |> List.filter_map (fromConstructorPath ~env:envToSearch)

let expandTypes ~file ~package ~supportsMarkdownLinks typ =
findRelevantTypesFromType typ ~file ~package
|> List.map (fun {decl; env; loc; path} ->
let linkToTypeDefinitionStr =
if supportsMarkdownLinks then
Markdown.goToDefinitionText ~env ~pos:loc.Warnings.loc_start
else ""
in
Markdown.divider
^ (if supportsMarkdownLinks then Markdown.spacing else "")
^ Markdown.codeBlock
(decl
|> Shared.declToString ~printNameAsIs:true
(SharedTypes.pathIdentToString path))
^ linkToTypeDefinitionStr ^ "\n")
match findRelevantTypesFromType typ ~file ~package with
| {decl; path} :: _
when Res_parsetree_viewer.has_inline_record_definition_attribute
decl.type_attributes ->
(* We print inline record types just with their definition, not the constr pointing
to them, since that doesn't make sense to show the user. *)
( [
Markdown.codeBlock
(decl
|> Shared.declToString ~printNameAsIs:true
(SharedTypes.pathIdentToString path));
],
`InlineType )
| all ->
( all
|> List.map (fun {decl; env; loc; path} ->
let linkToTypeDefinitionStr =
if
supportsMarkdownLinks
&& not
(Res_parsetree_viewer
.has_inline_record_definition_attribute
decl.type_attributes)
then Markdown.goToDefinitionText ~env ~pos:loc.Warnings.loc_start
else ""
in
Markdown.divider
^ (if supportsMarkdownLinks then Markdown.spacing else "")
^ Markdown.codeBlock
(decl
|> Shared.declToString ~printNameAsIs:true
(SharedTypes.pathIdentToString path))
^ linkToTypeDefinitionStr ^ "\n"),
`Default )

(* Produces a hover with relevant types expanded in the main type being hovered. *)
let hoverWithExpandedTypes ~file ~package ~supportsMarkdownLinks typ =
let typeString = Markdown.codeBlock (typ |> Shared.typeToString) in
typeString :: expandTypes ~file ~package ~supportsMarkdownLinks typ
|> String.concat "\n"
let expandedTypes, expansionType =
expandTypes ~file ~package ~supportsMarkdownLinks typ
in
match expansionType with
| `Default -> typeString :: expandedTypes |> String.concat "\n"
| `InlineType -> expandedTypes |> String.concat "\n"

(* Leverages autocomplete functionality to produce a hover for a position. This
makes it (most often) work with unsaved content. *)
Expand Down Expand Up @@ -171,10 +195,13 @@ let newHover ~full:{file; package} ~supportsMarkdownLinks locItem =
let typeDef = Markdown.codeBlock (Shared.declToString name decl) in
match decl.type_manifest with
| None -> Some typeDef
| Some typ ->
Some
(typeDef :: expandTypes ~file ~package ~supportsMarkdownLinks typ
|> String.concat "\n"))
| Some typ -> (
let expandedTypes, expansionType =
expandTypes ~file ~package ~supportsMarkdownLinks typ
in
match expansionType with
| `Default -> Some (typeDef :: expandedTypes |> String.concat "\n")
| `InlineType -> Some (expandedTypes |> String.concat "\n")))
| LModule (Definition (stamp, _tip)) | LModule (LocalReference (stamp, _tip))
-> (
match Stamps.findModule file.stamps stamp with
Expand Down
2 changes: 2 additions & 0 deletions compiler/ml/ctype.ml
Original file line number Diff line number Diff line change
Expand Up @@ -1016,6 +1016,7 @@ let new_declaration newtype manifest =
type_attributes = [];
type_immediate = false;
type_unboxed = unboxed_false_default_false;
type_inlined_types = [];
}

let instance_constructor ?in_pattern cstr =
Expand Down Expand Up @@ -4185,6 +4186,7 @@ let nondep_type_decl env mid id is_covariant decl =
type_attributes = decl.type_attributes;
type_immediate = decl.type_immediate;
type_unboxed = decl.type_unboxed;
type_inlined_types = decl.type_inlined_types;
}
with Not_found ->
clear_hash ();
Expand Down
1 change: 1 addition & 0 deletions compiler/ml/datarepr.ml
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,7 @@ let constructor_args priv cd_args cd_res path rep =
type_attributes = [];
type_immediate = false;
type_unboxed;
type_inlined_types = [];
}
in
(existentials, [newgenconstr path type_params], Some tdecl)
Expand Down
1 change: 1 addition & 0 deletions compiler/ml/predef.ml
Original file line number Diff line number Diff line change
Expand Up @@ -203,6 +203,7 @@ let decl_abstr =
type_attributes = [];
type_immediate = false;
type_unboxed = unboxed_false_default_false;
type_inlined_types = [];
}

let decl_abstr_imm = {decl_abstr with type_immediate = true}
Expand Down
Loading