Skip to content

Commit c3d0583

Browse files
committed
WIP, find cursor in broken case
1 parent e53ab8a commit c3d0583

9 files changed

+93
-67
lines changed

analysis/src/CompletionBackEndRevamped.ml

+1
Original file line numberDiff line numberDiff line change
@@ -121,3 +121,4 @@ let processCompletable ~debug ~full ~scope ~env ~pos
121121
(dec2, doc, maybeInsertText))
122122
|> List.map mkDecorator
123123
| CdecoratorPayload _ -> []
124+
| Ccase _ -> []

analysis/src/CompletionFrontEndRevamped.ml

+10-6
Original file line numberDiff line numberDiff line change
@@ -420,16 +420,14 @@ let completionWithParser ~currentFile ~debug ~offset ~path ~posCursor text =
420420
if expr.pexp_loc |> Loc.hasPos ~pos:posNoWhite && !result = None then (
421421
setFound ();
422422
match expr.pexp_desc with
423-
| Pexp_match (switchExpr, [{pc_lhs = lhsPat}])
423+
(* | Pexp_match (switchExpr, [{pc_lhs = lhsPat}])
424424
when CompletionPatterns.isPatternHole lhsPat
425425
&& locHasCursor switchExpr.pexp_loc = false ->
426-
setResult (Cpattern {kind = Empty; typeLoc = switchExpr.pexp_loc})
426+
setResult (Cpattern {kind = Empty; typeLoc = switchExpr.pexp_loc}) *)
427427
| Pexp_match (switchExpr, cases) ->
428428
let oldTypeLoc = !currentTypeLoc in
429429
currentTypeLoc := Some switchExpr.pexp_loc;
430-
cases
431-
|> List.iter (fun case ->
432-
Ast_iterator.default_iterator.case iterator case);
430+
cases |> List.iter (fun case -> iterator.case iterator case);
433431
currentTypeLoc := oldTypeLoc;
434432
processed := true
435433
| Pexp_extension ({txt = "obj"}, PStr [str_item]) ->
@@ -615,6 +613,10 @@ let completionWithParser ~currentFile ~debug ~offset ~path ~posCursor text =
615613
| _ -> ());
616614
if not !processed then Ast_iterator.default_iterator.expr iterator expr
617615
in
616+
let case (_iterator : Ast_iterator.iterator) (case : Parsetree.case) =
617+
if case.pc_loc |> Loc.hasPos ~pos:posCursor then
618+
setResult (Ccase case.pc_loc)
619+
in
618620
let typ (iterator : Ast_iterator.iterator) (core_type : Parsetree.core_type) =
619621
if core_type.ptyp_loc |> Loc.hasPos ~pos:posNoWhite then (
620622
found := true;
@@ -781,6 +783,7 @@ let completionWithParser ~currentFile ~debug ~offset ~path ~posCursor text =
781783
Ast_iterator.default_iterator with
782784
attribute;
783785
expr;
786+
case;
784787
location;
785788
module_expr;
786789
module_type;
@@ -800,7 +803,8 @@ let completionWithParser ~currentFile ~debug ~offset ~path ~posCursor text =
800803
Res_driver.parsing_engine.parse_implementation ~for_printer:false
801804
in
802805
let {Res_driver.parsetree = str} = parser ~filename:currentFile in
803-
iterator.structure iterator str |> ignore;
806+
let tree = Res_recovery.map str in
807+
iterator.structure iterator tree |> ignore;
804808
if blankAfterCursor = Some ' ' || blankAfterCursor = Some '\n' then
805809
scope := !lastScopeBeforeCursor
806810
(* TODO(revamp) Complete any value *)

analysis/src/SharedTypes.ml

+3
Original file line numberDiff line numberDiff line change
@@ -820,6 +820,7 @@ module CompletableRevamped = struct
820820
| CextensionNode of string
821821
| Cdecorator of string
822822
| CdecoratorPayload of decoratorPayload
823+
| Ccase of Location.t
823824

824825
let toString (t : t) =
825826
match t with
@@ -829,11 +830,13 @@ module CompletableRevamped = struct
829830
| CextensionNode _ -> "CextensionNode"
830831
| Cdecorator _ -> "Cdecorator"
831832
| CdecoratorPayload _ -> "CdecoratorPayload"
833+
| Ccase _ -> "Ccase"
832834

833835
let try_loc (t : t) =
834836
match t with
835837
| Cexpression {typeLoc; _} -> Some typeLoc
836838
| Cpattern {typeLoc; _} -> Some typeLoc
839+
| Ccase loc -> Some loc
837840
| _ -> None
838841
end
839842

compiler/syntax/src/res_driver.ml

+3-2
Original file line numberDiff line numberDiff line change
@@ -139,8 +139,9 @@ let parse_implementation ?(ignore_parse_errors = false) sourcefile =
139139
in
140140
if parse_result.invalid then (
141141
Res_diagnostics.print_report parse_result.diagnostics parse_result.source;
142-
if not ignore_parse_errors then exit 1);
143-
parse_result.parsetree
142+
if not ignore_parse_errors then exit 1;
143+
Res_recovery.map parse_result.parsetree)
144+
else parse_result.parsetree
144145
[@@raises exit]
145146

146147
let parse_interface ?(ignore_parse_errors = false) sourcefile =

compiler/syntax/src/res_recovery.ml

