// Copyright 2021 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

//go:generate go run -tags=generate generate.go

// Package command defines the interface provided by gopls for the
// workspace/executeCommand LSP request.
//
// This interface is fully specified by the Interface type, provided it
// conforms to the restrictions outlined in its doc string.
//
// Bindings for server-side command dispatch and client-side serialization are
// also provided by this package, via code generation.
package command

import (
	"context"
	"encoding/json"
	"fmt"

	"golang.org/x/tools/gopls/internal/protocol"
	"golang.org/x/tools/gopls/internal/vulncheck"
)

// Interface defines the interface gopls exposes for the
// workspace/executeCommand request.
//
// This interface is used to generate logic for marshaling,
// unmarshaling, and dispatch, so it has some additional restrictions:
//
//  1. All method arguments must be JSON serializable.
//
//  2. Methods must return either error or (T, error), where T is a
//     JSON serializable type.
//
//  3. The first line of the doc string is special.
//     Everything after the colon is considered the command 'Title'.
//     For example:
//
//     Command: Capitalized verb phrase with no period
//
//     Longer description here...
type Interface interface {
	// ApplyFix: Apply a fix
	//
	// Applies a fix to a region of source code.
	ApplyFix(context.Context, ApplyFixArgs) (*protocol.WorkspaceEdit, error)

	// RunTests: Run tests
	//
	// Runs `go test` for a specific set of test or benchmark functions.
	//
	// This command is asynchronous; clients must wait for the 'end' progress notification.
	RunTests(context.Context, RunTestsArgs) error

	// Generate: Run go generate
	//
	// Runs `go generate` for a given directory.
	Generate(context.Context, GenerateArgs) error

	// Doc: Browse package documentation.
	//
	// Opens the Go package documentation page for the current
	// package in a browser.
	Doc(context.Context, DocArgs) (protocol.URI, error)

	// SplitPackage: organize a package into two or more components
	//
	// Opens the "split package" tool in a web browser.
	SplitPackage(ctx context.Context, viewID, packageID string) error

	// RegenerateCgo: Regenerate cgo
	//
	// Regenerates cgo definitions.
	RegenerateCgo(context.Context, URIArg) error

	// Tidy: Run go mod tidy
	//
	// Runs `go mod tidy` for a module.
	Tidy(context.Context, URIArgs) error

	// Vendor: Run go mod vendor
	//
	// Runs `go mod vendor` for a module.
	Vendor(context.Context, URIArg) error

	// EditGoDirective: Run go mod edit -go=version
	//
	// Runs `go mod edit -go=version` for a module.
	EditGoDirective(context.Context, EditGoDirectiveArgs) error

	// UpdateGoSum: Update go.sum
	//
	// Updates the go.sum file for a module.
	UpdateGoSum(context.Context, URIArgs) error

	// CheckUpgrades: Check for upgrades
	//
	// Checks for module upgrades.
	CheckUpgrades(context.Context, CheckUpgradesArgs) error

	// AddDependency: Add a dependency
	//
	// Adds a dependency to the go.mod file for a module.
	AddDependency(context.Context, DependencyArgs) error

	// UpgradeDependency: Upgrade a dependency
	//
	// Upgrades a dependency in the go.mod file for a module.
	UpgradeDependency(context.Context, DependencyArgs) error

	// RemoveDependency: Remove a dependency
	//
	// Removes a dependency from the go.mod file of a module.
	RemoveDependency(context.Context, RemoveDependencyArgs) error

	// ResetGoModDiagnostics: Reset go.mod diagnostics
	//
	// Reset diagnostics in the go.mod file of a module.
	ResetGoModDiagnostics(context.Context, ResetGoModDiagnosticsArgs) error

	// GoGetPackage: 'go get' a package
	//
	// Runs `go get` to fetch a package.
	GoGetPackage(context.Context, GoGetPackageArgs) error

	// GCDetails: Toggle display of compiler optimization details
	//
	// Toggle the per-package flag that causes Go compiler
	// optimization decisions to be reported as diagnostics.
	//
	// (The name is a legacy of a time when the Go compiler was
	// known as "gc". Renaming the command would break custom
	// client-side logic in VS Code.)
	GCDetails(context.Context, protocol.DocumentURI) error

	// LSP is a command that functions as a generic dispatcher, allowing clients
	// to execute any LSP RPC through the "workspace/executeCommand" request.
	//
	// This serves two primary purposes:
	//
	// 1. It provides a unified endpoint for clients that are restricted from
	//    making arbitrary LSP calls directly, giving them full access to the
	//    server's capabilities.
	//
	// 2. It allows the client and server to extend the standard protocol. A
	//    client can send custom parameters that are not part of the official
	//    LSP, enabling richer functionality.
	//
	// The command takes the target LSP method name and its parameters as a
	// [json.RawMessage], routing the call to the appropriate internal handler.
	LSP(context.Context, LSPArgs) (any, error)

	// ListKnownPackages: List known packages
	//
	// Retrieve a list of packages that are importable from the given URI.
	ListKnownPackages(context.Context, URIArg) (ListKnownPackagesResult, error)

	// ListImports: List imports of a file and its package
	//
	// Retrieve a list of imports in the given Go file, and the package it
	// belongs to.
	ListImports(context.Context, URIArg) (ListImportsResult, error)

	// AddImport: Add an import
	//
	// Ask the server to add an import path to a given Go file.  The method will
	// call applyEdit on the client so that clients don't have to apply the edit
	// themselves.
	AddImport(context.Context, AddImportArgs) error

	// ExtractToNewFile: Move selected declarations to a new file
	//
	// Used by the code action of the same name.
	ExtractToNewFile(context.Context, protocol.Location) error

	// StartDebugging: Start the gopls debug server
	//
	// Start the gopls debug server if it isn't running, and return the debug
	// address.
	StartDebugging(context.Context, DebuggingArgs) (DebuggingResult, error)

	// StartProfile: Start capturing a profile of gopls' execution
	//
	// Start a new pprof profile. Before using the resulting file, profiling must
	// be stopped with a corresponding call to StopProfile.
	//
	// This command is intended for internal use only, by the gopls benchmark
	// runner.
	StartProfile(context.Context, StartProfileArgs) (StartProfileResult, error)

	// StopProfile: Stop an ongoing profile
	//
	// This command is intended for internal use only, by the gopls benchmark
	// runner.
	StopProfile(context.Context, StopProfileArgs) (StopProfileResult, error)

	// GoVulncheck: run vulncheck synchronously.
	//
	// Run vulnerability check (`govulncheck`).
	//
	// This command is synchronous, and returns the govulncheck result.
	Vulncheck(context.Context, VulncheckArgs) (VulncheckResult, error)

	// RunGovulncheck: Run vulncheck asynchronously.
	//
	// Run vulnerability check (`govulncheck`).
	//
	// This command is asynchronous; clients must wait for the 'end' progress
	// notification and then retrieve results using gopls.fetch_vulncheck_result.
	//
	// Deprecated: clients should call gopls.vulncheck instead, which returns the
	// actual vulncheck result.
	RunGovulncheck(context.Context, VulncheckArgs) (RunVulncheckResult, error)

	// FetchVulncheckResult: Get known vulncheck result
	//
	// Fetch the result of latest vulnerability check (`govulncheck`).
	//
	// Deprecated: clients should call gopls.vulncheck instead, which returns the
	// actual vulncheck result.
	FetchVulncheckResult(context.Context, URIArg) (map[protocol.DocumentURI]*vulncheck.Result, error)

	// MemStats: Fetch memory statistics
	//
	// Call runtime.GC multiple times and return memory statistics as reported by
	// runtime.MemStats.
	//
	// This command is used for benchmarking, and may change in the future.
	MemStats(context.Context) (MemStatsResult, error)

	// WorkspaceStats: Fetch workspace statistics
	//
	// Query statistics about workspace builds, modules, packages, and files.
	//
	// This command is intended for internal use only, by the gopls stats
	// command.
	WorkspaceStats(context.Context) (WorkspaceStatsResult, error)

	// RunGoWorkCommand: Run `go work [args...]`, and apply the resulting go.work
	// edits to the current go.work file
	RunGoWorkCommand(context.Context, RunGoWorkArgs) error

	// AddTelemetryCounters: Update the given telemetry counters
	//
	// Gopls will prepend "fwd/" to all the counters updated using this command
	// to avoid conflicts with other counters gopls collects.
	AddTelemetryCounters(context.Context, AddTelemetryCountersArgs) error

	// AddTest: add test for the selected function
	AddTest(context.Context, protocol.Location) (*protocol.WorkspaceEdit, error)

	// MaybePromptForTelemetry: Prompt user to enable telemetry
	//
	// Checks for the right conditions, and then prompts the user
	// to ask if they want to enable Go telemetry uploading. If
	// the user responds 'Yes', the telemetry mode is set to "on".
	MaybePromptForTelemetry(context.Context) error

	// ChangeSignature: Perform a "change signature" refactoring
	//
	// This command is experimental, currently only supporting parameter removal.
	// Its signature will certainly change in the future (pun intended).
	ChangeSignature(context.Context, ChangeSignatureArgs) (*protocol.WorkspaceEdit, error)

	// DiagnoseFiles: Cause server to publish diagnostics for the specified files.
	//
	// This command is needed by the 'gopls {check,fix}' CLI subcommands.
	DiagnoseFiles(context.Context, DiagnoseFilesArgs) error

	// Views: List current Views on the server.
	//
	// This command is intended for use by gopls tests only.
	Views(context.Context) ([]View, error)

	// FreeSymbols: Browse free symbols referenced by the selection in a browser.
	//
	// This command is a query over a selected range of Go source
	// code. It reports the set of "free" symbols of the
	// selection: the set of symbols that are referenced within
	// the selection but are declared outside of it. This
	// information is useful for understanding at a glance what a
	// block of code depends on, perhaps as a precursor to
	// extracting it into a separate function.
	FreeSymbols(ctx context.Context, viewID string, loc protocol.Location) error

	// Assembly: Browse assembly listing of current function in a browser.
	//
	// This command opens a web-based disassembly listing of the
	// specified function symbol (plus any nested lambdas and defers).
	// The machine architecture is determined by the view.
	Assembly(_ context.Context, viewID, packageID, symbol string) error

	// ClientOpenURL: Request that the client open a URL in a browser.
	ClientOpenURL(_ context.Context, url string) error

	// ScanImports: force a synchronous scan of the imports cache.
	//
	// This command is intended for use by gopls tests only.
	ScanImports(context.Context) error

	// Packages: Return information about packages
	//
	// This command returns an empty result if the specified files
	// or directories are not associated with any Views on the
	// server yet.
	Packages(context.Context, PackagesArgs) (PackagesResult, error)

	// Modules: Return information about modules within a directory
	//
	// This command returns an empty result if there is no module, or if module
	// mode is disabled. Modules will not cause any new views to be loaded and
	// will only return modules associated with views that have already been
	// loaded, regardless of how it is called. Given current usage (by the
	// language server client), there should never be a case where Modules is
	// called on a path that has not already been loaded.
	Modules(context.Context, ModulesArgs) (ModulesResult, error)

	// PackageSymbols: Return information about symbols in the given file's package.
	PackageSymbols(context.Context, PackageSymbolsArgs) (PackageSymbolsResult, error)

	// ModifyTags: Add or remove struct tags on a given node.
	ModifyTags(context.Context, ModifyTagsArgs) error

	// MoveType: Move a type declaration to a different package.
	MoveType(context.Context, MoveTypeArgs) error
}

