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

// Package webtest implements script-based testing for web servers.
//
// The scripts, described below, can be run against http.Handler
// implementations or against running servers. Testing against an
// http.Handler makes it easier to test handlers serving multiple sites
// as well as scheme-based features like redirecting to HTTPS.
// Testing against a running server provides a more complete end-to-end test.
//
// The test functions TestHandler and TestServer take a *testing.T
// and a glob pattern, which must match at least one file.
// They create a subtest of the top-level test for each script.
// Within each per-script subtest, they create a per-case subtest
// for each case in the script, making it easy to run selected cases.
//
// The functions CheckHandler and CheckServer are similar but do
// not require a *testing.T, making them suitable for use in other contexts.
// They run the entire script and return a multiline error summarizing
// any problems.
//
// Scripts
//
// A script is a text file containing a sequence of cases, separated by blank lines.
// Lines beginning with # characters are ignored as comments.
// A case is a sequence of lines describing a request, along with checks to be
// applied to the response. For example, here is a trivial script:
//
//	GET /
//	body contains Go is an open source programming language
//
// This script has a single case. The first line describes the request.
// The second line describes a single check to be applied to the response.
// In this case, the request is a GET of the URL /, and the response body
// must contain the text “Go is an open source programming language”.
//
// Requests
//
// Each case begins with a line starting with GET, HEAD, or POST.
// The argument (the remainder of the line) is the URL to be used in the request.
// Following this line, the request can be further customized using
// lines of the form
//
//	<verb> <text>
//
// where the verb is a single space-separated word and the text is arbitrary text
// to the end of the line, or multiline text (described below).
//
// The possible values for <verb> are as follows.
//
// The verb “hint” specifies text to be printed if the test case fails, as a
// hint about what might be wrong.
//
// The verbs “postbody”, “postquery”, and “posttype” customize a POST request.
//
// For example:
//
//	POST /api
//	posttype application/json
//	postbody {"go": true}
//
// This describes a POST request with a posted Content-Type of “application/json”
// and a body “{"go": true}”.
//
// The “postquery” verb specifies a post body in the form of a sequence of
// key-value pairs, query-encoded and concatenated automatically as a
// convenience. Using “postquery” also sets the default posted Content-Type
// to “application/x-www-form-urlencoded”.
//
// For example:
//
//	POST /api
//	postquery
//		x=hello world
//		y=Go & You
//
// This stanza sends a request with post body “x=hello+world&y=Go+%26+You”.
// (The multiline syntax is described in detail below.)
//
// Checks
//
// By default, a stanza like the ones above checks only that the request
// succeeds in returning a response with HTTP status code 200 (OK).
// Additional checks are specified by more lines of the form
//
//	<value> [<key>] <op> <text>
//
// In the example above, <value> is “body”, there is no <key>,
// <op> is “contains”, and <text> is “Go is an open source programming language”.
// Whether there is a <key> depends on the <value>; “body” does not have one.
//
// The possible values for <value> are:
//
//	body - the full response body
//	code - the HTTP status code
//	header <key> - the value in the header line with the given key
//	redirect - the target of a redirect, as found in the Location header
//	trimbody - the response body, trimmed
//
// If a case contains no check of “code”, then it defaults to checking that
// the HTTP status code is 200, as described above, with one exception:
// if the case contains a check of “redirect”, then the code is required to
// be a 30x code.
//
// The “trimbody” value is the body with all runs of spaces and tabs
// reduced to single spaces, leading and trailing spaces removed on
// each line, and blank lines removed.
//
// The possible operators for <op> are:
//
//	== - the value must be equal to the text
//	!= - the value must not be equal to the text
//	~  - the value must match the text interprted as a regular expression
//	!~ - the value must not match the text interprted as a regular expression
//	contains  - the value must contain the text as a substring
//	!contains - the value must not contain the text as a substring
//
// For example:
//
//	GET /change/75944e2e3a63
//	hint no change redirect - hg to git mapping not registered?
//	code == 302
//	redirect contains bdb10cf
//	body contains bdb10cf
//	body !contains UA-
//
//	GET /pkg/net/http/httptrace/
//	body ~ Got1xxResponse.*// Go 1\.11
//	body ~ GotFirstResponseByte func\(\)\s*$
//
// Multiline Texts
//
// The <text> in a request or check line can take a multiline form,
// by omitting it from the original line and then specifying the text
// as one or more following lines, each indented by a single tab.
// The text is taken to be the sequence of indented lines, including
// the final newline, but with the leading tab removed from each.
//
// The “postquery” example above showed the multiline syntax.
// Another common use is for multiline “body” checks. For example:
//
//	GET /hello
//	body ==
//		<!DOCTYPE html>
//		hello, world
//
package webtest

