// Copyright 2020 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.

package bench

import (
	"flag"
	"fmt"
	"strings"
	"testing"

	. "golang.org/x/tools/internal/lsp/regtest"

	"golang.org/x/tools/internal/lsp/fake"
)

// dummyCompletionFunction to test manually configured completion using CLI.
func dummyCompletionFunction() { const s = "placeholder"; fmt.Printf("%s", s) }

type completionBenchOptions struct {
	workdir, file, locationRegexp string
	printResults                  bool
	// hook to run edits before initial completion, not supported for manually
	// configured completions.
	preCompletionEdits func(*Env)
}

var completionOptions = completionBenchOptions{}

func init() {
	flag.StringVar(&completionOptions.workdir, "completion_workdir", "", "directory to run completion benchmarks in")
	flag.StringVar(&completionOptions.file, "completion_file", "", "relative path to the file to complete in")
	flag.StringVar(&completionOptions.locationRegexp, "completion_regexp", "", "regexp location to complete at")
	flag.BoolVar(&completionOptions.printResults, "completion_print_results", false, "whether to print completion results")
}

func benchmarkCompletion(options completionBenchOptions, t *testing.T) {
	if completionOptions.workdir == "" {
		t.Skip("-completion_workdir not configured, skipping benchmark")
	}

	opts := stressTestOptions(options.workdir)

	// Completion gives bad results if IWL is not yet complete, so we must await
	// it first (and therefore need hooks).
	opts = append(opts, SkipHooks(false))

	WithOptions(opts...).Run(t, "", func(t *testing.T, env *Env) {
		env.OpenFile(options.file)

		// Run edits required for this completion.
		if options.preCompletionEdits != nil {
			options.preCompletionEdits(env)
		}

		// Run a completion to make sure the system is warm.
		pos := env.RegexpSearch(options.file, options.locationRegexp)
		completions := env.Completion(options.file, pos)

		if options.printResults {
			fmt.Println("Results:")
			for i := 0; i < len(completions.Items); i++ {
				fmt.Printf("\t%d. %v\n", i, completions.Items[i])
			}
		}

		results := testing.Benchmark(func(b *testing.B) {
			for i := 0; i < b.N; i++ {
				env.Completion(options.file, pos)
			}
		})

		printBenchmarkResults(results)
	})
}

// endPosInBuffer returns the position for last character in the buffer for
// the given file.
func endPosInBuffer(env *Env, name string) fake.Pos {
	buffer := env.Editor.BufferText(name)
	lines := strings.Split(buffer, "\n")
	numLines := len(lines)

	return fake.Pos{
		Line:   numLines - 1,
		Column: len([]rune(lines[numLines-1])),
	}
}

// Benchmark completion at a specified file and location. When no CLI options
// are specified, this test is skipped.
// To Run (from x/tools/gopls) against the dummy function above:
//
//	go test -v ./internal/regtest/bench -run=TestBenchmarkConfiguredCompletion
//	-completion_workdir="$HOME/Developer/tools"
//	-completion_file="gopls/internal/regtest/completion_bench_test.go"
//	-completion_regexp="dummyCompletionFunction.*fmt\.Printf\(\"%s\", s(\))"
func TestBenchmarkConfiguredCompletion(t *testing.T) {
	benchmarkCompletion(completionOptions, t)
}

// To run (from x/tools/gopls):
// 	go test -v ./internal/regtest/bench -run TestBenchmark<>Completion
//	-completion_workdir="$HOME/Developer/tools"
// where <> is one of the tests below. completion_workdir should be path to
// x/tools on your system.

// Benchmark struct completion in tools codebase.
func TestBenchmarkStructCompletion(t *testing.T) {
	file := "internal/lsp/cache/session.go"

	preCompletionEdits := func(env *Env) {
		env.OpenFile(file)
		originalBuffer := env.Editor.BufferText(file)
		env.EditBuffer(file, fake.Edit{
			End:  endPosInBuffer(env, file),
			Text: originalBuffer + "\nvar testVariable map[string]bool = Session{}.\n",
		})
	}

	benchmarkCompletion(completionBenchOptions{
		workdir:            completionOptions.workdir,
		file:               file,
		locationRegexp:     `var testVariable map\[string\]bool = Session{}(\.)`,
		preCompletionEdits: preCompletionEdits,
		printResults:       completionOptions.printResults,
	}, t)
}

// Benchmark import completion in tools codebase.
func TestBenchmarkImportCompletion(t *testing.T) {
	benchmarkCompletion(completionBenchOptions{
		workdir:        completionOptions.workdir,
		file:           "internal/lsp/source/completion/completion.go",
		locationRegexp: `go\/()`,
		printResults:   completionOptions.printResults,
	}, t)
}

// Benchmark slice completion in tools codebase.
func TestBenchmarkSliceCompletion(t *testing.T) {
	file := "internal/lsp/cache/session.go"

	preCompletionEdits := func(env *Env) {
		env.OpenFile(file)
		originalBuffer := env.Editor.BufferText(file)
		env.EditBuffer(file, fake.Edit{
			End:  endPosInBuffer(env, file),
			Text: originalBuffer + "\nvar testVariable []byte = \n",
		})
	}

	benchmarkCompletion(completionBenchOptions{
		workdir:            completionOptions.workdir,
		file:               file,
		locationRegexp:     `var testVariable \[\]byte (=)`,
		preCompletionEdits: preCompletionEdits,
		printResults:       completionOptions.printResults,
	}, t)
}

// Benchmark deep completion in function call in tools codebase.
func TestBenchmarkFuncDeepCompletion(t *testing.T) {
	file := "internal/lsp/source/completion/completion.go"
	fileContent := `
func (c *completer) _() {
	c.inference.kindMatches(c.)
}
`
	preCompletionEdits := func(env *Env) {
		env.OpenFile(file)
		originalBuffer := env.Editor.BufferText(file)
		env.EditBuffer(file, fake.Edit{
			End:  endPosInBuffer(env, file),
			Text: originalBuffer + fileContent,
		})
	}

	benchmarkCompletion(completionBenchOptions{
		workdir:            completionOptions.workdir,
		file:               file,
		locationRegexp:     `func \(c \*completer\) _\(\) {\n\tc\.inference\.kindMatches\((c)`,
		preCompletionEdits: preCompletionEdits,
		printResults:       completionOptions.printResults,
	}, t)
}
