Skip to content

⚡️ Gofast is a HTTP client based on fasthttp with zero memory allocation.

License

Notifications You must be signed in to change notification settings

cloudingcity/gofast

Repository files navigation

Gofast

Test Lint codecov Go Report Card

⚡️ Gofast is a HTTP client based on fasthttp with zero memory allocation.

Automatic struct binding let you focus on entity writing.

JSON-to-Go is very useful to generate struct.

Install

go get -u github.com/cloudingcity/gofast

Quick Start

package main

import (
	"fmt"
	"log"

	"github.com/cloudingcity/gofast"
)

type Out struct {
	Hello string `json:"hello"`
}

func main() {
	fast := gofast.New()

	var out Out
	uri := "http://echo.jsontest.com/hello/world"
	if err := fast.Get(uri, &out, nil); err != nil {
		log.Fatalln(err)
	}
	fmt.Printf("hello %v", out.Hello)
	// hello world
}

Examples

Send request with body

The default encoding is JSON with application/json header.

You can also use map to bind value, but the worse performance you will get.

type CreateToken struct {
    ID     string `json:"id"`
    Secret string `json:"secret"`
}

type Token struct {
    Token     string `json:"token"`
    ExpiredAt string `json:"expired_at"`
}

fast := gofast.New()

uri := "https://example.com/api/v1/token"
body := CreateToken{
    ID:     "my-id",
    Secret: "my-secret",
}
var token Token
if err := fast.Post(uri, &body, &token, nil); err != nil {
    log.Fatalln(err)
}
fmt.Printf("token: %v, expired_at: %v", token.Token, token.ExpiredAt)

Get with header

type User struct {
    ID   int    `json:"id"`
    Name string `json:"name"`
}

fast := gofast.New()

var user User
uri := "https://example.com/api/v1/users/100"
h := gofast.Header{fasthttp.HeaderAuthorization: "Bearer My-JWT"}
if err := fast.Get(uri, &user, h); err != nil {
    log.Fatalln(err)
}
fmt.Printf("id: %v, name: %v", user.ID, user.Name)

URL encode

Post body with application/x-www-form-urlencoded header and get text.

fast := gofast.New(gofast.Config{
    RequestEncoder:  gofast.URLEncoder,
    ResponseDecoder: gofast.TextDecoder,
})

uri := "https://example.com/api/v1/token"
body := gofast.Body{
    "id":     "my-id",
    "secret": "my-secret",
}
var token string
if err := fast.Post(uri, body, &token, nil); err != nil {
    log.Fatalln(err)
}

Customize error handler

Error handler will handle non 2xx HTTP status code.

cfg := gofast.Config{
    ErrorHandler: func(resp *fasthttp.Response) error {
        return fmt.Errorf("http code = %d", resp.StatusCode())
    },
}

fast := gofast.New(cfg)
err := fast.Get(uri, nil, nil)
// http code = 400

Benchmarks

$ go test -bench=. -benchmem -benchtime=3s -run=none -cpu 4
BenchmarkPostJSON-4               1263522              2891 ns/op               0 B/op          0 allocs/op
BenchmarkPostURLEncode-4          1219441              2777 ns/op               0 B/op          0 allocs/op