import (
	"bytes"
	"errors"
	"fmt"
	"io"
	"io/fs"
	"io/ioutil"
	"net/http"
	"net/http/httptest"
	"net/url"
	"path/filepath"
	"regexp"
	"strings"
	"testing"
	"unicode/utf8"
)

// HandlerWithCheck returns an http.Handler that responds to each request
// by running the test script files mached by glob against the handler h.
// If the tests pass, the returned http.Handler responds with status code 200.
// If they fail, it prints the details and responds with status code 503
// (service unavailable).
func HandlerWithCheck(h http.Handler, path string, fsys fs.FS, glob string) http.Handler {
	return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
		if r.URL.Path == path {
			err := CheckHandler(fsys, glob, h)
			if err != nil {
				http.Error(w, "webtest.CheckHandler failed:\n"+err.Error()+"\n", http.StatusInternalServerError)
			} else {
				fmt.Fprintf(w, "ok\n")
			}
			return
		}
		h.ServeHTTP(w, r)
	})
}

// CheckHandler runs the test script files in fsys matched by glob
// against the handler h. If any errors are encountered,
// CheckHandler returns an error listing the problems.
func CheckHandler(fsys fs.FS, glob string, h http.Handler) error {
	return check(fsys, glob, func(c *case_) error { return c.runHandler(h) })
}

func check(fsys fs.FS, glob string, do func(*case_) error) error {
	files, err := fs.Glob(fsys, glob)
	if err != nil {
		return err
	}
	if len(files) == 0 {
		return fmt.Errorf("no files match %#q", glob)
	}
	var buf bytes.Buffer
	for _, file := range files {
		data, err := fs.ReadFile(fsys, file)
		if err != nil {
			fmt.Fprintf(&buf, "# %s\n%v\n", file, err)
			continue
		}
		script, err := parseScript(file, string(data))
		if err != nil {
			fmt.Fprintf(&buf, "# %s\n%v\n", file, err)
			continue
		}
		hdr := false
		for _, c := range script.cases {
			if err := do(c); err != nil {
				if !hdr {
					fmt.Fprintf(&buf, "# %s\n", file)
					hdr = true
				}
				fmt.Fprintf(&buf, "## %s %s\n", c.method, c.url)
				fmt.Fprintf(&buf, "%v\n", err)
			}
		}
	}
	if buf.Len() > 0 {
		return errors.New(buf.String())
	}
	return nil
}

// TestHandler runs the test script files matched by glob
// against the handler h.
func TestHandler(t *testing.T, glob string, h http.Handler) {
	test(t, glob, func(c *case_) error { return c.runHandler(h) })
}

func test(t *testing.T, glob string, do func(*case_) error) {
	files, err := filepath.Glob(glob)
	if err != nil {
		t.Fatal(err)
	}
	if len(files) == 0 {
		t.Fatalf("no files match %#q", glob)
	}
	for _, file := range files {
		t.Run(filepath.Base(file), func(t *testing.T) {
			data, err := ioutil.ReadFile(file)
			if err != nil {
				t.Fatal(err)
			}
			script, err := parseScript(file, string(data))
			if err != nil {
				t.Fatal(err)
			}
			for _, c := range script.cases {
				t.Run(c.method+"/"+strings.TrimPrefix(c.url, "/"), func(t *testing.T) {
					if err := do(c); err != nil {
						t.Fatal(err)
					}
				})
			}
		})
	}
}

// A script is a parsed test script.
type script struct {
	cases []*case_
}

