htest

package module
v0.0.0-...-e34d504 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 21, 2017 License: MIT Imports: 15 Imported by: 0

README

HTest Build Status GoDoc License

A lightweight high-level abstractions for testing HTTP inspired by supertest built around http.ResponseRecorder

Screenshot

Install/Update

$ go get -u github.com/celrenheit/htest

Usage

Let's say that when we hit /admin we get a status code of 401 Unauthorized, a response body of You are not authorized and a header of foo=bar

mux := http.NewServeMux()
mux.HandleFunc("/admin", func(w http.ResponseWriter, r *http.Request) {
	w.Header().Set("foo", "bar")
	w.WriteHeader(http.StatusUnauthorized)
	fmt.Fprintf(w, "You are not authorized")
})

We can write a Test to test if our program behaves correctly

func TestUnauthorized(t *testing.T) {
  // We create a new instance for HTTPTester
  // It requires a testing.T and an http.Handler as argument
	h := htest.New(t, mux)

  // We make assertions to the repsonse received
	h.Get("/admin").Do().
		ExpectHeader("foo", "bar").
		ExpectStatus(http.StatusUnauthorized).
		ExpectBody("You are not authorized")
}

h.Get returns a Requester to be able to easily build your request. We call the Do() to execute the request and get a ResponseAsserter.

There are methods for each http methods in the HTTPTester interface

Building the request

We send some arbitrary data and set a header to the request. The response should have the same body and the same header value.

func TestBuildingRequest(t *testing.T) {
	mux := http.NewServeMux()
	mux.HandleFunc("/path", func(w http.ResponseWriter, r *http.Request) {
		w.Header().Set("foo", r.Header.Get("foo"))
		io.Copy(w, r.Body)
	})

	test := htest.New(t, mux)

	test.Get("/path").
		// Set a header to the request
		AddHeader("foo", "barbar").
		// Send a string to the request's body
		SendString("my data").

		// Executes the request
		Do().

		// The body sent should stay the same
		ExpectBody("my data").
		// The header sent should stay the same
		ExpectHeader("foo", "barbar")
}

Credits

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type HTTPTester

type HTTPTester interface {
	Get(path string) Requester
	Head(path string) Requester
	Post(path string) Requester
	Put(path string) Requester
	Delete(path string) Requester
	Trace(path string) Requester
	Options(path string) Requester
	Connect(path string) Requester
	Patch(path string) Requester

	// Request allows to create a Requester object with the passed HTTP method and path
	Request(method, path string) Requester

	// Request allows to create a Requester object with the passed HTTP method, path and body.
	RequestWithBody(method, path string, body io.Reader) Requester

	// SetHandler changes the underlying http.Handler
	SetHandler(handler http.Handler) HTTPTester
}

HTTPTester is an interface that represents the main entry point of HTest

func New

func New(t testing.TB, handler http.Handler) HTTPTester

New returns a new HTTPTester instance

type Requester

type Requester interface {
	// AddHeader adds a Header to the list of headers
	AddHeader(key, value string) Requester

	// SetHeader sets the Header for the key specified
	SetHeader(key, value string) Requester

	// AddCookie adds a cookie with a key and its value to the http request
	AddCookie(key, value string) Requester

	// AddForm adds request's form key and value to the request
	AddForm(key, value string) Requester

	// SetForm sets request's form key and value to the request
	SetForm(key, value string) Requester

	// FormValues allows to set a form's custom values
	FormValues(u url.Values) Requester

	// Send sends whatever data it gets as its parameter
	// The current types are supported:
	// 		- Structs, maps, slices and arrays will be marshalled to JSON
	// 		- Strings will be converted to []byte and sent to the request body
	Send(data interface{}) Requester

	// SendBytes sets a slice de bytes as the request's body
	SendBytes(data []byte) Requester

	// SendString sets a string as the request's body
	SendString(data string) Requester

	// Do executes the request and returns a ResponseAsserter allowing to perform tests on the results of this request
	Do() ResponseAsserter
}

Requester is responsible for building an http request. When done you should call Do() method to be able to make assertions using ResponseAsserter

type ResponseAsserter

type ResponseAsserter interface {
	// ExpectHeader triggers an error if the actual value for the key is different from the expected value
	ExpectHeader(key, expected string) ResponseAsserter

	// ExpectCookie triggers an error if the actual value for the key is different from the expected value
	ExpectCookie(key, expected string) ResponseAsserter

	// ExpectCookie triggers an error if the actual value for the key is different from the expected value
	ExpectStatus(expected int) ResponseAsserter

	// ExpectBody triggers an error if actual body received is different from the expected one
	ExpectBody(expected string) ResponseAsserter

	// ExpectBody triggers an error if actual body does not contain the passed string
	ExpectBodyContains(str string) ResponseAsserter

	// ExpectBodyBytes triggers an error if actual body received is different from the expected one
	ExpectBodyBytes(b []byte) ResponseAsserter

	// ExpectJSON triggers an error if actual body received is different from the expected one.
	// Before comparing it marshals the data passed a argument using json.Marshal
	ExpectJSON(data interface{}) ResponseAsserter

	// Recorder returns the underlying ResponseRecorder instance
	Recorder() *httptest.ResponseRecorder
}

ResponseAsserter is responsible for making assertions based on the expected and the actual value returned from httptest.ResponseRecorder

func NewResponseAsserter

func NewResponseAsserter(t testing.TB, w *httptest.ResponseRecorder, r *http.Request) ResponseAsserter

NewResponseAsserter create a new response asserter

type StackFrame

type StackFrame struct {
	PC       uintptr
	File     string
	FuncName string
	Package  string
	Line     int
}

StackFrame describes a single stackframe with its Program Counter, Function name, Package, File and Line number

func NewStackFrame

func NewStackFrame(pc uintptr) *StackFrame

NewStackFrame creates a new StackFrame instance It extracts the File, Line, Package and Function name for the passed Program Counter

func (*StackFrame) IsTest

func (s *StackFrame) IsTest() bool

IsTest determines if the found function is a Test

func (*StackFrame) String

func (s *StackFrame) String() string

String return a strings with the following format:

example.com/mypackage.TestMyFunction:99

type StackFrames

type StackFrames []*StackFrame

StackFrames is a list of StackFrame

func Trace

func Trace() (frames StackFrames)

Trace parses the stacktrace and returns a slice of StackFrame

func (StackFrames) OnlyTests

func (frames StackFrames) OnlyTests() (out StackFrames)

OnlyTests filters only the stackframes that are Tests

func (StackFrames) String

func (frames StackFrames) String() string

String returns a pretty string for each StackFrame

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL