httpclient

package
v0.0.3 Latest Latest
Warning

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

Go to latest
Published: Dec 3, 2019 License: MIT Imports: 14 Imported by: 0

Documentation

Overview

Package httpclient is a high level wrapper around net/http with more types and easier to use interface TODO: ref https://github.com/bradfitz/exp-httpclient

Index

Constants

View Source
const UnixBasePath = "http://localhost"

UnixBasePath is used as a placeholder for unix domain socket client, only the protocol http is needed, host is ignored because dialer use socket path TODO: what about tls over unix domain socket?

Variables

This section is empty.

Functions

func DrainAndClose

func DrainAndClose(res *http.Response)

DrainAndClose ignore all the errors when drain response body to /dev/null and close it It should be used when are using a raw http.Response and don't want to write server lines for draining and close the body

You should use FetchToNull most of the time, this only useful when you need some header and don't care about the body

func DrainResponseBody

func DrainResponseBody(res *http.Response) ([]byte, error)

DrainResponseBody reads entire response into a byte slice and close the underlying body so the connection can be reused.

It replace res.Body with a bytes.Reader so it can be passed to func that reads res.Body

func IsSuccess

func IsSuccess(status int) bool

func JoinPath

func JoinPath(base string, sub string) string

JoinPath does not sanitize path like path.Join, which would change https:// to https:/, it only remove duplicated slashes to avoid // in url i.e. http://myapi.com/api/v1//comments/1

Types

type BasicErrorHandler

type BasicErrorHandler struct {
}

BasicErrorHandler use value receiver because it does not have any fields

func (BasicErrorHandler) DecodeError

func (h BasicErrorHandler) DecodeError(status int, body []byte, res *http.Response) error

func (BasicErrorHandler) IsError

func (h BasicErrorHandler) IsError(status int, res *http.Response) bool

type Client

type Client struct {
	// contains filtered or unexported fields
}

func New

func New(base string, opts ...Option) (*Client, error)

TODO: allow using config struct

func NewDefault added in v0.0.3

func NewDefault(base string) (*Client, error)

NewDefault creates a dev client that use a shared un pooled http.Transport

func NewDefaultSkipVerify added in v0.0.3

func NewDefaultSkipVerify(base string) (*Client, error)

NewDefaultSkipVerify is same as NewDefault but disabled tls certificate verify. You should NOT use it production, it is useful for testing with self signed certs TODO: add links on how to generate and use self signed cert

func (*Client) Delete

func (c *Client) Delete(ctx *Context, path string, resBody interface{}) error

func (*Client) DeleteIgnoreRes

func (c *Client) DeleteIgnoreRes(ctx *Context, path string) error

func (*Client) DeleteRaw

func (c *Client) DeleteRaw(ctx *Context, path string) (*http.Response, error)

func (*Client) Do

func (c *Client) Do(ctx *Context, method httputil.Method, path string, reqBody interface{}) (*http.Response, error)

Do handles application level error, default is based on status code and drain entire body as string. User can give a handler when create client or have request specific handler using context

It does not drain response body, use FetchTo if want to decode body as json

func (*Client) FetchTo

func (c *Client) FetchTo(ctx *Context, method httputil.Method, path string, reqBody interface{}, resBody interface{}) error

func (*Client) FetchToNull

func (c *Client) FetchToNull(ctx *Context, method httputil.Method, path string, reqBody interface{}) error

func (*Client) Get

func (c *Client) Get(ctx *Context, path string, resBody interface{}) error

func (*Client) GetHeaders added in v0.0.3

func (c *Client) GetHeaders() map[string]string

GetHeaders a copy of headers set on the client, it will return a empty but non nil map even if no header is set

func (*Client) GetIgnoreRes

func (c *Client) GetIgnoreRes(ctx *Context, path string) error

func (*Client) GetRaw

func (c *Client) GetRaw(ctx *Context, path string) (*http.Response, error)

func (*Client) NewRequest

func (c *Client) NewRequest(ctx *Context, method httputil.Method, path string, reqBody interface{}) (*http.Request, error)

NewRequest create a http.Request by concat base path in client and path, it will encode the body if the body is not already encoded and it's a json client

You should use high level wrapper like FetchTo most of the time

func (*Client) Patch

func (c *Client) Patch(ctx *Context, path string, reqBody interface{}, resBody interface{}) error

func (*Client) PatchIgnoreRes