// A case_ is a single test case (GET/HEAD/POST) in a script.
type case_ struct {
	file      string
	line      int
	method    string
	url       string
	postbody  string
	postquery string
	posttype  string
	hint      string
	checks    []*cmpCheck
}

// A cmp is a single comparison (check) made against a test case.
type cmpCheck struct {
	file    string
	line    int
	what    string
	whatArg string
	op      string
	want    string
	wantRE  *regexp.Regexp
}

// runHandler runs a test case against the handler h.
func (c *case_) runHandler(h http.Handler) error {
	w := httptest.NewRecorder()
	r, err := c.newRequest(c.url)
	if err != nil {
		return err
	}
	h.ServeHTTP(w, r)
	return c.check(w.Result(), w.Body.String())
}

// runServer runs a test case against the server at address addr.
func (c *case_) runServer(addr string) error {
	baseURL := ""
	if strings.HasPrefix(addr, "http://") || strings.HasPrefix(addr, "https://") {
		// addr is a base URL
		if !strings.HasSuffix(addr, "/") {
			addr += "/"
		}
		baseURL = addr
	} else {
		// addr is an HTTP proxy
		baseURL = "http://" + addr + "/"
	}

	// Build full URL for request.
	u := c.url
	if !strings.HasPrefix(u, "http://") && !strings.HasPrefix(u, "https://") {
		u = strings.TrimSuffix(baseURL, "/")
		if !strings.HasPrefix(c.url, "/") {
			u += "/"
		}
		u += c.url
	}
	req, err := c.newRequest(u)

	if err != nil {
		return fmt.Errorf("%s:%d: %s %s: %s", c.file, c.line, c.method, c.url, err)
	}
	tr := &http.Transport{}
	if !strings.HasPrefix(u, baseURL) {
		// If u does not begin with baseURL, then we're in the proxy case
		// and we try to tunnel the network activity through the proxy's address.
		proxyURL, err := url.Parse(baseURL)
		if err != nil {
			return fmt.Errorf("invalid addr: %v", err)
		}
		tr.Proxy = func(*http.Request) (*url.URL, error) { return proxyURL, nil }
	}
	resp, err := tr.RoundTrip(req)
	if err != nil {
		return fmt.Errorf("%s:%d: %s %s: %s", c.file, c.line, c.method, c.url, err)
	}
	body, err := ioutil.ReadAll(resp.Body)
	resp.Body.Close()
	if err != nil {
		return fmt.Errorf("%s:%d: %s %s: reading body: %s", c.file, c.line, c.method, c.url, err)
	}
	return c.check(resp, string(body))
}

// newRequest creates a new request for the case c,
// using the URL u.
func (c *case_) newRequest(u string) (*http.Request, error) {
	body := c.requestBody()
	r, err := http.NewRequest(c.method, u, body)
	if err != nil {
		return nil, err
	}
	typ := c.posttype
	if body != nil && typ == "" {
		typ = "application/x-www-form-urlencoded"
	}
	if typ != "" {
		r.Header.Set("Content-Type", typ)
	}
	return r, nil
}

// requestBody returns the body for the case's request.
func (c *case_) requestBody() io.Reader {
	if c.postbody == "" {
		return nil
	}
	return strings.NewReader(c.postbody)
}