type RunTestsArgs struct {
	// The test file containing the tests to run.
	URI protocol.DocumentURI

	// Specific test names to run, e.g. TestFoo.
	Tests []string

	// Specific benchmarks to run, e.g. BenchmarkFoo.
	Benchmarks []string
}

type GenerateArgs struct {
	// URI for the directory to generate.
	Dir protocol.DocumentURI

	// Whether to generate recursively (go generate ./...)
	Recursive bool
}

type DocArgs struct {
	Location     protocol.Location
	ShowDocument bool // in addition to returning the URL, send showDocument
}

// TODO(rFindley): document the rest of these once the docgen is fleshed out.

type ApplyFixArgs struct {
	// The name of the fix to apply.
	//
	// For fixes suggested by analyzers, this is a string constant
	// advertised by the analyzer that matches the Category of
	// the analysis.Diagnostic with a SuggestedFix containing no edits.
	//
	// For fixes suggested by code actions, this is a string agreed
	// upon by the code action and golang.ApplyFix.
	Fix string

	// The portion of the document to fix.
	Location protocol.Location

	// Whether to resolve and return the edits.
	ResolveEdits bool
}

type URIArg struct {
	// The file URI.
	URI protocol.DocumentURI
}

type URIArgs struct {
	// The file URIs.
	URIs []protocol.DocumentURI
}

