Skip to content

Commit 03bda7d

Browse files
committed
refactor and unify how pat tuple items are traversed
1 parent 93ec653 commit 03bda7d

File tree

1 file changed

+60
-100
lines changed

1 file changed

+60
-100
lines changed

analysis/src/CompletionFrontEnd.ml

Lines changed: 60 additions & 100 deletions
Original file line numberDiff line numberDiff line change
@@ -238,12 +238,6 @@ let findArgCompletables ~(args : arg list) ~endPos ~posBeforeCursor
238238
})
239239
| _ -> loop args
240240

241-
let lastLocIndexBeforePos locs ~pos =
242-
let posNum = ref (-1) in
243-
locs
244-
|> List.iteri (fun index loc -> if pos >= Loc.start loc then posNum := index);
245-
if !posNum > -1 then Some !posNum else None
246-
247241
let rec exprToContextPath (e : Parsetree.expression) =
248242
match e.pexp_desc with
249243
| Pexp_constant (Pconst_string _) -> Some Completable.CPString
@@ -403,7 +397,27 @@ let completionWithParser1 ~currentFile ~debug ~offset ~path ~posCursor ~text =
403397

404398
let lookingForPat = ref None in
405399

406-
let rec traversePattern (pat : Parsetree.pattern) ~patternPath =
400+
let rec traverseTupleItems tupleItems ~nextPatternPath ~resultFromFoundItemNum
401+
=
402+
let itemNum = ref (-1) in
403+
let itemWithCursor =
404+
tupleItems
405+
|> List.find_map (fun pat ->
406+
itemNum := !itemNum + 1;
407+
pat |> traversePattern ~patternPath:(nextPatternPath !itemNum))
408+
in
409+
match (itemWithCursor, firstCharBeforeCursorNoWhite) with
410+
| None, Some ',' ->
411+
(* No tuple item has the cursor, but there's a comma before the cursor.
412+
Figure out what arg we're trying to complete. Example: (true, <com>, None) *)
413+
let posNum = ref (-1) in
414+
tupleItems
415+
|> List.iteri (fun index pat ->
416+
if posBeforeCursor >= Loc.start pat.Parsetree.ppat_loc then
417+
posNum := index);
418+
if !posNum > -1 then Some ("", resultFromFoundItemNum !posNum) else None
419+
| v, _ -> v
420+
and traversePattern (pat : Parsetree.pattern) ~patternPath =
407421
if
408422
pat.ppat_loc
409423
|> CursorPosition.classifyLoc ~pos:posBeforeCursor
@@ -433,31 +447,13 @@ let completionWithParser1 ~currentFile ~debug ~offset ~path ~posCursor ~text =
433447
arrayPatterns
434448
|> List.find_map (fun pat ->
435449
pat |> traversePattern ~patternPath:nextPatternPath)
436-
| Ppat_tuple tupleItems -> (
437-
let itemNum = ref (-1) in
438-
let itemWithCursor =
439-
tupleItems
440-
|> List.find_map (fun pat ->
441-
itemNum := !itemNum + 1;
442-
pat
443-
|> traversePattern
444-
~patternPath:
445-
([Completable.PTupleItem {itemNum = !itemNum}]
446-
@ patternPath))
447-
in
448-
match (itemWithCursor, firstCharBeforeCursorNoWhite) with
449-
| None, Some ',' -> (
450-
(* No tuple item has the cursor, but there's a comma before the cursor.
451-
Figure out what arg we're trying to complete. Example: #test(true, <com>, None) *)
452-
let locs = tupleItems |> List.map (fun p -> p.Parsetree.ppat_loc) in
453-
match locs |> lastLocIndexBeforePos ~pos:posBeforeCursor with
454-
| None -> None
455-
| Some itemNum ->
456-
Some
457-
( "",
458-
[Completable.PTupleItem {itemNum = itemNum + 1}] @ patternPath
459-
))
460-
| v, _ -> v)
450+
| Ppat_tuple tupleItems ->
451+
tupleItems
452+
|> traverseTupleItems
453+
~nextPatternPath:(fun itemNum ->
454+
[Completable.PTupleItem {itemNum}] @ patternPath)
455+
~resultFromFoundItemNum:(fun itemNum ->
456+
[Completable.PTupleItem {itemNum = itemNum + 1}] @ patternPath)
461457
| Ppat_record ([], _) ->
462458
(* Empty fields means we're in a record body `{}`. Complete for the fields. *)
463459
Some ("", [Completable.PRecordBody {seenFields = []}] @ patternPath)
@@ -557,43 +553,24 @@ let completionWithParser1 ~currentFile ~debug ~offset ~path ~posCursor ~text =
557553
({txt}, Some {ppat_loc; ppat_desc = Ppat_tuple tupleItems})
558554
when ppat_loc
559555
|> CursorPosition.classifyLoc ~pos:posBeforeCursor
560-
= HasCursor -> (
561-
let itemNum = ref (-1) in
562-
let itemWithCursor =
563-
tupleItems
564-
|> List.find_map (fun pat ->
565-
itemNum := !itemNum + 1;
566-
pat
567-
|> traversePattern
568-
~patternPath:
569-
([
570-
Completable.PVariantPayload
571-
{
572-
constructorName = getUnqualifiedName txt;
573-
itemNum = !itemNum;
574-
};
575-
]
576-
@ patternPath))
577-
in
578-
match (itemWithCursor, firstCharBeforeCursorNoWhite) with
579-
| None, Some ',' -> (
580-
(* No tuple item has the cursor, but there's a comma before the cursor.
581-
Figure out what arg we're trying to complete. Example: Test(true, <com>, None) *)
582-
let locs = tupleItems |> List.map (fun p -> p.Parsetree.ppat_loc) in
583-
match locs |> lastLocIndexBeforePos ~pos:posBeforeCursor with
584-
| None -> None
585-
| Some itemNum ->
586-
Some
587-
( "",
588-
[
589-
Completable.PVariantPayload
590-
{
591-
constructorName = getUnqualifiedName txt;
592-
itemNum = itemNum + 1;
593-
};
594-
]
595-
@ patternPath ))
596-
| v, _ -> v)
556+
= HasCursor ->
557+
tupleItems
558+
|> traverseTupleItems
559+
~nextPatternPath:(fun itemNum ->
560+
[
561+
Completable.PVariantPayload
562+
{constructorName = getUnqualifiedName txt; itemNum};
563+
]
564+
@ patternPath)
565+
~resultFromFoundItemNum:(fun itemNum ->
566+
[
567+
Completable.PVariantPayload
568+
{
569+
constructorName = getUnqualifiedName txt;
570+
itemNum = itemNum + 1;
571+
};
572+
]
573+
@ patternPath)
597574
| Ppat_variant
598575
( txt,
599576
Some {ppat_loc; ppat_desc = Ppat_construct ({txt = Lident "()"}, _)}
@@ -638,37 +615,20 @@ let completionWithParser1 ~currentFile ~debug ~offset ~path ~posCursor ~text =
638615
| Ppat_variant (txt, Some {ppat_loc; ppat_desc = Ppat_tuple tupleItems})
639616
when ppat_loc
640617
|> CursorPosition.classifyLoc ~pos:posBeforeCursor
641-
= HasCursor -> (
642-
let itemNum = ref (-1) in
643-
let itemWithCursor =
644-
tupleItems
645-
|> List.find_map (fun pat ->
646-
itemNum := !itemNum + 1;
647-
pat
648-
|> traversePattern
649-
~patternPath:
650-
([
651-
Completable.PPolyvariantPayload
652-
{constructorName = txt; itemNum = !itemNum};
653-
]
654-
@ patternPath))
655-
in
656-
match (itemWithCursor, firstCharBeforeCursorNoWhite) with
657-
| None, Some ',' -> (
658-
(* No tuple item has the cursor, but there's a comma before the cursor.
659-
Figure out what arg we're trying to complete. Example: #test(true, <com>, None) *)
660-
let locs = tupleItems |> List.map (fun p -> p.Parsetree.ppat_loc) in
661-
match locs |> lastLocIndexBeforePos ~pos:posBeforeCursor with
662-
| None -> None
663-
| Some itemNum ->
664-
Some
665-
( "",
666-
[
667-
Completable.PPolyvariantPayload
668-
{constructorName = txt; itemNum = itemNum + 1};
669-
]
670-
@ patternPath ))
671-
| v, _ -> v)
618+
= HasCursor ->
619+
tupleItems
620+
|> traverseTupleItems
621+
~nextPatternPath:(fun itemNum ->
622+
[
623+
Completable.PPolyvariantPayload {constructorName = txt; itemNum};
624+
]
625+
@ patternPath)
626+
~resultFromFoundItemNum:(fun itemNum ->
627+
[
628+
Completable.PPolyvariantPayload
629+
{constructorName = txt; itemNum = itemNum + 1};
630+
]
631+
@ patternPath)
672632
| _ -> None
673633
else None
674634
in

0 commit comments

Comments
 (0)