diff --git a/CHANGELOG.md b/CHANGELOG.md index 47a20f1a8..a054d487c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -23,6 +23,7 @@ - Add support for completion in typed expressions. https://github.com/rescript-lang/rescript-vscode/pull/682 - Complete for `React.element` creator functions (`React.string` etc) when in JSX context. https://github.com/rescript-lang/rescript-vscode/pull/681 - Handle optional record fields in expression/pattern completion. https://github.com/rescript-lang/rescript-vscode/pull/691 +- Expand options in completion to make working with options a bit more ergonomic. https://github.com/rescript-lang/rescript-vscode/pull/690 #### :nail_care: Polish diff --git a/analysis/src/CompletionBackEnd.ml b/analysis/src/CompletionBackEnd.ml index 1302a374f..ac8dc013b 100644 --- a/analysis/src/CompletionBackEnd.ml +++ b/analysis/src/CompletionBackEnd.ml @@ -1796,7 +1796,7 @@ let printConstructorArgs argsLen ~asSnippet = if List.length !args > 0 then "(" ^ (!args |> String.concat ", ") ^ ")" else "" -let completeTypedValue (t : Types.type_expr) ~env ~full ~prefix +let rec completeTypedValue (t : Types.type_expr) ~env ~full ~prefix ~completionContext = match t |> extractType ~env ~package:full.package with | Some (Tbool env) -> @@ -1849,6 +1849,21 @@ let completeTypedValue (t : Types.type_expr) ~env ~full ~prefix ~env ()) |> filterItems ~prefix | Some (Toption (env, t)) -> + let innerType = Utils.unwrapIfOption t in + let expandedCompletions = + innerType + |> completeTypedValue ~env ~full ~prefix ~completionContext + |> List.map (fun (c : Completion.t) -> + { + c with + name = "Some(" ^ c.name ^ ")"; + sortText = None; + insertText = + (match c.insertText with + | None -> None + | Some insertText -> Some ("Some(" ^ insertText ^ ")")); + }) + in [ Completion.create ~name:"None" ~kind:(Label (t |> Shared.typeToString)) @@ -1857,6 +1872,7 @@ let completeTypedValue (t : Types.type_expr) ~env ~full ~prefix ~kind:(Label (t |> Shared.typeToString)) ~env ~insertText:"Some(${1:_})" (); ] + @ expandedCompletions |> filterItems ~prefix | Some (Tuple (env, exprs, typ)) -> let numExprs = List.length exprs in diff --git a/analysis/tests/src/CompletionExpressions.res b/analysis/tests/src/CompletionExpressions.res index 408467075..4e806fbe7 100644 --- a/analysis/tests/src/CompletionExpressions.res +++ b/analysis/tests/src/CompletionExpressions.res @@ -108,3 +108,11 @@ let fnTakingRecordWithOptionalField = (r: recordWithOptionalField) => { // let _ = fnTakingRecordWithOptionalField({someOptField: }) // ^com +type recordWithOptVariant = {someVariant: option} + +let fnTakingRecordWithOptVariant = (r: recordWithOptVariant) => { + ignore(r) +} + +// let _ = fnTakingRecordWithOptVariant({someVariant: }) +// ^com diff --git a/analysis/tests/src/expected/CompletionExpressions.res.txt b/analysis/tests/src/expected/CompletionExpressions.res.txt index 0d014613d..6531231ae 100644 --- a/analysis/tests/src/expected/CompletionExpressions.res.txt +++ b/analysis/tests/src/expected/CompletionExpressions.res.txt @@ -167,6 +167,14 @@ Completable: Cexpression CArgument Value[fnTakingRecord]($0)->recordField(nested "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some({})", + "kind": 12, + "tags": [], + "detail": "otherRecord", + "documentation": null, + "insertText": "Some({$0})", + "insertTextFormat": 2 }] Complete src/CompletionExpressions.res 44:46 @@ -328,6 +336,18 @@ Completable: Cexpression CArgument Value[fnTakingArray]($0)->array "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionExpressions.res 75:26 @@ -378,6 +398,18 @@ Completable: Cexpression CArgument Value[fnTakingArray]($0)->array "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionExpressions.res 84:31 @@ -398,6 +430,18 @@ Completable: Cexpression CArgument Value[fnTakingArray]($0)->array "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionExpressions.res 89:38 @@ -445,3 +489,47 @@ Completable: Cexpression CArgument Value[fnTakingRecordWithOptionalField]($0)->r "documentation": null }] +Complete src/CompletionExpressions.res 116:53 +posCursor:[116:53] posNoWhite:[116:52] Found expr:[116:11->116:56] +Pexp_apply ...[116:11->116:39] (...[116:40->116:56]) +Completable: Cexpression CArgument Value[fnTakingRecordWithOptVariant]($0)->recordField(someVariant) +[{ + "label": "None", + "kind": 4, + "tags": [], + "detail": "someVariant", + "documentation": null + }, { + "label": "Some(_)", + "kind": 4, + "tags": [], + "detail": "someVariant", + "documentation": null, + "insertText": "Some(${1:_})", + "insertTextFormat": 2 + }, { + "label": "Some(One)", + "kind": 4, + "tags": [], + "detail": "One\n\ntype someVariant = One | Two | Three(int, string)", + "documentation": null, + "insertText": "Some(One)", + "insertTextFormat": 2 + }, { + "label": "Some(Two)", + "kind": 4, + "tags": [], + "detail": "Two\n\ntype someVariant = One | Two | Three(int, string)", + "documentation": null, + "insertText": "Some(Two)", + "insertTextFormat": 2 + }, { + "label": "Some(Three(_, _))", + "kind": 4, + "tags": [], + "detail": "Three(int, string)\n\ntype someVariant = One | Two | Three(int, string)", + "documentation": null, + "insertText": "Some(Three(${1:_}, ${2:_}))", + "insertTextFormat": 2 + }] + diff --git a/analysis/tests/src/expected/CompletionPattern.res.txt b/analysis/tests/src/expected/CompletionPattern.res.txt index 88936aa77..a1e346ef3 100644 --- a/analysis/tests/src/expected/CompletionPattern.res.txt +++ b/analysis/tests/src/expected/CompletionPattern.res.txt @@ -497,6 +497,18 @@ Completable: Cpattern Value[p]->variantPayload::Test($2) "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionPattern.res 140:23 @@ -573,6 +585,18 @@ Completable: Cpattern Value[v]->polyvariantPayload::test($2) "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionPattern.res 156:24 @@ -647,6 +671,18 @@ Completable: Cpattern Value[s]->tuple($1) "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionPattern.res 170:22 @@ -667,6 +703,18 @@ Completable: Cpattern Value[s]->tuple($1) "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionPattern.res 173:35 @@ -700,6 +748,18 @@ Completable: Cpattern Value[s]->tuple($1) "documentation": null, "insertText": "Some(${1:_})", "insertTextFormat": 2 + }, { + "label": "Some(true)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null + }, { + "label": "Some(false)", + "kind": 4, + "tags": [], + "detail": "bool", + "documentation": null }] Complete src/CompletionPattern.res 179:21