type CheckUpgradesArgs struct {
	// The go.mod file URI.
	URI protocol.DocumentURI
	// The modules to check.
	Modules []string
}

type DependencyArgs struct {
	// The go.mod file URI.
	URI protocol.DocumentURI
	// Additional args to pass to the go command.
	GoCmdArgs []string
	// Whether to add a require directive.
	AddRequire bool
}

type RemoveDependencyArgs struct {
	// The go.mod file URI.
	URI protocol.DocumentURI
	// The module path to remove.
	ModulePath string
	// If the module is tidied apart from the one unused diagnostic, we can
	// run `go get module@none`, and then run `go mod tidy`. Otherwise, we
	// must make textual edits.
	OnlyDiagnostic bool
}

type EditGoDirectiveArgs struct {
	// Any document URI within the relevant module.
	URI protocol.DocumentURI
	// The version to pass to `go mod edit -go`.
	Version string
}

type GoGetPackageArgs struct {
	// Any document URI within the relevant module.
	URI protocol.DocumentURI
	// The package to go get.
	Pkg        string
	AddRequire bool
}

type AddImportArgs struct {
	// ImportPath is the target import path that should
	// be added to the URI file
	ImportPath string
	// URI is the file that the ImportPath should be
	// added to
	URI protocol.DocumentURI
}