+44
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
let map_expr (mapper : Ast_mapper.mapper) (expr : Parsetree.expression) =
2+
match expr.pexp_desc with
3+
| Pexp_match (e, cases) ->
4+
let mapped_e = mapper.expr mapper e in
5+
let match_end_loc = expr.pexp_loc.loc_end in
6+
7+
let is_ghost_case case =
8+
let open Parsetree in
9+
case.pc_lhs.ppat_loc.loc_ghost && case.pc_rhs.pexp_loc.loc_ghost
10+
in
11+
12+
let rec process_cases mapped_cases cases =
13+
match cases with
14+
| [] -> mapped_cases
15+
| [last_case] when is_ghost_case last_case ->
16+
prerr_endline "last case";
17+
let mapped =
18+
mapper.case mapper
19+
{
20+
last_case with
21+
pc_loc = {last_case.pc_loc with loc_end = match_end_loc};
22+
}
23+
in
24+
process_cases (mapped :: mapped_cases) []
25+
| current :: (next :: _ as rest) when is_ghost_case current ->
26+
let mapped =
27+
mapper.case mapper
28+
{
29+
current with
30+
pc_loc =
31+
{current.pc_loc with loc_end = next.pc_lhs.ppat_loc.loc_start};
32+
}
33+
in
34+
process_cases (mapped :: mapped_cases) rest
35+
| c :: rest -> process_cases (mapper.case mapper c :: mapped_cases) rest
36+
in
37+
38+
let adjusted_cases = process_cases [] cases in
39+
{expr with pexp_desc = Pexp_match (mapped_e, adjusted_cases)}
40+
| _ -> Ast_mapper.default_mapper.expr mapper expr
41+
42+
let map (tree : Parsetree.structure) =
43+
let mapper = {Ast_mapper.default_mapper with expr = map_expr} in
44+
mapper.structure mapper tree
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,15 @@
1-
Found Completable: Cpattern at type loc: [3:15->3:28]
1+
case _ vamp [4:2->6:1], has cursor true
2+
Found Completable: Ccase
23

3-
2let someStringArr = ["hello"]
44
3
55
4let x = switch someStringArr {
6-
│ ‾‾‾‾‾‾‾‾‾‾‾‾‾
76
5 │ |
7+
│ ‾‾
88
6 │ // ^com
9+
│ ‾‾‾‾‾‾‾‾
10+
7 │ }
11+
│ ‾
12+
8
913

10-
[{
11-
"label": "[]",
12-
"kind": 12,
13-
"tags": [],
14-
"detail": "array<string>",
15-
"documentation": null,
16-
"sortText": "A",
17-
"insertText": "[$0]",
18-
"insertTextFormat": 2
19-
}]
14+
[]
2015

Original file line numberDiff line numberDiff line change
@@ -1,28 +1,15 @@
1-
Found Completable: Cpattern at type loc: [1:15->1:19]
1+
case _ vamp [2:2->4:1], has cursor true
2+
Found Completable: Ccase
23

34
1// Empty case, bool
45
2let x = switch true {
5-
│ ‾‾‾‾
66
3 │ |
7+
│ ‾‾
78
4 │ // ^com
9+
│ ‾‾‾‾‾‾‾‾
10+
5 │ }
11+
│ ‾
12+
6
813

9-
[{
10-
"label": "true",
11-
"kind": 12,
12-
"tags": [],
13-
"detail": "bool",
14-
"documentation": null,
15-
"sortText": "A",
16-
"insertText": "true",
17-
"insertTextFormat": 2
18-
}, {
19-
"label": "false",
20-
"kind": 12,
21-
"tags": [],
22-
"detail": "bool",
23-
"documentation": null,
24-
"sortText": "A",
25-
"insertText": "false",
26-
"insertTextFormat": 2
27-
}]
14+
[]
2815

Original file line numberDiff line numberDiff line change
@@ -1,19 +1,15 @@
1-
Found Completable: Cpattern at type loc: [1:15->1:44]
1+
case _ vamp [2:2->4:1], has cursor true
2+
Found Completable: Ccase
23

34
1// Empty case, record
45
2let x = switch TestTypeDefs.nestedTestRecord {
5-
│ ‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾‾
66
3 │ |
7+
│ ‾‾
78
4 │ // ^com
9+
│ ‾‾‾‾‾‾‾‾
10+
5 │ }
11+
│ ‾
12+
6
813

9-
[{
10-
"label": "{}",
11-
"kind": 12,
12-
"tags": [],
13-
"detail": "TestTypeDefs.nestedTestRecord",
14-
"documentation": {"kind": "markdown", "value": "```rescript\ntype nestedTestRecord = {\n test: bool,\n nested: {name: string, oneMoreLevel: {here: bool}},\n}\n```"},
15-
"sortText": "A",
16-
"insertText": "{$0}",
17-
"insertTextFormat": 2
18-
}]
14+
[]
1915

Original file line numberDiff line numberDiff line change
@@ -1,20 +1,15 @@
1-
Found Completable: Cpattern at type loc: [2:15->2:18]
1+
case _ vamp [3:2->5:1], has cursor true
2+
Found Completable: Ccase
23

3-
1// Empty case, string
44
2let str = "hello"
55
3let x = switch str {
6-
│ ‾‾‾
76
4 │ |
7+
│ ‾‾
88
5 │ // ^com
9+
│ ‾‾‾‾‾‾‾‾
10+
6 │ }
11+
│ ‾
12+
7
913

10-
[{
11-
"label": "\"\"",
12-
"kind": 12,
13-
"tags": [],
14-
"detail": "string",
15-
"documentation": null,
16-
"sortText": "A",
17-
"insertText": "\"$0\"",
18-
"insertTextFormat": 2
19-
}]
14+
[]
2015

0 commit comments

Comments
 (0)