// Copyright 2017 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:build go1.16 && (linux || darwin)
// +build go1.16
// +build linux darwin

package main

import (
	"context"
	"fmt"
	"log"
	"net/http/httptest"
	"net/url"
	"os"
	"strings"
	"sync"
	"testing"
	"time"

	"golang.org/x/build/buildlet"
	"golang.org/x/build/dashboard"
	"golang.org/x/build/internal/coordinator/pool"
	"golang.org/x/build/internal/gophers"
)

type TestBuildletPool struct {
	clients map[string]buildlet.Client
	mu      sync.Mutex
}

// GetBuildlet finds the first available buildlet for the hostType and returns
// it, or an error if no buildlets are available for that hostType.
func (tp *TestBuildletPool) GetBuildlet(ctx context.Context, hostType string, lg pool.Logger) (buildlet.Client, error) {
	tp.mu.Lock()
	defer tp.mu.Unlock()
	c, ok := tp.clients[hostType]
	if ok {
		return c, nil
	}
	return nil, fmt.Errorf("No client found for host type %s", hostType)
}

// Add sets the given client for the given hostType, overriding any previous
// entries.
func (tp *TestBuildletPool) Add(hostType string, client buildlet.Client) {
	tp.mu.Lock()
	if tp.clients == nil {
		tp.clients = make(map[string]buildlet.Client)
	}
	tp.clients[hostType] = client
	tp.mu.Unlock()
}

func (tp *TestBuildletPool) Remove(hostType string) {
	tp.mu.Lock()
	delete(tp.clients, hostType)
	tp.mu.Unlock()
}

func (tp *TestBuildletPool) String() string { return "test" }

func (tp *TestBuildletPool) HasCapacity(string) bool { return true }

var testPool = &TestBuildletPool{}

func TestHandleBuildletCreateWrongMethod(t *testing.T) {
	req := httptest.NewRequest("GET", "/buildlet/create", nil)
	w := httptest.NewRecorder()
	handleBuildletCreate(w, req)
	if w.Code != 400 {
		t.Fatalf("GET /buildlet/create: expected code 400, got %d", w.Code)
	}
	if body := w.Body.String(); !strings.Contains(body, "POST required") {
		t.Fatalf("GET /buildlet/create: expected 'POST required' error, got %s", body)
	}
}

func TestHandleBuildletCreateOldVersion(t *testing.T) {
	data := url.Values{}
	data.Set("version", "20150922")
	req := httptest.NewRequest("POST", "/buildlet/create", strings.NewReader(data.Encode()))
	req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
	w := httptest.NewRecorder()
	handleBuildletCreate(w, req)
	if w.Code != 400 {
		t.Fatalf("GET /buildlet/create: expected code 400, got %d", w.Code)
	}
	if body := w.Body.String(); !strings.Contains(body, `client version "20150922" is too old`) {
		t.Fatalf("GET /buildlet/create: expected 'version too old' error, got %s", body)
	}
}

func addBuilder(name string) {
	dashboard.Builders[name] = &dashboard.BuildConfig{
		Name:     name,
		HostType: "test-host",
		Notes:    "Dummy client for testing",
	}
	dashboard.Hosts["test-host"] = &dashboard.HostConfig{
		HostType: "test-host",
		Owners:   []*gophers.Person{{Emails: []string{"test@golang.org"}}},
	}
	testPool.Add("test-host", &buildlet.FakeClient{})
}

func removeBuilder(name string) {
	delete(dashboard.Builders, name)
	delete(dashboard.Builders, "test-host")
	testPool.Remove("test-host")
}

const buildName = "linux-amd64-test"

type tlogger struct{ t *testing.T }

func (t tlogger) Write(p []byte) (int, error) {
	t.t.Logf("LOG: %s", p)
	return len(p), nil
}

func TestHandleBuildletCreate_PreStream(t *testing.T) {
	log.SetOutput(tlogger{t})
	defer log.SetOutput(os.Stderr)
	addBuilder(buildName)
	remoteBuildlets.m = map[string]*remoteBuildlet{}
	pool.TestPoolHook = func(_ *dashboard.HostConfig) pool.Buildlet { return testPool }
	defer func() {
		timeNow = time.Now
		removeBuilder(buildName)
		pool.TestPoolHook = nil
	}()
	timeNow = func() time.Time { return time.Unix(123, 0).In(time.UTC) }
	data := url.Values{}
	data.Set("version", "20160922")
	data.Set("builderType", buildName)
	req := httptest.NewRequest("POST", "/buildlet/create", strings.NewReader(data.Encode()))
	req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
	req.SetBasicAuth("gopher", "fake-not-checked-password") // auth is handled in outer wrapper
	w := httptest.NewRecorder()
	handleBuildletCreate(w, req)
	if w.Code != 200 {
		t.Fatal("bad code", w.Code, w.Body.String())
	}
	want := `{"User":"gopher","Name":"gopher-linux-amd64-test-0","HostType":"test-host","BuilderType":"linux-amd64-test","Created":"1970-01-01T00:02:03Z","Expires":"1970-01-01T00:32:03Z"}`
	if got := strings.TrimSpace(w.Body.String()); got != want {
		t.Errorf("unexpected output.\n got: %s\nwant: %s\n", got, want)
	}
}

func TestHandleBuildletCreate_Stream(t *testing.T) {
	log.SetOutput(tlogger{t})
	defer log.SetOutput(os.Stderr)
	addBuilder(buildName)
	remoteBuildlets.m = map[string]*remoteBuildlet{}
	pool.TestPoolHook = func(_ *dashboard.HostConfig) pool.Buildlet { return testPool }
	defer func() {
		timeNow = time.Now
		removeBuilder(buildName)
		pool.TestPoolHook = nil
	}()
	timeNow = func() time.Time { return time.Unix(123, 0).In(time.UTC) }
	data := url.Values{}
	data.Set("version", buildlet.GomoteCreateStreamVersion)
	data.Set("builderType", buildName)
	req := httptest.NewRequest("POST", "/buildlet/create", strings.NewReader(data.Encode()))
	req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
	req.SetBasicAuth("gopher", "fake-not-checked-password") // auth is handled in outer wrapper
	w := httptest.NewRecorder()
	handleBuildletCreate(w, req)
	if w.Code != 200 {
		t.Fatal("bad code", w.Code, w.Body.String())
	}
	want := `{"buildlet":{"User":"gopher","Name":"gopher-linux-amd64-test-0","HostType":"test-host","BuilderType":"linux-amd64-test","Created":"1970-01-01T00:02:03Z","Expires":"1970-01-01T00:32:03Z"}}`
	if got := strings.TrimSpace(w.Body.String()); got != want {
		t.Errorf("unexpected output.\n got: %s\nwant: %s\n", got, want)
	}
}