type ListKnownPackagesResult struct {
	// Packages is a list of packages relative
	// to the URIArg passed by the command request.
	// In other words, it omits paths that are already
	// imported or cannot be imported due to compiler
	// restrictions.
	Packages []string
}

type ListImportsResult struct {
	// Imports is a list of imports in the requested file.
	Imports []FileImport

	// PackageImports is a list of all imports in the requested file's package.
	PackageImports []PackageImport
}

type FileImport struct {
	// Path is the import path of the import.
	Path string
	// Name is the name of the import, e.g. `foo` in `import foo "strings"`.
	Name string
}

type PackageImport struct {
	// Path is the import path of the import.
	Path string
}

type DebuggingArgs struct {
	// Optional: the address (including port) for the debug server to listen on.
	// If not provided, the debug server will bind to "localhost:0", and the
	// full debug URL will be contained in the result.
	//
	// If there is more than one gopls instance along the serving path (i.e. you
	// are using a daemon), each gopls instance will attempt to start debugging.
	// If Addr specifies a port, only the daemon will be able to bind to that
	// port, and each intermediate gopls instance will fail to start debugging.
	// For this reason it is recommended not to specify a port (or equivalently,
	// to specify ":0").
	//
	// If the server was already debugging this field has no effect, and the
	// result will contain the previously configured debug URL(s).
	Addr string
}

type DebuggingResult struct {
	// The URLs to use to access the debug servers, for all gopls instances in
	// the serving path. For the common case of a single gopls instance (i.e. no
	// daemon), this will be exactly one address.
	//
	// In the case of one or more gopls instances forwarding the LSP to a daemon,
	// URLs will contain debug addresses for each server in the serving path, in
	// serving order. The daemon debug address will be the last entry in the
	// slice. If any intermediate gopls instance fails to start debugging, no
	// error will be returned but the debug URL for that server in the URLs slice
	// will be empty.
	URLs []string
}

// StartProfileArgs holds the arguments to the StartProfile command.
//
// It is a placeholder for future compatibility.
type StartProfileArgs struct {
}

// StartProfileResult holds the result of the StartProfile command.
//
// It is a placeholder for future compatibility.
type StartProfileResult struct {
}

// StopProfileArgs holds the arguments to the StopProfile command.
//
// It is a placeholder for future compatibility.
type StopProfileArgs struct {
}

// StopProfileResult holds the result to the StopProfile command.
type StopProfileResult struct {
	// File is the profile file name.
	File string
}