// check checks the response against the comparisons for the case.
func (c *case_) check(resp *http.Response, body string) error {
	var msg bytes.Buffer
	for _, chk := range c.checks {
		what := chk.what
		if chk.whatArg != "" {
			what += " " + chk.whatArg
		}
		var value string
		switch chk.what {
		default:
			value = "unknown what: " + chk.what
		case "body":
			value = body
		case "trimbody":
			value = trim(body)
		case "code":
			value = fmt.Sprint(resp.StatusCode)
		case "header":
			value = resp.Header.Get(chk.whatArg)
		case "redirect":
			if resp.StatusCode/10 == 30 {
				value = resp.Header.Get("Location")
			}
		}

		switch chk.op {
		default:
			fmt.Fprintf(&msg, "%s:%d: unknown operator %s\n", chk.file, chk.line, chk.op)
		case "==":
			if value != chk.want {
				fmt.Fprintf(&msg, "%s:%d: %s = %q, want %q\n", chk.file, chk.line, what, value, chk.want)
			}
		case "!=":
			if value == chk.want {
				fmt.Fprintf(&msg, "%s:%d: %s == %q (but want !=)\n", chk.file, chk.line, what, value)
			}
		case "~":
			if !chk.wantRE.MatchString(value) {
				fmt.Fprintf(&msg, "%s:%d: %s does not match %#q (but should)\n\t%s\n", chk.file, chk.line, what, chk.want, indent(value))
			}
		case "!~":
			if chk.wantRE.MatchString(value) {
				fmt.Fprintf(&msg, "%s:%d: %s matches %#q (but should not)\n\t%s\n", chk.file, chk.line, what, chk.want, indent(value))
			}
		case "contains":
			if !strings.Contains(value, chk.want) {
				fmt.Fprintf(&msg, "%s:%d: %s does not contain %#q (but should)\n\t%s\n", chk.file, chk.line, what, chk.want, indent(value))
			}
		case "!contains":
			if strings.Contains(value, chk.want) {
				fmt.Fprintf(&msg, "%s:%d: %s contains %#q (but should not)\n\t%s\n", chk.file, chk.line, what, chk.want, indent(value))
			}
		}
	}
	if msg.Len() > 0 && c.hint != "" {
		fmt.Fprintf(&msg, "hint: %s\n", indent(c.hint))
	}

	if msg.Len() > 0 {
		return fmt.Errorf("%s:%d: %s %s\n%s", c.file, c.line, c.method, c.url, msg.String())
	}
	return nil
}

// trim returns a trimming of s, in which all runs of spaces and tabs have
// been collapsed to a single space, leading and trailing spaces have been
// removed from each line, and blank lines are removed entirely.
func trim(s string) string {
	s = regexp.MustCompile(`[ \t]+`).ReplaceAllString(s, " ")
	s = regexp.MustCompile(`(?m)(^ | $)`).ReplaceAllString(s, "")
	s = strings.TrimLeft(s, "\n")
	s = regexp.MustCompile(`\n\n+`).ReplaceAllString(s, "\n")
	return s
}

// indent indents text for formatting in a message.
func indent(text string) string {
	if text == "" {
		return "(empty)"
	}
	if text == "\n" {
		return "(blank line)"
	}
	text = strings.TrimRight(text, "\n")
	if text == "" {
		return "(blank lines)"
	}
	text = strings.ReplaceAll(text, "\n", "\n\t")
	return text
}

