// Copyright 2019 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 middleware

import (
	"context"
	"fmt"
	"net/http"
	"net/http/httptest"
	"testing"
	"time"

	"github.com/alicebob/miniredis/v2"
	"github.com/go-redis/redis/v8"
	"github.com/google/go-cmp/cmp"
	"go.opencensus.io/stats/view"
	"golang.org/x/pkgsite/internal/config"
)

func TestLegacyQuota(t *testing.T) {
	mw := LegacyQuota(config.QuotaSettings{QPS: 1, Burst: 2, MaxEntries: 1, RecordOnly: boolptr(false)})
	var npass int
	h := func(w http.ResponseWriter, r *http.Request) {
		npass++
	}
	ts := httptest.NewServer(mw(http.HandlerFunc(h)))
	defer ts.Close()
	c := ts.Client()
	view.Register(QuotaResultCount)
	defer view.Unregister(QuotaResultCount)

	check := func(msg string, nwant int) {
		npass = 0
		for i := 0; i < 5; i++ {
			req, err := http.NewRequest("GET", ts.URL, nil)
			if err != nil {
				t.Fatal(err)
			}
			req.Header.Add("X-Forwarded-For", "1.2.3.4, and more")
			res, err := c.Do(req)
			if err != nil {
				t.Fatalf("%s: %v", msg, err)
			}
			res.Body.Close()
			want := http.StatusOK
			if i >= nwant {
				want = http.StatusTooManyRequests
			}
			if got := res.StatusCode; got != want {
				t.Errorf("%s, #%d: got %d, want %d", msg, i, got, want)
			}
		}
		if npass != nwant {
			t.Errorf("%s: got %d requests to pass, want %d", msg, npass, nwant)
		}
	}

	// When making multiple requests in quick succession from the same IP,
	// only the first two get through; the rest are blocked.
	check("before", 2)
	// After a second (and a bit more), we should have one token back, meaning
	// we can serve one request.
	time.Sleep(1100 * time.Millisecond)
	check("after", 1)

	// Check the metric.
	got := collectViewData(t)
	want := map[bool]int{true: 7, false: 3} // only 3 requests of the ten we sent get through.
	if diff := cmp.Diff(want, got); diff != "" {
		t.Errorf("mismatch (-want +got):\n%s", diff)
	}
}

func TestLegacyQuotaRecordOnly(t *testing.T) {
	// Like TestQuota, but with in RecordOnly mode nothing is actually blocked.
	mw := LegacyQuota(config.QuotaSettings{QPS: 1, Burst: 2, MaxEntries: 1, RecordOnly: boolptr(true)})
	npass := 0
	h := func(w http.ResponseWriter, r *http.Request) {
		npass++
	}
	ts := httptest.NewServer(mw(http.HandlerFunc(h)))
	defer ts.Close()
	c := ts.Client()
	view.Register(QuotaResultCount)
	defer view.Unregister(QuotaResultCount)

	const nreq = 100
	for i := 0; i < nreq; i++ {
		req, err := http.NewRequest("GET", ts.URL, nil)
		if err != nil {
			t.Fatal(err)
		}
		req.Header.Add("X-Forwarded-For", "1.2.3.4, and more")
		res, err := c.Do(req)
		if err != nil {
			t.Fatal(err)
		}
		res.Body.Close()
	}
	if npass != nreq {
		t.Errorf("%d passed, want %d", npass, nreq)
	}
	got := collectViewData(t)
	want := map[bool]int{true: nreq - 2, false: 2} // record as if blocking occurred
	if diff := cmp.Diff(want, got); diff != "" {
		t.Errorf("mismatch (-want +got):\n%s", diff)
	}
}

func TestLegacyQuotaBadKey(t *testing.T) {
	// Verify that invalid IP addresses are not blocked.
	mw := LegacyQuota(config.QuotaSettings{QPS: 1, Burst: 2, MaxEntries: 1, RecordOnly: boolptr(true)})
	npass := 0
	h := func(w http.ResponseWriter, r *http.Request) {
		npass++
	}
	ts := httptest.NewServer(mw(http.HandlerFunc(h)))
	defer ts.Close()
	c := ts.Client()
	view.Register(QuotaResultCount)
	defer view.Unregister(QuotaResultCount)

	const nreq = 100
	for i := 0; i < nreq; i++ {
		req, err := http.NewRequest("GET", ts.URL, nil)
		if err != nil {
			t.Fatal(err)
		}
		req.Header.Add("X-Forwarded-For", "not.a.valid.ip, and more")
		res, err := c.Do(req)
		if err != nil {
			t.Fatal(err)
		}
		res.Body.Close()
	}
	if npass != nreq {
		t.Errorf("%d passed, want %d", npass, nreq)
	}
	got := collectViewData(t)
	want := map[bool]int{false: nreq} // no blocking occurred
	if diff := cmp.Diff(want, got); diff != "" {
		t.Errorf("mismatch (-want +got):\n%s", diff)
	}
}

func collectViewData(t *testing.T) map[bool]int {
	m := map[bool]int{}
	rows, err := view.RetrieveData(QuotaResultCount.Name)
	if err != nil {
		t.Fatal(err)
	}
	for _, row := range rows {
		blocked := row.Tags[0].Value == "blocked"
		if err != nil {
			t.Fatalf("collectViewData: %v", err)
		}
		count := int(row.Data.(*view.CountData).Value)
		m[blocked] = count
	}
	return m
}

func TestIPKey(t *testing.T) {
	for _, test := range []struct {
		in   string
		want interface{}
	}{
		{"", ""},
		{"1.2.3", ""},
		{"128.197.17.3", "128.197.17.0"},
		{"  128.197.17.3, foo  ", "128.197.17.0"},
		{"2001:db8::ff00:42:8329", "2001:db8::ff00:42:8300"},
	} {
		got := ipKey(test.in)
		if got != test.want {
			t.Errorf("%q: got %v, want %v", test.in, got, test.want)
		}
	}
}

func boolptr(b bool) *bool { return &b }

func TestEnforceQuota(t *testing.T) {
	// This test is inherently time-dependent, so inherently flaky, especially on CI.
	// So run it a few times before giving up.
	ctx := context.Background()
	s, err := miniredis.Run()
	if err != nil {
		t.Fatal(err)
	}
	defer s.Close()

	c := redis.NewClient(&redis.Options{Addr: s.Addr()})
	defer c.Close()

	const qps = 5

	var failReason string
	for n := 0; n < 10; n++ {
		failReason = ""

		check := func(n int, ip string, want bool) {
			if failReason != "" {
				return
			}
			for i := 0; i < n; i++ {
				blocked, reason := enforceQuota(ctx, c, qps, ip+",x", []byte{1, 2, 3, 4})
				got := !blocked
				if got != want {
					failReason = fmt.Sprintf("%d: got %t, want %t (reason=%q)", i, got, want, reason)
					break
				}
			}
		}

		check(qps, "1.2.3.4", true) // first qps requests are allowed
		check(1, "1.2.3.4", false)  // anything after that fails
		check(1, "1.2.3.5", false)  // low-order byte doesn't matter
		check(qps, "1.2.4.1", true) // other IP is allowed
		check(1, "1.2.4.9", false)  // other IP blocked after qps requests

		if failReason == "" {
			return
		}
		time.Sleep(2 * time.Second)
	}
	t.Error(failReason)
}