type ResetGoModDiagnosticsArgs struct {
	URIArg

	// Optional: source of the diagnostics to reset.
	// If not set, all resettable go.mod diagnostics will be cleared.
	DiagnosticSource string
}

type VulncheckArgs struct {
	// Any document in the directory from which govulncheck will run.
	URI protocol.DocumentURI

	// Package pattern. E.g. "", ".", "./...".
	Pattern string

	// TODO: -tests
}

// RunVulncheckResult holds the result of asynchronously starting the vulncheck
// command.
type RunVulncheckResult struct {
	// Token holds the progress token for LSP workDone reporting of the vulncheck
	// invocation.
	Token protocol.ProgressToken
}

// VulncheckResult holds the result of synchronously running the vulncheck
// command.
type VulncheckResult struct {
	// Result holds the result of running vulncheck.
	Result *vulncheck.Result
	// Token holds the progress token used to report progress during back to the
	// LSP client during vulncheck execution.
	Token protocol.ProgressToken
}

// MemStatsResult holds selected fields from runtime.MemStats.
type MemStatsResult struct {
	HeapAlloc  uint64
	HeapInUse  uint64
	TotalAlloc uint64
}

// WorkspaceStatsResult returns information about the size and shape of the
// workspace.
type WorkspaceStatsResult struct {
	Files FileStats   // file stats for the cache
	Views []ViewStats // stats for each view in the session
}

// FileStats holds information about a set of files.
type FileStats struct {
	Total   int // total number of files
	Largest int // number of bytes in the largest file
	Errs    int // number of files that could not be read
}

// ViewStats holds information about a single View in the session.
type ViewStats struct {
	GoCommandVersion  string       // version of the Go command resolved for this view
	AllPackages       PackageStats // package info for all packages (incl. dependencies)
	WorkspacePackages PackageStats // package info for workspace packages
	Diagnostics       int          // total number of diagnostics in the workspace
}

// PackageStats holds information about a collection of packages.
type PackageStats struct {
	Packages        int // total number of packages
	LargestPackage  int // number of files in the largest package
	CompiledGoFiles int // total number of compiled Go files across all packages
	Modules         int // total number of unique modules
}

type RunGoWorkArgs struct {
	ViewID    string   // ID of the view to run the command from
	InitFirst bool     // Whether to run `go work init` first
	Args      []string // Args to pass to `go work`
}

// AddTelemetryCountersArgs holds the arguments to the AddCounters command
// that updates the telemetry counters.
type AddTelemetryCountersArgs struct {
	// Names and Values must have the same length.
	Names  []string // Name of counters.
	Values []int64  // Values added to the corresponding counters. Must be non-negative.
}

// ChangeSignatureArgs specifies a "change signature" refactoring to perform.
//
// The new signature is expressed via the NewParams and NewResults fields. The
// elements of these lists each describe a new field of the signature, by
// either referencing a field in the old signature or by defining a new field:
//   - If the element is an integer, it references a positional parameter in the
//     old signature.
//   - If the element is a string, it is parsed as a new field to add.
//
// Suppose we have a function `F(a, b int) (string, error)`. Here are some
// examples of refactoring this signature in practice, eliding the 'Location'
// and 'ResolveEdits' fields.
//   - `{ "NewParams": [0], "NewResults": [0, 1] }` removes the second parameter
//   - `{ "NewParams": [1, 0], "NewResults": [0, 1] }` flips the parameter order
//   - `{ "NewParams": [0, 1, "a int"], "NewResults": [0, 1] }` adds a new field
//   - `{ "NewParams": [1, 2], "NewResults": [1] }` drops the `error` result
type ChangeSignatureArgs struct {
	// Location is any range inside the function signature. By convention, this
	// is the same location provided in the codeAction request.
	Location protocol.Location // a range inside of the function signature, as passed to CodeAction

	// NewParams describes parameters of the new signature.
	// An int value references a parameter in the old signature by index.
	// A string value describes a new parameter field (e.g. "x int").
	NewParams []ChangeSignatureParam

	// NewResults describes results of the new signature (see above).
	// An int value references a result in the old signature by index.
	// A string value describes a new result field (e.g. "err error").
	NewResults []ChangeSignatureParam

	// Whether to resolve and return the edits.
	ResolveEdits bool
}

