Skip to content

Commit 356320e

Browse files
committed
support leveraging type annotations when inferring
1 parent eae19ae commit 356320e

File tree

4 files changed

+83
-23
lines changed

4 files changed

+83
-23
lines changed

Diff for: analysis/src/CompletionBackEnd.ml

+60-22
Original file line numberDiff line numberDiff line change
@@ -588,6 +588,12 @@ let completionsGetTypeEnv = function
588588
| {Completion.kind = Field ({typ}, _); env} :: _ -> Some (typ, env)
589589
| _ -> None
590590

591+
type getCompletionsForContextPathMode = Regular | Pipe
592+
593+
type completionsTypeEnvTyp =
594+
| TypeExpr of Types.type_expr
595+
| ExtractedType of completionType
596+
591597
let completionsGetCompletionType ~full = function
592598
| {Completion.kind = Value typ; env} :: _
593599
| {Completion.kind = ObjLabel typ; env} :: _
@@ -602,9 +608,27 @@ let completionsGetCompletionType ~full = function
602608
| {Completion.kind = ExtractedType (typ, _); env} :: _ -> Some (typ, env)
603609
| _ -> None
604610

605-
type getCompletionsForContextPathMode = Regular | Pipe
611+
let rec completionsGetCompletionType2 ~full ~opens ~rawOpens ~allFiles ~pos
612+
~scope = function
613+
| {Completion.kind = Value typ; env} :: _
614+
| {Completion.kind = ObjLabel typ; env} :: _
615+
| {Completion.kind = Field ({typ}, _); env} :: _ ->
616+
Some (TypeExpr typ, env)
617+
| {Completion.kind = FollowContextPath ctxPath; env} :: _ ->
618+
ctxPath
619+
|> getCompletionsForContextPath ~full ~env ~exact:true ~opens ~rawOpens
620+
~allFiles ~pos ~scope
621+
|> completionsGetCompletionType2 ~full ~opens ~rawOpens ~allFiles ~pos
622+
~scope
623+
| {Completion.kind = Type typ; env} :: _ -> (
624+
match TypeUtils.extractTypeFromResolvedType typ ~env ~full with
625+
| None -> None
626+
| Some extractedType -> Some (ExtractedType extractedType, env))
627+
| {Completion.kind = ExtractedType (typ, _); env} :: _ ->
628+
Some (ExtractedType typ, env)
629+
| _ -> None
606630