func (c *Client) PatchIgnoreRes(ctx *Context, path string, reqBody interface{}) error

func (*Client) PatchRaw

func (c *Client) PatchRaw(ctx *Context, path string, reqBody interface{}) (*http.Response, error)

func (*Client) Post

func (c *Client) Post(ctx *Context, path string, reqBody interface{}, resBody interface{}) error

func (*Client) PostIgnoreRes

func (c *Client) PostIgnoreRes(ctx *Context, path string, reqBody interface{}) error

func (*Client) PostRaw

func (c *Client) PostRaw(ctx *Context, path string, reqBody interface{}) (*http.Response, error)

func (*Client) SetHeader added in v0.0.3

func (c *Client) SetHeader(k, v string) *Client

func (*Client) Transport

func (c *Client) Transport() (tr *http.Transport, ok bool)

Transport returns the transport of the http.Client being used for user to modify tls config etc. It returns (nil, false) if the transport is the default transport or the type didn't match. You should NOT use http.DefaultTransport in the first place, and modify it is even worse

type Context

type Context struct {
	// contains filtered or unexported fields
}

Context

It is lazy initialized, only call `make` when they are actually write to, so all the maps are EMPTY even when using factory func. User (including this package itself) should use setter when set value.

func Bkg

func Bkg() *Context

Bkg returns a Context that does not embed context.Context, it behaves like context.Background(), however we can't use a singleton like context package because Context in httpclient can be modified in place to store req/response body etc. So we always return pointer to a fresh new instance.

We return pointer because it is meant to be modified along the way, it is not immutable like context.Context Also the context.Context is implemented using pointer receiver

func ConvertContext

func ConvertContext(ctx context.Context) *Context

ConvertContext returns the original context if it is already *httpclient.Context, Otherwise it wraps the context using NewContext

func NewContext

func NewContext(ctx context.Context) *Context

NewContext returns a context that embed a context.Context

func (*Context) Deadline

func (c *Context) Deadline() (deadline time.Time, ok bool)

Deadline returns Deadline() from underlying context.Context if set

func (*Context) Done

func (c *Context) Done() <-chan struct{}

Done returns Done() from underlying context.Context if set

func (*Context) Err

func (c *Context) Err() error

Err returns Err() from underlying context.Context if set

func (*Context) SetBase added in v0.0.3

func (c *Context) SetBase(s string) *Context

func (*Context) SetErrorHandler

func (c *Context) SetErrorHandler(h ErrorHandler) *Context

func (*Context) SetHeader

func (c *Context) SetHeader(k, v string) *Context

func (*Context) SetParam

func (c *Context) SetParam(k, v string) *Context

func (*Context) Value

func (c *Context) Value(key interface{}) interface{}

Value first checks the map[string]interface{}, if not found, it use the underlying context.Context if is set if not set, it returns nil

type ErrApplication

type ErrApplication struct {
	Status int
	Method httputil.Method
	// Url is the full url including schema, host and query parameters
	Url string
	// Path is just the api path without host etc.
	Path string
	// Body is string instead of []byte because it's immutable
	Body string
}

func (*ErrApplication) Error

func (e *ErrApplication) Error() string

type ErrDecoding

type ErrDecoding struct {
	Codec string
	Err   error
	Body  string
}

func (*ErrDecoding) Error

func (e *ErrDecoding) Error() string

type ErrorHandler

type ErrorHandler interface {
	IsError(status int, res *http.Response) bool
	DecodeError(status int, body []byte, res *http.Response) (decodedError error)
}

func DefaultHandler

func DefaultHandler() ErrorHandler

type ErrorHandlerFunc

type ErrorHandlerFunc func(status int, body []byte, res *http.Response) (decodedError error)

ErrorHandlerFunc use status code for IsError

func (ErrorHandlerFunc) DecodeError

func (f ErrorHandlerFunc) DecodeError(status int, body []byte, res *http.Response) error

func (ErrorHandlerFunc) IsError

func (f ErrorHandlerFunc) IsError(status int, res *http.Response) bool

type Option

type Option func(c *Client) error

func UseJSON

func UseJSON() Option

func WithErrorHandler

func WithErrorHandler(h ErrorHandler) Option

func WithErrorHandlerFunc

func WithErrorHandlerFunc(f ErrorHandlerFunc) Option

func WithTransport

func WithTransport(tr *http.Transport) Option

Jump to

Keyboard shortcuts

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