// ChangeSignatureParam implements the API described in the doc string of
// [ChangeSignatureArgs]: a union of JSON int | string.
type ChangeSignatureParam struct {
	OldIndex int
	NewField string
}

func (a *ChangeSignatureParam) UnmarshalJSON(b []byte) error {
	var s string
	if err := json.Unmarshal(b, &s); err == nil {
		a.NewField = s
		return nil
	}
	var i int
	if err := json.Unmarshal(b, &i); err == nil {
		a.OldIndex = i
		return nil
	}
	return fmt.Errorf("must be int or string")
}

func (a ChangeSignatureParam) MarshalJSON() ([]byte, error) {
	if a.NewField != "" {
		return json.Marshal(a.NewField)
	}
	return json.Marshal(a.OldIndex)
}

// DiagnoseFilesArgs specifies a set of files for which diagnostics are wanted.
type DiagnoseFilesArgs struct {
	Files []protocol.DocumentURI
}

// A View holds summary information about a cache.View.
type View struct {
	ID         string               // view ID (the index of this view among all views created)
	Type       string               // view type (via cache.ViewType.String)
	Root       protocol.DocumentURI // root dir of the view (e.g. containing go.mod or go.work)
	Folder     protocol.DocumentURI // workspace folder associated with the view
	EnvOverlay []string             // environment variable overrides
}

// PackagesArgs holds arguments for the Packages command.
type PackagesArgs struct {
	// Files is a list of files and directories whose associated
	// packages should be described by the result.
	//
	// In some cases, a file may belong to more than one package;
	// the result may describe any of them.
	Files []protocol.DocumentURI

	// Enumerate all packages under the directory loadable with
	// the ... pattern.
	// The search does not cross the module boundaries and
	// does not return packages that are not yet loaded.
	// (e.g. those excluded by the gopls directory filter setting,
	// or the go.work configuration)
	Recursive bool `json:"Recursive,omitempty"`

	// Mode controls the types of information returned for each package.
	Mode PackagesMode
}

// PackagesMode controls the details to include in PackagesResult.
type PackagesMode uint64

const (
	// Populate the [TestFile.Tests] field in [Package] returned by the
	// Packages command.
	NeedTests PackagesMode = 1 << iota
)

// PackagesResult is the result of the Packages command.
type PackagesResult struct {
	// Packages is an unordered list of package metadata.
	Packages []Package

	// Module maps module path to module metadata for
	// all the modules of the returned Packages.
	Module map[string]Module
}

// Package describes a Go package (not an empty parent).
type Package struct {
	// Package path.
	Path string
	// Module path. Empty if the package doesn't
	// belong to any module.
	ModulePath string
	// q in a "p [q.test]" package.
	ForTest string

	// Note: the result does not include the directory name
	// of the package because mapping between a package and
	// a folder is not possible in certain build systems.
	// If directory info is needed, one can guess it
	// from the TestFile's file name.

	// TestFiles contains the subset of the files of the package
	// whose name ends with "_test.go".
	// They are ordered deterministically as determined
	// by the underlying build system.
	TestFiles []TestFile
}

type Module struct {
	Path    string               // module path
	Version string               // module version if any.
	GoMod   protocol.DocumentURI // path to the go.mod file.
}

type TestFile struct {
	URI protocol.DocumentURI // a *_test.go file

	// Tests is the list of tests in File, including subtests.
	//
	// The set of subtests is not exhaustive as in general they may be
	// dynamically generated, so it is impossible for static heuristics
	// to enumerate them.
	//
	// Tests are lexically ordered.
	// Since subtest names are prefixed by their top-level test names
	// each top-level test precedes its subtests.
	Tests []TestCase
}