607-
let rec completionsGetTypeEnv2 (completions : Completion.t list) ~full ~opens
631+
and completionsGetTypeEnv2 (completions : Completion.t list) ~full ~opens
608632
~rawOpens ~allFiles ~pos ~scope =
609633
match completions with
610634
| {Completion.kind = Value typ; env} :: _ -> Some (typ, env)
@@ -744,29 +768,43 @@ and getCompletionsForContextPath ~full ~opens ~rawOpens ~allFiles ~pos ~env
744768
|> getCompletionsForPath ~package ~opens ~allFiles ~pos ~exact
745769
~completionContext:Field ~env ~scope
746770
| CPField (cp, fieldName) -> (
747-
match
771+
let completionsForCtxPath =
748772
cp
749773
|> getCompletionsForContextPath ~full ~opens ~rawOpens ~allFiles ~pos ~env
750774
~exact:true ~scope
751-
|> completionsGetTypeEnv2 ~full ~opens ~rawOpens ~allFiles ~pos ~scope
752-
with
753-
| Some (typ, env) -> (
754-
match typ |> TypeUtils.extractRecordType ~env ~package with
755-
| Some (env, fields, typDecl) ->
756-
fields
757-
|> Utils.filterMap (fun field ->
758-
if Utils.checkName field.fname.txt ~prefix:fieldName ~exact then
759-
Some
760-
(Completion.create field.fname.txt ~env
761-
~docstring:field.docstring
762-
~kind:
763-
(Completion.Field
764-
( field,
765-
typDecl.item.decl
766-
|> Shared.declToString typDecl.name.txt )))
767-
else None)
768-
| None -> [])
769-
| None -> [])
775+
in
776+
let extracted =
777+
match
778+
completionsForCtxPath
779+
|> completionsGetCompletionType2 ~full ~opens ~rawOpens ~allFiles ~pos
780+
~scope
781+
with
782+
| Some (TypeExpr typ, env) -> (
783+
match typ |> TypeUtils.extractRecordType ~env ~package with
784+
| Some (env, fields, typDecl) ->
785+
Some
786+
( env,
787+
fields,
788+
typDecl.item.decl |> Shared.declToString typDecl.name.txt )
789+
| None -> None)
790+
| Some (ExtractedType typ, env) -> (
791+
match typ with
792+
| Trecord {fields} ->
793+
Some (env, fields, typ |> TypeUtils.extractedTypeToString)
794+
| _ -> None)
795+
| None -> None
796+
in
797+
match extracted with
798+
| None -> []
799+
| Some (env, fields, recordAsString) ->
800+
fields
801+
|> Utils.filterMap (fun field ->
802+
if Utils.checkName field.fname.txt ~prefix:fieldName ~exact then
803+
Some
804+
(Completion.create field.fname.txt ~env
805+
~docstring:field.docstring
806+
~kind:(Completion.Field (field, recordAsString)))
807+
else None))
770808
| CPObj (cp, label) -> (
771809
match
772810
cp

Diff for: analysis/src/CompletionFrontEnd.ml

+2-1
Original file line numberDiff line numberDiff line change
@@ -316,7 +316,8 @@ let completionWithParser1 ~currentFile ~debug ~offset ~path ~posCursor ~text =
316316
fields |> List.iter (fun (_, p) -> scopePattern ?contextPath p)
317317
| Ppat_array pl -> pl |> List.iter (scopePattern ?contextPath)
318318
| Ppat_or (p1, _) -> scopePattern ?contextPath p1
319-
| Ppat_constraint (p, _) -> scopePattern ?contextPath p
319+
| Ppat_constraint (p, coreType) ->
320+
scopePattern ?contextPath:(TypeUtils.contextPathFromCoreType coreType) p
320321
| Ppat_type _ -> ()
321322
| Ppat_lazy p -> scopePattern ?contextPath p
322323
| Ppat_unpack {txt; loc} ->

Diff for: analysis/tests/src/CompletionInferValues.res

+3
Original file line numberDiff line numberDiff line change
@@ -54,3 +54,6 @@ module Div = {
5454

5555
// let _ = <div onMouseEnter={event => { let btn = event->JsxEvent.Mouse.button->Belt.Int.toString->Js.String2.split("/"); btn->ma }} />
5656
// ^com
57+
58+
// let x: someRecord = {name: "Hello", age: 123}; x.
59+
// ^com

Diff for: analysis/tests/src/expected/CompletionInferValues.res.txt

+18
Original file line numberDiff line numberDiff line change
@@ -202,3 +202,21 @@ Completable: Cpath Value[btn]->ma <<jsx>>
202202
"documentation": {"kind": "markdown", "value": "\nApplies the function (the second argument) to each item in the array, returning\na new array. The result array does not have to have elements of the same type\nas the input array. See\n[`Array.map`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map)\non MDN.\n\n```res example\nJs.Array2.map([12, 4, 8], x => x * x) == [144, 16, 64]\nJs.Array2.map([\"animal\", \"vegetable\", \"mineral\"], Js.String.length) == [6, 9, 7]\n```\n"}
203203
}]
204204

205+
Complete src/CompletionInferValues.res 57:52
206+
posCursor:[57:52] posNoWhite:[57:51] Found expr:[57:50->57:52]
207+
Pexp_field [57:50->57:51] _:[60:0->57:52]
208+
Completable: Cpath Value[x].""
209+
[{
210+
"label": "name",
211+
"kind": 5,
212+
"tags": [],
213+
"detail": "name: string\n\ntype someRecord = {name: string, age: int}",
214+
"documentation": null
215+
}, {
216+
"label": "age",
217+
"kind": 5,
218+
"tags": [],
219+
"detail": "age: int\n\ntype someRecord = {name: string, age: int}",
220+
"documentation": null
221+
}]
222+

0 commit comments

Comments
 (0)