// parseScript parses the test script in text.
// Errors are reported as being from file, but file is not directly read.
func parseScript(file, text string) (*script, error) {
	var current struct {
		Case      *case_
		Multiline *string
	}
	script := new(script)
	lastLineWasBlank := true
	lineno := 0
	line := ""
	errorf := func(format string, args ...interface{}) error {
		if line != "" {
			line = "\n" + line
		}
		return fmt.Errorf("%s:%d: %v%s", file, lineno, fmt.Sprintf(format, args...), line)
	}
	for text != "" {
		lineno++
		prevLine := line
		line, text, _ = cut(text, "\n")
		if strings.HasPrefix(line, "#") {
			continue
		}
		line = strings.TrimRight(line, " \t")
		if line == "" {
			lastLineWasBlank = true
			continue
		}
		what, args := splitOneField(line)

		// Add indented line to current multiline check, or else it ends.
		if what == "" {
			// Line is indented.
			if current.Multiline != nil {
				lastLineWasBlank = false
				*current.Multiline += args + "\n"
				continue
			}
			return nil, errorf("unexpected indented line")
		}

		// Multiline text is over; must be present.
		if current.Multiline != nil && *current.Multiline == "" {
			lineno--
			line = prevLine
			return nil, errorf("missing multiline text")
		}
		current.Multiline = nil

		// Look for start of new check.
		switch what {
		case "GET", "HEAD", "POST":
			if !lastLineWasBlank {
				return nil, errorf("missing blank line before start of case")
			}
			if args == "" {
				return nil, errorf("missing %s URL", what)
			}
			cas := &case_{method: what, url: args, file: file, line: lineno}
			script.cases = append(script.cases, cas)
			current.Case = cas
			lastLineWasBlank = false
			continue
		}

		if lastLineWasBlank || current.Case == nil {
			return nil, errorf("missing GET/HEAD/POST at start of check")
		}

		// Look for case metadata.
		var targ *string
		switch what {
		case "postbody":
			targ = &current.Case.postbody
		case "postquery":
			targ = &current.Case.postquery
		case "posttype":
			targ = &current.Case.posttype
		case "hint":
			targ = &current.Case.hint
		}
		if targ != nil {
			if strings.HasPrefix(what, "post") && current.Case.method != "POST" {
				return nil, errorf("need POST (not %v) for %v", current.Case.method, what)
			}
			if args != "" {
				*targ = args
			} else {
				current.Multiline = targ
			}
			continue
		}

		// Start a comparison check.
		chk := &cmpCheck{file: file, line: lineno, what: what}
		current.Case.checks = append(current.Case.checks, chk)
		switch what {
		case "body", "code", "redirect":
			// no WhatArg
		case "header":
			chk.whatArg, args = splitOneField(args)
			if chk.whatArg == "" {
				return nil, errorf("missing header name")
			}
		}

		// Opcode, with optional leading "not"
		chk.op, args = splitOneField(args)
		switch chk.op {
		case "==", "!=", "~", "!~", "contains", "!contains":
			// ok
		default:
			return nil, errorf("unknown check operator %q", chk.op)
		}

		if args != "" {
			chk.want = args
		} else {
			current.Multiline = &chk.want
		}
	}

	// Finish each case.
	// Compute POST body from POST query.
	// Check that each regexp compiles, and insert "code equals 200"
	// in each case that doesn't already have a code check.
	for _, cas := range script.cases {
		if cas.postquery != "" {
			if cas.postbody != "" {
				line = ""
				lineno = cas.line
				return nil, errorf("case has postbody and postquery")
			}
			for _, kv := range strings.Split(cas.postquery, "\n") {
				kv = strings.TrimSpace(kv)
				if kv == "" {
					continue
				}
				k, v, ok := cut(kv, "=")
				if !ok {
					lineno = cas.line // close enough
					line = kv
					return nil, errorf("postquery has non key=value line")
				}
				if cas.postbody != "" {
					cas.postbody += "&"
				}
				cas.postbody += url.QueryEscape(k) + "=" + url.QueryEscape(v)
			}
		}
		sawCode := false
		for _, chk := range cas.checks {
			if chk.what == "code" || chk.what == "redirect" {
				sawCode = true
			}
			if chk.op == "~" || chk.op == "!~" {
				re, err := regexp.Compile(`(?m)` + chk.want)
				if err != nil {
					lineno = chk.line
					line = chk.want
					return nil, errorf("invalid regexp: %s", err)
				}
				chk.wantRE = re
			}
		}
		if !sawCode {
			line := cas.line
			if len(cas.checks) > 0 {
				line = cas.checks[0].line
			}
			chk := &cmpCheck{file: cas.file, line: line, what: "code", op: "==", want: "200"}
			cas.checks = append(cas.checks, chk)
		}
	}
	return script, nil
}

// cut returns the result of cutting s around the first instance of sep.
func cut(s, sep string) (before, after string, ok bool) {
	if i := strings.Index(s, sep); i >= 0 {
		return s[:i], s[i+len(sep):], true
	}
	return s, "", false
}

// cutAny returns the result of cutting s around the first instance of
// any code point from any.
func cutAny(s, any string) (before, after string, ok bool) {
	if i := strings.IndexAny(s, any); i >= 0 {
		_, size := utf8.DecodeRuneInString(s[i:])
		return s[:i], s[i+size:], true
	}
	return s, "", false
}

// splitOneField splits text at the first space or tab
// and returns that first field and the remaining text.
func splitOneField(text string) (field, rest string) {
	i := strings.IndexAny(text, " \t")
	if i < 0 {
		return text, ""
	}
	return text[:i], strings.TrimLeft(text[i:], " \t")
}