// TestCase represents a test case.
// A test case can be a top-level Test/Fuzz/Benchmark/Example function,
// as recognized by 'go list' or 'go test -list', or
// a subtest within a top-level function.
type TestCase struct {
	// Name is the complete name of the test (Test, Benchmark, Example, or Fuzz)
	// or the subtest as it appears in the output of go test -json.
	// The server may attempt to infer names of subtests by static
	// analysis; if so, it should aim to simulate the actual computed
	// name of the test, including any disambiguating suffix such as "#01".
	// To run only this test, clients need to compute the -run, -bench, -fuzz
	// flag values by first splitting the Name with "/" and
	// quoting each element with "^" + regexp.QuoteMeta(Name) + "$".
	// e.g. TestToplevel/Inner.Subtest → -run=^TestToplevel$/^Inner\.Subtest$
	Name string

	// Loc is the filename and range enclosing this test function
	// or the subtest. This is used to place the gutter marker
	// and group tests based on location.
	// For subtests whose test names can be determined statically,
	// this can be either t.Run or the test data table
	// for table-driven setup.
	// Some testing frameworks allow to declare the actual test
	// logic in a different file. For example, one can define
	// a testify test suite in suite_test.go and use it from
	// main_test.go.
	/*
	   -- main_test.go --
	   ...
	   func TestFoo(t *testing.T) {
	       suite.Run(t, new(MyTestSuite))
	   }
	   -- suite_test.go --
	   type MyTestSuite struct {
	   	suite.Suite
	   }
	   func (suite *MyTestSuite) TestBar() { ... }
	*/
	// In this case, the testing framework creates "TestFoo/TestBar"
	// and the corresponding test case belongs to "main_test.go"
	// TestFile. However, the test case has "suite_test.go" as its
	// file location.
	Loc protocol.Location
}

type ModulesArgs struct {
	// Dir is the directory in which to search for go.mod files.
	Dir protocol.DocumentURI

	// MaxDepth is the directory walk limit.
	// A value of 0 means inspect only Dir.
	// 1 means inspect its child directories too, and so on.
	// A negative value removes the limit.
	MaxDepth int
}

type ModulesResult struct {
	Modules []Module
}

type PackageSymbolsArgs struct {
	URI protocol.DocumentURI
}

type PackageSymbolsResult struct {
	PackageName string
	// Files is a list of files in the given URI's package.
	Files   []protocol.DocumentURI
	Symbols []PackageSymbol
}

// PackageSymbol has the same fields as DocumentSymbol, with an additional int field "File"
// which stores the index of the symbol's file in the PackageSymbolsResult.Files array
type PackageSymbol struct {
	Name string `json:"name"`

	Detail string `json:"detail,omitempty"`

	// protocol.SymbolKind maps an integer to an enum:
	// https://microsoft.github.io/language-server-protocol/specifications/lsp/3.17/specification/#symbolKind
	// i.e. File = 1
	Kind protocol.SymbolKind `json:"kind"`

	Tags []protocol.SymbolTag `json:"tags,omitempty"`

	Range protocol.Range `json:"range"`

	SelectionRange protocol.Range `json:"selectionRange"`

	Children []PackageSymbol `json:"children,omitempty"`

	// Index of this symbol's file in PackageSymbolsResult.Files
	File int `json:"file,omitempty"`
}

// ModifyTagsArgs holds variables that determine how struct tags are modified.
type ModifyTagsArgs struct {
	URI                  protocol.DocumentURI // uri of the file to be modified
	Range                protocol.Range       // range in the file for where to modify struct tags
	Add                  string               // comma-separated list of tags to add; i.e. "json,xml"
	AddOptions           string               // comma-separated list of options to add, per tag; i.e. "json=omitempty"
	Remove               string               // comma-separated list of tags to remove
	RemoveOptions        string               // comma-separated list of options to remove
	Clear                bool                 // if set, clear all tags. tags are cleared before any new tags are added
	ClearOptions         bool                 // if set, clear all tag options; options are cleared before any new options are added
	Overwrite            bool                 // if set, replace existing tags when adding
	SkipUnexportedFields bool                 // if set, do not modify tags on unexported struct fields
	Transform            string               // transform rule for adding tags; i.e. "snakecase"
	ValueFormat          string               // format for the tag's value, after transformation; for example "column:{field}"
}

type LSPArgs struct {
	Method string          `json:"method"`
	Param  json.RawMessage `json:"param"`
}

// MoveTypeArgs specifies a "move type" refactoring to perform.
type MoveTypeArgs struct {
	// The location of the type to move.
	Location protocol.Location
	// TODO(mkalil): Determine format of the parameter that specifies where to
	// move the type to.
}
