Skip to content

Commit

Permalink
gopls/internal/analysis/undeclared: merge into CodeAction
Browse files Browse the repository at this point in the history
  • Loading branch information
xzbdmw committed Nov 18, 2024
1 parent 6fe4f96 commit 33b78d7
Show file tree
Hide file tree
Showing 27 changed files with 618 additions and 414 deletions.
20 changes: 0 additions & 20 deletions gopls/doc/analyzers.md
Original file line number Diff line number Diff line change
Expand Up @@ -842,26 +842,6 @@ Default: on.

Package documentation: [timeformat](https://pkg.go.dev/golang.org/x/tools/go/analysis/passes/timeformat)

<a id='undeclaredname'></a>
## `undeclaredname`: suggested fixes for "undeclared name: <>"


This checker provides suggested fixes for type errors of the
type "undeclared name: <>". It will either insert a new statement,
such as:

<> :=

or a new function declaration, such as:

func <>(inferred parameters) {
panic("implement me!")
}

Default: on.

Package documentation: [undeclaredname](https://pkg.go.dev/golang.org/x/tools/gopls/internal/analysis/undeclaredname)

<a id='unmarshal'></a>
## `unmarshal`: report passing non-pointer or non-interface values to unmarshal

Expand Down
50 changes: 50 additions & 0 deletions gopls/doc/features/diagnostics.md
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,56 @@ func (f Foo) bar(s string, i int) string {
}
```

### `CreateUndeclared`: Create missing declaration for "undeclared name: X"

A Go compiler error "undeclared name: X" indicates that a variable or function is being used before
it has been declared in the current scope. In this scenario, gopls offers a quick fix to create the declaration.

#### Declare a new variable

When you reference a variable that hasn't been declared:

```go
func main() {
x := 42
min(x, y) // error: undefined: y
}
```

The quick fix would be:

```go
func main() {
x := 42
y :=
min(x, y)
}
```

#### Declare a new function

Similarly, if you call a function that hasn't been declared:

```go
func main() {
var s string
s = doSomething(42) // error: undefined: doSomething
}
```

Gopls will insert a new function declaration below,
inferring its type from the call:

```go
func main() {
var s string
s = doSomething(42)
}

func doSomething(i int) string {
panic("unimplemented")
}
```
<!--
dorky details and deletia:
Expand Down
23 changes: 0 additions & 23 deletions gopls/internal/analysis/undeclaredname/doc.go

This file was deleted.

28 changes: 0 additions & 28 deletions gopls/internal/analysis/undeclaredname/testdata/src/a/a.go

This file was deleted.

13 changes: 0 additions & 13 deletions gopls/internal/analysis/undeclaredname/testdata/src/a/channels.go

This file was deleted.

This file was deleted.

This file was deleted.

11 changes: 0 additions & 11 deletions gopls/internal/analysis/undeclaredname/testdata/src/a/literals.go

This file was deleted.

11 changes: 0 additions & 11 deletions gopls/internal/analysis/undeclaredname/testdata/src/a/operation.go

This file was deleted.

10 changes: 0 additions & 10 deletions gopls/internal/analysis/undeclaredname/testdata/src/a/selector.go

This file was deleted.

This file was deleted.

13 changes: 0 additions & 13 deletions gopls/internal/analysis/undeclaredname/testdata/src/a/tuple.go

This file was deleted.

This file was deleted.

17 changes: 0 additions & 17 deletions gopls/internal/analysis/undeclaredname/undeclared_test.go

This file was deleted.

11 changes: 0 additions & 11 deletions gopls/internal/doc/api.json
Original file line number Diff line number Diff line change
Expand Up @@ -569,11 +569,6 @@
"Doc": "check for calls of (time.Time).Format or time.Parse with 2006-02-01\n\nThe timeformat checker looks for time formats with the 2006-02-01 (yyyy-dd-mm)\nformat. Internationally, \"yyyy-dd-mm\" does not occur in common calendar date\nstandards, and so it is more likely that 2006-01-02 (yyyy-mm-dd) was intended.",
"Default": "true"
},
{
"Name": "\"undeclaredname\"",
"Doc": "suggested fixes for \"undeclared name: \u003c\u003e\"\n\nThis checker provides suggested fixes for type errors of the\ntype \"undeclared name: \u003c\u003e\". It will either insert a new statement,\nsuch as:\n\n\t\u003c\u003e :=\n\nor a new function declaration, such as:\n\n\tfunc \u003c\u003e(inferred parameters) {\n\t\tpanic(\"implement me!\")\n\t}",
"Default": "true"
},
{
"Name": "\"unmarshal\"",
"Doc": "report passing non-pointer or non-interface values to unmarshal\n\nThe unmarshal analysis reports calls to functions such as json.Unmarshal\nin which the argument type is not a pointer or an interface.",
Expand Down Expand Up @@ -1255,12 +1250,6 @@
"URL": "https://pkg.go.dev/golang.org/x/tools/go/analysis/passes/timeformat",
"Default": true
},
{
"Name": "undeclaredname",
"Doc": "suggested fixes for \"undeclared name: \u003c\u003e\"\n\nThis checker provides suggested fixes for type errors of the\ntype \"undeclared name: \u003c\u003e\". It will either insert a new statement,\nsuch as:\n\n\t\u003c\u003e :=\n\nor a new function declaration, such as:\n\n\tfunc \u003c\u003e(inferred parameters) {\n\t\tpanic(\"implement me!\")\n\t}",
"URL": "https://pkg.go.dev/golang.org/x/tools/gopls/internal/analysis/undeclaredname",
"Default": true
},
{
"Name": "unmarshal",
"Doc": "report passing non-pointer or non-interface values to unmarshal\n\nThe unmarshal analysis reports calls to functions such as json.Unmarshal\nin which the argument type is not a pointer or an interface.",
Expand Down
13 changes: 12 additions & 1 deletion gopls/internal/golang/codeaction.go
Original file line number Diff line number Diff line change
Expand Up @@ -302,7 +302,7 @@ func quickFix(ctx context.Context, req *codeActionsRequest) error {
continue
}

msg := typeError.Error()
msg := typeError.Msg
switch {
// "Missing method" error? (stubmethods)
// Offer a "Declare missing methods of INTERFACE" code action.
Expand All @@ -329,6 +329,17 @@ func quickFix(ctx context.Context, req *codeActionsRequest) error {
msg := fmt.Sprintf("Declare missing method %s.%s", si.Receiver.Obj().Name(), si.MethodName)
req.addApplyFixAction(msg, fixMissingCalledFunction, req.loc)
}

// "undeclared name: x" or "undefined: x" compiler error.
// Offer a "Create variable/function x" code action.
// See [fixUndeclared] for command implementation.
case strings.HasPrefix(msg, "undeclared name: "),
strings.HasPrefix(msg, "undefined: "):
path, _ := astutil.PathEnclosingInterval(req.pgf.File, start, end)
title := undeclaredFixTitle(path, msg)
if title != "" {
req.addApplyFixAction(title, fixCreateUndeclared, req.loc)
}
}
}

Expand Down
4 changes: 2 additions & 2 deletions gopls/internal/golang/fix.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ import (
"golang.org/x/tools/go/analysis"
"golang.org/x/tools/gopls/internal/analysis/embeddirective"
"golang.org/x/tools/gopls/internal/analysis/fillstruct"
"golang.org/x/tools/gopls/internal/analysis/undeclaredname"
"golang.org/x/tools/gopls/internal/analysis/unusedparams"
"golang.org/x/tools/gopls/internal/cache"
"golang.org/x/tools/gopls/internal/cache/parsego"
Expand Down Expand Up @@ -65,6 +64,7 @@ const (
fixInvertIfCondition = "invert_if_condition"
fixSplitLines = "split_lines"
fixJoinLines = "join_lines"
fixCreateUndeclared = "create_undeclared"
fixMissingInterfaceMethods = "stub_missing_interface_method"
fixMissingCalledFunction = "stub_missing_called_function"
)
Expand Down Expand Up @@ -99,7 +99,6 @@ func ApplyFix(ctx context.Context, fix string, snapshot *cache.Snapshot, fh file
// These match the Diagnostic.Category.
embeddirective.FixCategory: addEmbedImport,
fillstruct.FixCategory: singleFile(fillstruct.SuggestedFix),
undeclaredname.FixCategory: singleFile(undeclaredname.SuggestedFix),

// Ad-hoc fixers: these are used when the command is
// constructed directly by logic in server/code_action.
Expand All @@ -110,6 +109,7 @@ func ApplyFix(ctx context.Context, fix string, snapshot *cache.Snapshot, fh file
fixInvertIfCondition: singleFile(invertIfCondition),
fixSplitLines: singleFile(splitLines),
fixJoinLines: singleFile(joinLines),
fixCreateUndeclared: singleFile(CreateUndeclared),
fixMissingInterfaceMethods: stubMissingInterfaceMethodsFixer,
fixMissingCalledFunction: stubMissingCalledFunctionFixer,
}
Expand Down
Loading

0 comments on commit 33b78d7

Please sign in to comment.