Giter Club home page Giter Club logo

fiber's Introduction

Fiber
Codecov

Fiber is an Express inspired web framework built on top of Fasthttp, the fastest HTTP engine for Go. Designed to ease things up for fast development with zero memory allocation and performance in mind.


⚠️ Attention

Fiber v3 is currently in beta and under active development. While it offers exciting new features, please note that it may not be stable for production use. We recommend sticking to the latest stable release (v2.x) for mission-critical applications. If you choose to use v3, be prepared for potential bugs and breaking changes. Always check the official documentation and release notes for updates and proceed with caution. Happy coding! 🚀


⚙️ Installation

Fiber requires Go version 1.21 or higher to run. If you need to install or upgrade Go, visit the official Go download page. To start setting up your project. Create a new directory for your project and navigate into it. Then, initialize your project with Go modules by executing the following command in your terminal:

go mod init github.com/your/repo

To learn more about Go modules and how they work, you can check out the Using Go Modules blog post.

After setting up your project, you can install Fiber with the go get command:

go get -u github.com/gofiber/fiber/v3

This command fetches the Fiber package and adds it to your project's dependencies, allowing you to start building your web applications with Fiber.

⚡️ Quickstart

Getting started with Fiber is easy. Here's a basic example to create a simple web server that responds with "Hello, World 👋!" on the root path. This example demonstrates initializing a new Fiber app, setting up a route, and starting the server.

package main

import (
    "log"

    "github.com/gofiber/fiber/v3"
)

func main() {
    // Initialize a new Fiber app
    app := fiber.New()

    // Define a route for the GET method on the root path '/'
    app.Get("/", func(c fiber.Ctx) error {
        // Send a string response to the client
        return c.SendString("Hello, World 👋!")
    })

    // Start the server on port 3000
    log.Fatal(app.Listen(":3000"))
}

This simple server is easy to set up and run. It introduces the core concepts of Fiber: app initialization, route definition, and starting the server. Just run this Go program, and visit http://localhost:3000 in your browser to see the message.

🤖 Benchmarks

These tests are performed by TechEmpower and Go Web. If you want to see all the results, please visit our Wiki.

🎯 Features

💡 Philosophy

New gophers that make the switch from Node.js to Go are dealing with a learning curve before they can start building their web applications or microservices. Fiber, as a web framework, was created with the idea of minimalism and follows the UNIX way, so that new gophers can quickly enter the world of Go with a warm and trusted welcome.

Fiber is inspired by Express, the most popular web framework on the Internet. We combined the ease of Express and raw performance of Go. If you have ever implemented a web application in Node.js (using Express or similar), then many methods and principles will seem very common to you.

We listen to our users in issues, Discord channel and all over the Internet to create a fast, flexible and friendly Go web framework for any task, deadline and developer skill! Just like Express does in the JavaScript world.

⚠️ Limitations

  • Due to Fiber's usage of unsafe, the library may not always be compatible with the latest Go version. Fiber 3.0.0 has been tested with Go versions 1.21 and 1.22.
  • Fiber is not compatible with net/http interfaces. This means you will not be able to use projects like gqlgen, go-swagger, or any others which are part of the net/http ecosystem.

👀 Examples

Listed below are some of the common examples. If you want to see more code examples, please visit our Recipes repository or visit our hosted API documentation.

func main() {
    app := fiber.New()

    // GET /api/register
    app.Get("/api/*", func(c fiber.Ctx) error {
        msg := fmt.Sprintf("✋ %s", c.Params("*"))
        return c.SendString(msg) // => ✋ register
    })

    // GET /flights/LAX-SFO
    app.Get("/flights/:from-:to", func(c fiber.Ctx) error {
        msg := fmt.Sprintf("💸 From: %s, To: %s", c.Params("from"), c.Params("to"))
        return c.SendString(msg) // => 💸 From: LAX, To: SFO
    })

    // GET /dictionary.txt
    app.Get("/:file.:ext", func(c fiber.Ctx) error {
        msg := fmt.Sprintf("📃 %s.%s", c.Params("file"), c.Params("ext"))
        return c.SendString(msg) // => 📃 dictionary.txt
    })

    // GET /john/75
    app.Get("/:name/:age/:gender?", func(c fiber.Ctx) error {
        msg := fmt.Sprintf("👴 %s is %s years old", c.Params("name"), c.Params("age"))
        return c.SendString(msg) // => 👴 john is 75 years old
    })

    // GET /john
    app.Get("/:name", func(c fiber.Ctx) error {
        msg := fmt.Sprintf("Hello, %s 👋!", c.Params("name"))
        return c.SendString(msg) // => Hello john 👋!
    })

    log.Fatal(app.Listen(":3000"))
}
func main() {
    app := fiber.New()

    // GET /api/register
    app.Get("/api/*", func(c fiber.Ctx) error {
        msg := fmt.Sprintf("✋ %s", c.Params("*"))
        return c.SendString(msg) // => ✋ register
    }).Name("api")

    data, _ := json.MarshalIndent(app.GetRoute("api"), "", "  ")
    fmt.Print(string(data))
    // Prints:
    // {
    //    "method": "GET",
    //    "name": "api",
    //    "path": "/api/*",
    //    "params": [
    //      "*1"
    //    ]
    // }

    log.Fatal(app.Listen(":3000"))
}
func main() {
    app := fiber.New()

    app.Static("/", "./public")
    // => http://localhost:3000/js/script.js
    // => http://localhost:3000/css/style.css

    app.Static("/prefix", "./public")
    // => http://localhost:3000/prefix/js/script.js
    // => http://localhost:3000/prefix/css/style.css

    app.Static("*", "./public/index.html")
    // => http://localhost:3000/any/path/shows/index/html

    log.Fatal(app.Listen(":3000"))
}
func main() {
    app := fiber.New()

    // Match any route
    app.Use(func(c fiber.Ctx) error {
        fmt.Println("🥇 First handler")
        return c.Next()
    })

    // Match all routes starting with /api
    app.Use("/api", func(c fiber.Ctx) error {
        fmt.Println("🥈 Second handler")
        return c.Next()
    })

    // GET /api/list
    app.Get("/api/list", func(c fiber.Ctx) error {
        fmt.Println("🥉 Last handler")
        return c.SendString("Hello, World 👋!")
    })

    log.Fatal(app.Listen(":3000"))
}
📚 Show more code examples

Views engines

📖 Config 📖 Engines 📖 Render

Fiber defaults to the html/template when no view engine is set.

If you want to execute partials or use a different engine like amber, handlebars, mustache or pug etc..

Checkout our Template package that support multiple view engines.

package main

import (
    "log"

    "github.com/gofiber/fiber/v3"
    "github.com/gofiber/template/pug"
)

func main() {
    // You can setup Views engine before initiation app:
    app := fiber.New(fiber.Config{
        Views: pug.New("./views", ".pug"),
    })

    // And now, you can call template `./views/home.pug` like this:
    app.Get("/", func(c fiber.Ctx) error {
        return c.Render("home", fiber.Map{
            "title": "Homepage",
            "year":  1999,
        })
    })

    log.Fatal(app.Listen(":3000"))
}

Grouping routes into chains

📖 Group

func middleware(c fiber.Ctx) error {
    fmt.Println("Don't mind me!")
    return c.Next()
}

func handler(c fiber.Ctx) error {
    return c.SendString(c.Path())
}

func main() {
    app := fiber.New()

    // Root API route
    api := app.Group("/api", middleware) // /api

    // API v1 routes
    v1 := api.Group("/v1", middleware) // /api/v1
    v1.Get("/list", handler)           // /api/v1/list
    v1.Get("/user", handler)           // /api/v1/user

    // API v2 routes
    v2 := api.Group("/v2", middleware) // /api/v2
    v2.Get("/list", handler)           // /api/v2/list
    v2.Get("/user", handler)           // /api/v2/user

    // ...
}

Middleware logger

📖 Logger

package main

import (
    "log"

    "github.com/gofiber/fiber/v3"
    "github.com/gofiber/fiber/v3/middleware/logger"
)

func main() {
    app := fiber.New()

    app.Use(logger.New())

    // ...

    log.Fatal(app.Listen(":3000"))
}

Cross-Origin Resource Sharing (CORS)

📖 CORS

import (
    "log"

    "github.com/gofiber/fiber/v3"
    "github.com/gofiber/fiber/v3/middleware/cors"
)

func main() {
    app := fiber.New()

    app.Use(cors.New())

    // ...

    log.Fatal(app.Listen(":3000"))
}

Check CORS by passing any domain in Origin header:

curl -H "Origin: http://example.com" --verbose http://localhost:3000

Custom 404 response

📖 HTTP Methods

func main() {
    app := fiber.New()

    app.Static("/", "./public")

    app.Get("/demo", func(c fiber.Ctx) error {
        return c.SendString("This is a demo!")
    })

    app.Post("/register", func(c fiber.Ctx) error {
        return c.SendString("Welcome!")
    })

    // Last middleware to match anything
    app.Use(func(c fiber.Ctx) error {
        return c.SendStatus(404)
        // => 404 "Not Found"
    })

    log.Fatal(app.Listen(":3000"))
}

JSON Response

📖 JSON

type User struct {
    Name string `json:"name"`
    Age  int    `json:"age"`
}

func main() {
    app := fiber.New()

    app.Get("/user", func(c fiber.Ctx) error {
        return c.JSON(&User{"John", 20})
        // => {"name":"John", "age":20}
    })

    app.Get("/json", func(c fiber.Ctx) error {
        return c.JSON(fiber.Map{
            "success": true,
            "message": "Hi John!",
        })
        // => {"success":true, "message":"Hi John!"}
    })

    log.Fatal(app.Listen(":3000"))
}

WebSocket Upgrade

📖 Websocket

import (
    "log"

    "github.com/gofiber/fiber/v3"
    "github.com/gofiber/fiber/v3/middleware/websocket"
)

func main() {
  app := fiber.New()

  app.Get("/ws", websocket.New(func(c *websocket.Conn) {
    for {
      mt, msg, err := c.ReadMessage()
      if err != nil {
        log.Println("read:", err)
        break
      }
      log.Printf("recv: %s", msg)
      err = c.WriteMessage(mt, msg)
      if err != nil {
        log.Println("write:", err)
        break
      }
    }
  }))

  log.Fatal(app.Listen(":3000"))
  // ws://localhost:3000/ws
}

Server-Sent Events

📖 More Info

import (
    "log"

    "github.com/gofiber/fiber/v3"
    "github.com/valyala/fasthttp"
)

func main() {
  app := fiber.New()

  app.Get("/sse", func(c fiber.Ctx) error {
    c.Set("Content-Type", "text/event-stream")
    c.Set("Cache-Control", "no-cache")
    c.Set("Connection", "keep-alive")
    c.Set("Transfer-Encoding", "chunked")

    c.Context().SetBodyStreamWriter(fasthttp.StreamWriter(func(w *bufio.Writer) {
      fmt.Println("WRITER")
      var i int

      for {
        i++
        msg := fmt.Sprintf("%d - the time is %v", i, time.Now())
        fmt.Fprintf(w, "data: Message: %s\n\n", msg)
        fmt.Println(msg)

        w.Flush()
        time.Sleep(5 * time.Second)
      }
    }))

    return nil
  })

  log.Fatal(app.Listen(":3000"))
}

Recover Middleware

📖 Recover

import (
    "log"

    "github.com/gofiber/fiber/v3"
    "github.com/gofiber/fiber/v3/middleware/recover"
)

func main() {
    app := fiber.New()

    app.Use(recover.New())

    app.Get("/", func(c fiber.Ctx) error {
        panic("normally this would crash your app")
    })

    log.Fatal(app.Listen(":3000"))
}

Using Trusted Proxy

📖 Config

import (
    "log"

    "github.com/gofiber/fiber/v3"
)

func main() {
    app := fiber.New(fiber.Config{
        EnableTrustedProxyCheck: true,
        TrustedProxies: []string{"0.0.0.0", "1.1.1.1/30"}, // IP address or IP address range
        ProxyHeader: fiber.HeaderXForwardedFor,
    })

    log.Fatal(app.Listen(":3000"))
}

🧬 Internal Middleware

Here is a list of middleware that are included within the Fiber framework.

Middleware Description
adaptor Converter for net/http handlers to/from Fiber request handlers.
basicauth Provides HTTP basic authentication. It calls the next handler for valid credentials and 401 Unauthorized for missing or invalid credentials.
cache Intercept and cache HTTP responses.
compress Compression middleware for Fiber, with support for deflate, gzip and brotli.
cors Enable cross-origin resource sharing (CORS) with various options.
csrf Protect from CSRF exploits.
earlydata Adds support for TLS 1.3's early data ("0-RTT") feature.
encryptcookie Encrypt middleware which encrypts cookie values.
envvar Expose environment variables with providing an optional config.
etag Allows for caches to be more efficient and save bandwidth, as a web server does not need to resend a full response if the content has not changed.
expvar Serves via its HTTP server runtime exposed variants in the JSON format.
favicon Ignore favicon from logs or serve from memory if a file path is provided.
filesystem FileSystem middleware for Fiber.
healthcheck Liveness and Readiness probes for Fiber.
helmet Helps secure your apps by setting various HTTP headers.
idempotency Allows for fault-tolerant APIs where duplicate requests do not erroneously cause the same action performed multiple times on the server-side.
keyauth Adds support for key based authentication.
limiter Adds Rate-limiting support to Fiber. Use to limit repeated requests to public APIs and/or endpoints such as password reset.
logger HTTP request/response logger.
pprof Serves runtime profiling data in pprof format.
proxy Allows you to proxy requests to multiple servers.
recover Recovers from panics anywhere in the stack chain and handles the control to the centralized ErrorHandler.
redirect Redirect middleware.
requestid Adds a request ID to every request.
rewrite Rewrites the URL path based on provided rules. It can be helpful for backward compatibility or just creating cleaner and more descriptive links.
session Session middleware. NOTE: This middleware uses our Storage package.
skip Skip middleware that skips a wrapped handler if a predicate is true.
timeout Adds a max time for a request and forwards to ErrorHandler if it is exceeded.

🧬 External Middleware

List of externally hosted middleware modules and maintained by the Fiber team.

Middleware Description
contrib Third party middlewares
storage Premade storage drivers that implement the Storage interface, designed to be used with various Fiber middlewares.
template This package contains 9 template engines that can be used with Fiber v3 Go version 1.21 or higher is required.

🕶️ Awesome List

For more articles, middlewares, examples or tools check our awesome list.

👍 Contribute

If you want to say Thank You and/or support the active development of Fiber:

  1. Add a GitHub Star to the project.
  2. Tweet about the project on your 𝕏 (Twitter).
  3. Write a review or tutorial on Medium, Dev.to or personal blog.
  4. Support the project by donating a cup of coffee.

🖥️ Development

To ensure your contributions are ready for a Pull Request, please use the following Makefile commands. These tools help maintain code quality, consistency.

  • make help: Display available commands.
  • make audit: Conduct quality checks.
  • make benchmark: Benchmark code performance.
  • make coverage: Generate test coverage report.
  • make format: Automatically format code.
  • make lint: Run lint checks.
  • make test: Execute all tests.
  • make tidy: Tidy dependencies.

Run these commands to ensure your code adheres to project standards and best practices.

☕ Supporters

Fiber is an open source project that runs on donations to pay the bills e.g. our domain name, gitbook, netlify and serverless hosting. If you want to support Fiber, you can ☕ buy a coffee here.

User Donation
@destari ☕ x 10
@dembygenesis ☕ x 5
@thomasvvugt ☕ x 5
@hendratommy ☕ x 5
@ekaputra07 ☕ x 5
@jorgefuertes ☕ x 5
@candidosales ☕ x 5
@l0nax ☕ x 3
@bihe ☕ x 3
@justdave ☕ x 3
@koddr ☕ x 1
@lapolinar ☕ x 1
@diegowifi ☕ x 1
@ssimk0 ☕ x 1
@raymayemir ☕ x 1
@melkorm ☕ x 1
@marvinjwendt ☕ x 1
@toishy ☕ x 1

💻 Code Contributors

Code Contributors

⭐️ Stargazers

Stargazers over time

🧾 License

Copyright (c) 2019-present Fenny and Contributors. Fiber is free and open-source software licensed under the MIT License. Official logo was created by Vic Shóstak and distributed under Creative Commons license (CC BY-SA 4.0 International).

fiber's People

Contributors

ajf-sa avatar anatolelucet avatar bestgopher avatar codemicro avatar dependabot[bot] avatar dozheiny avatar efectn avatar fenny avatar fufuok avatar gaby avatar hi019 avatar jfcg avatar kamandlou avatar kiyonlin avatar klipitkas avatar koddr avatar larrylv avatar leonklingele avatar li-jin-gou avatar marvinjwendt avatar nickajacks1 avatar r-52 avatar renanbastos93 avatar renewerner87 avatar sixcolors avatar sujit-baniya avatar trim21 avatar vecpeng avatar wangjq4214 avatar xenowits avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

fiber's Issues

How do i use other flag parse tools ,like kingpin🤔

Question description
fiber.New() calls flag.Parse 。but when i use kingpin,they are in conflict.
i think the fiber.New() may should not call flag.Parse() . What do you think?
Could there be another solution?Sorry, I'm new to golang.
Code snippet (optional)

package main

import (
	"github.com/gofiber/fiber"
	"gopkg.in/alecthomas/kingpin.v2"
	"os"
)

func main()  {
	var testFlag string
	application := kingpin.New("demo", "demo")
	application.Flag("test","kinping flag").Default("test").StringVar(&testFlag)
	application.Parse(os.Args[1:])
	server := fiber.New()
	server.Listen(8080)
}

🔥 Add Websocket Support

Is your feature request related to a problem? No

Describe the solution you'd like: I'd like to see the ability to promote a request to a websocket connection and handle pub-sub messaging therein. This is a big feature present in other libraries like gorilla and it would make fiber more competitive.

Describe alternatives you've considered: Use a different web library.

Additional context: None.

🥳 v1.8.0 release notes!

Fiber v1.8.0 #189

go get -u github.com/gofiber/fiber

[NEW] app.Settings.Immutable / https://fiber.wiki/application#settings

[RENAME] Settings.TemplateFolder-> Settings.TemplateFolder https://fiber.wiki/context#render
[RENAME] Settings.TemplateEngine-> Settings.TemplateEngine https://fiber.wiki/context#render
[RENAME] Settings.TemplateExtension-> Settings.TemplateExtension https://fiber.wiki/context#render

[UPDATE] app.METHOD(path string, handlers ...func(*Ctx)) https://fiber.wiki/application#http-methods
[UPDATE] *Cookie https://fiber.wiki/context#cookie
[UPDATE] ctx.Cookie(*Cookie) https://fiber.wiki/context#cookie
[UPDATE] Removed path params for WebSocket https://fiber.wiki/application#websocket
[UPDATE] Update websocket to v1.4.2

[FIX] Immutable values #185
[FIX] Stronger typed API #178
[FIX] Argument conflict #159
[FIX] Convert Recover error
[FIX] Bundle template dependencies
[FIX] Many internal optimizations

🐞 bodyparser error when using with javascript fetch

Fiber version/commit
Fiber v1.8.0
Issue description
I get this error when trying to use body-parser with content-type: "application/json"
Error on /login: schema: invalid path "{"username":"test","password":"test"}"
Expected behavior

Steps to reproduce
JS fetch with gofiber api

Code snippet
Javascript:

async function handleLogin(){
        const res = await fetch('/auth/login',{
            method: 'POST',
            headers: {
                'Accept': 'application/json',
                'Content-Type': 'application/json'
            },
            body: JSON.stringify({ "username": username, "password": password})
        });

GO/Fiber:

package main

import "github.com/gofiber/fiber"


func main() {
  app := fiber.New()

  type User struct{
    Username string `json:"username", form:"username"` 
    Password string `json:"username", form:"username"`
}
auth:= app.Group("/auth")
auth.Post("/login", func(c *fiber.Ctx){
	var user User
	if err := c.BodyParser(&user); err != nil {
		fmt.Println("Error on /login: ", err)
        c.JSON(fiber.Map{
			"result" : "error",
			"message" : "Error trying to login",
		})
		return
	}
}

🤔 Is there any way for handling JSON error?

Question description
I have used gofiber for creating a REST API with JSON. The JSON function returns error so I must handle it every time in responses. Is there any better way of doing this?

Code snippet (optional)

package main

import "github.com/gofiber/fiber"

func main() {
  app := fiber.New()
  app.Get("/json", func (c *fiber.Ctx) {
    if err := c.Status(200).JSON("Hello World"); err != nil {
      panic(err)
    }
  })
}

🔥 Router chi

I know that you have designed the router but, if you know about chi, it has been designed to be simple, robust, without external dependencies and it's being used at sites like CloudFlare or Heroku.

https://github.com/go-chi/chi

🔥 Add support or documentation for unit tests

I loved the framework. Simple and straightforward. Excellent for making microservices. However, I didn't find any support to create unit tests :(

The use of the gin framework is precisely because it allows the use of httptest as a standard, which is already well documented.

Maybe it would be nice to make a mock of the context to test the behaviors, and be able to access all the registered routes if you want to test the association between middleware, methods and routes.

🤔 How to modify fiber.Ctx?

Question description

In Express, it's possible to dangle any sort of custom methods or properties from the request/response objects via middleware. I can't see anything in the documentation of how to do this in Fiber.

For instance, I want to write middleware that deals with some authentication that gives me an API in my route handlers that allows me to check for permissions or call an upstream service, how would this be done?

🔥 Fast logger middleware

Is your feature request related to a problem? Please describe.

I'm not sure if there were any plans to write your own logger (as middleware?), but it would be very cool to add a logger from Uber — zap. It's blazing fast, structured, leveled logging system.

Describe the solution you'd like

For one of my side project (Create Go App, to be exact), I created web app template for Fiber with example usage of zap logger:

Describe alternatives you've considered

As alternative solution, I know only Logrus, but he's very slow and doesn't have flexible structure for configuring (really, when I read zap's docs and source code, I found every things, which I wanted to re-configure).

Therefore, I don't recommend to use Logrus for Fiber, but good to know! 😉

Additional context

I'm ready to discus about this various feature for every web frameworks and may (want) help to write logger middleware, if needed. Please, let me know what you think!

🐞 Color output problem on Windows

Fiber version
1.5.0

Hi, this problem occurs if you use Windows CMD to run fiber:
image

Full Windows color support could possibly be accomplished by using the "Windows Way" of the fathi/color package:
image

This problem also occurs if you use inbuilt terminals (in e.g. IntelliJ IDEA):
image

c.Body() can't read raw data

I don't get data from c.Body ("email") when I request via postman with Raw Body

Raw Data

{
  "email": "[email protected]"
}

Code snippet

package main

import "github.com/gofiber/fiber"

func main() {
  app := fiber.New()

  app.Post("/login", func (c *fiber.Ctx) {
    c.Body("email") // no value here
  })

  app.Listen(8080)
}

🤔 Does Fiber support Hot reload ?

Just tried fiber. and the very first thing i feel missing was the hot reload.
I'm coming from a python background where Flask has a feature like development=True parameter to enable hot reload (reflect result in server instantly after changing the code).

🔥 Request Validation

Is your feature request related to a problem?
No

Describe the solution you'd like
Fiber has BodyParser function to parse request into the given interface. We can check that the interface has the Validation method and call it to see the parsed request is valid or not.

Describe alternatives you've considered
Validation may seem like an overkill feature, but I think it can reduce the handler code that is written for fiber.

Additional context

The following code shows a request with its validation method.

package request

import (
	"time"

	validation "github.com/go-ozzo/ozzo-validation"
	"github.com/go-ozzo/ozzo-validation/is"
)

// URL represents short URL creation request
type URL struct {
	URL    string     `json:"url"`
	Name   string     `json:"name"`
	Expire *time.Time `json:"expire"`
}

// Validate URL request
func (r URL) Validate() error {
	return validation.ValidateStruct(&r,
		validation.Field(&r.URL, validation.Required, is.URL),
	)
}

Fiber can check the validation method and call it if it is there on the given request.

🤔 How do I Set/Get data in context?

Question description
I want save the user information in JWT middleware and get it in the routing handler

Code snippet (optional)
In gin,i'll do it like this:

main.go

package main

func main() {
  app := fiber.New()
  app.Use("/api", midlleware.JwtAuth)
  app.Get("/api/v1/manager", api.ManagerGet)
}

middleware/jwt.go

package middleware

func JwtAuth() {
  // parse authorization
  c.Set("claims", claims)
  c.Next()
}

api/v1/manager.go

package api

func ManagerGet(c *fiber.Ctx) {
  claims, err := c.Get("claims")
}

🔥 Consider strong typing for API

Is your feature request related to a problem?
Hi!

In Go (IMO) it is considered bad practice to use interface{} if strongly typed API can be implemented.
I understand that idea is to have similarity with the expressjs library, but now developer has to visit documentation/source to identify what are proper params types for the routing function.

Also I think strongly typed API is one of things developers look after when choosing framework. It also can decrease amount of runtime checks and will show errors/mistypes during compile time.

Describe the solution you'd like
As an example for routing function:

func (app *App) Get(
    path string, 
    handler func()(ctx *Ctx), 
    middlewares ...func()(ctx *Ctx)
) App* {
    ...
}

Describe alternatives you've considered
Leave it as it is ¯\(ツ)

🤔 G104 (CWE-703): Errors unhandled. (Confidence: HIGH, Severity: LOW)

Based on new pipeline security, we need to treat errors

[/home/runner/work/fiber/fiber/context.go:107] - G104 (CWE-703): Errors unhandled. (Confidence: HIGH, Severity: LOW)
  > conn.Close()

I saw this message then we need to treat possible error returns method close.
https://github.com/gofiber/fiber/blob/master/context.go#L107

Suggestion

func releaseConn(conn *Conn) {
	if err := conn.Close(); err != nil {
             ...
        }
	conn.params = nil
	conn.values = nil
	conn.Conn = nil
	poolConn.Put(conn)
}

Congratulations!

This is the first web framework/library at Go that really like to me.

🔥 app.Group seems impossible to nest multiple layers

Is your feature request related to a problem?
app.Group seems impossible to nest multiple layers like gin

Describe the solution you'd like

//my api module
apiRouter := app.Group("/api")
{
	authRouter := apiRouter.Group("/auth")
	{
		authRouter.POST("/login", auth.Login)
		authRouter.GET("/tokenRefresh", middleware.JWTAuth(), auth.TokenRefresh)
	}
	v1Router := apiRouter.Group("/v1", middleware.JWTAuth())
	{
		managerRouter := v1Router.Group("/managers")
		{
			managerRouter.POST("", manager.Add)
		}
		testRouter := v1Router.Group("/test")
		{
			testRouter.GET("/redisSet", test.RedisSet)
		}
	}
	v2Router := apiRouter.Group("/v2")
	{
		managerRouter := v2Router.Group("/manager")
		{
			managerRouter.POST("/add", v2manager.Add)
		}
	}
}

Describe alternatives you've considered

Additional context

🐞 Document clearly that properties of the request ctx are invalid after the handler returns

Fiber version/commit: Latest
Issue description
Not sure if this is intentional or somewhat of a bug.
Currently, many properties of the request context are returned as strings but are unsafe to persist after the handler has returned (due to unsafe conversion here).

Expected behavior
It should be possible to safely store request properties for reuse after the handler has returned.

Steps to reproduce
See code snippet. Send a few requests in quick succession, e.g.:

for (( c=1; c<=10; c++ )); do   curl "http://localhost:3000/$c";   done

The second fmt.Printf will not output the correct value.

Code snippet

package main
 
import (
        "fmt"
        "time"
 
        "github.com/gofiber/fiber"
)
 
func main() {
        app := fiber.New()
 
        app.Get("/:number", func(c *fiber.Ctx) {
                number := c.Params("number")
                go myfunc(number)
                c.Send(number)
        })
        app.Listen(3000)
}
func myfunc(number string) {
        fmt.Printf("number is %s \n", number)
        time.Sleep(1 * time.Second)
        fmt.Printf("number is now %s \n", number)
}

🎉 v1.7.x release notes!

Fiber v1.7.1

go get -u github.com/gofiber/fiber

[NEW] ctx.BodyParser / https://fiber.wiki/context#bodyparser
[NEW] ctx.Error / https://fiber.wiki/context#error
[NEW] ctx.Next / https://fiber.wiki/context#next
[NEW] ctx.Render / https://fiber.wiki/context#render
[NEW] app.New / https://fiber.wiki/application#settings
[NEW] app.Recover / https://fiber.wiki/application#recover
[NEW] app.Group / https://fiber.wiki/application#group
[NEW] app.Settings / https://fiber.wiki/application#settings
[NEW] app.WebSocket / https://fiber.wiki/application#websocket
[NEW] app.Test / https://fiber.wiki/application#test
[NEW] fiber.Map / #153

[FIX] G104 (CWE-703) #168
[FIX] Flag redefined #167
[FIX] Group nesting #155
[FIX] Fix logo #160
[FIX] JSON err handling #126
[FIX] Add windows to tests #119
[FIX] Banner issue #109
[FIX] Static wildcard support #71
[FIX] Unit testing #41
[FIX] Gosec #5
[FIX] Default static files #3
[FIX] ctx.SaveFile #1

[DEPRECATE] ctx.BasicAuth
[DEPRECATE] ctx.Json
[DEPRECATE] ctx.JsonBytes
[DEPRECATE] ctx.JSONBytes
[DEPRECATE] ctx.JsonString
[DEPRECATE] ctx.JSONString
[DEPRECATE] ctx.Xml
[DEPRECATE] ctx.XML
[DEPRECATE] app.Prefork
[DEPRECATE] app.Engine
[DEPRECATE] app.Banner

If you got suggestions, ideas or criticism please create a new issue.

🏎️ v1.8.2 changelog

Fiber v1.8.2

go get -u github.com/gofiber/fiber/...

[NEW] app.Settings.BodyLimit https://fiber.wiki/application#settings
[NEW] middleware.Recover(handle ...func(*Ctx, error)) https://fiber.wiki/middleware#recover

[UPDATED] app.Static(prefix, root string) / https://fiber.wiki/application#static
[UPDATED] app.Listen(address interface{}, tlsconfig ...*tls.Config) / https://fiber.wiki/application#listen

[FIX] Allow TLS config #200 / https://fiber.wiki/application#listen
[FIX] Fiber router optimizations
[FIX] app.Settings.Immutable / this will now also keep []byte returns immutable
[FIX] ctx.Next / allows to continue after other routes finished
https://fiber.wiki/context#next

[DEPRECATED] app.Recover()
[DEPRECATED] settings.GETOnly
[DEPRECATED] settings.IdleTimeout
[DEPRECATED] settings.Concurrency
[DEPRECATED] settings.ReadTimeout
[DEPRECATED] settings.WriteTimeout
[DEPRECATED] settings.TCPKeepalive
[DEPRECATED] settings.MaxConnsPerIP
[DEPRECATED] settings.ReadBufferSize
[DEPRECATED] settings.WriteBufferSize
[DEPRECATED] settings.ConcurrencySleep
[DEPRECATED] settings.DisableKeepAlive
[DEPRECATED] settings.ReduceMemoryUsage
[DEPRECATED] settings.MaxRequestsPerConn
[DEPRECATED] settings.TCPKeepalivePeriod

🔥 Query params

I can't find any normal way to get a query string params without using raw fasthttp queryString
Something like that can be very useful:

app.Get("/", func(c *fiber.Ctx) {
  queryValue := c.Query().Get("param_key")
})

Thanx!

🤔 Trailer Headers?

Question description

👋 I was pleasantly surprised by this library and wanted to learn about adding (advocating?) for HTTP Trailer support.

I would like to try this library out with a problem that requires streaming and trailers are very helpful in this case.

Further reading: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Trailer

I reviewed the documentation for Fiber to learn if this was possible. It does not appear to be the case. I did further research and it seems that the underlying http layer does not yet support Traillers (yet) valyala/fasthttp#210. The messaging in the Issue is promising and so I was wondering/hoping if this is something the Fiber team could get behind and advocate for as a desired use case?

Best of luck on this project!

🔥 Add a shortcut for map like gin.H

Is your feature request related to a problem?
No

Describe the solution you'd like

c.JSON(fiber.H{
    "field1": someStructData1,
    "field2": someStructData2,
})
// H is a shortcut for map[string]interface{}
type H map[string]interface{}

Describe alternatives you've considered

Additional context

[🐞] Found 3 gosec issues: CWE-78 and CWE-242

Your environment:

  • Fiber Web Framework [e.g. 1.2.3]: 1.2.3
  • OS [e.g. macOS 10.14.6]: macOS 10.14.6
  • Golang [e.g. 1.13.7]: 1.13.7

Describe the bug

A clear and concise description of what the bug is.

To Reproduce

Steps to reproduce the behavior:

  1. Install securego/gosec
  2. Run $ gosec ./...
  3. See security report:

Issue G204 (CWE-78): Subprocess launched with function call as argument or cmd arguments:

[/Users/koddr/CodeProjects/fiber/listen.go:101] - G204 (CWE-78): Subprocess launched with function call as argument or cmd arguments (Confidence: HIGH, Severity: MEDIUM)
  > exec.Command(os.Args[0], "-prefork", "-child")

Issue G103 (CWE-242): Use of unsafe calls should be audited:

[/Users/koddr/CodeProjects/fiber/utils.go:82] - G103 (CWE-242): Use of unsafe calls should be audited (Confidence: HIGH, Severity: LOW)
  > unsafe.Pointer(&b)

[/Users/koddr/CodeProjects/fiber/utils.go:86] - G103 (CWE-242): Use of unsafe calls should be audited (Confidence: HIGH, Severity: LOW)
  > unsafe.Pointer(&s)

Expected behavior

No security issues on report.

Screenshots

No need.

Additional context

Full console output:

$ sw_vers

ProductName:    Mac OS X
ProductVersion: 10.14.6
BuildVersion:   18G2022

$ go version 

go version go1.13.7 darwin/amd64

$ gosec ./...

[gosec] 2020/02/02 12:32:41 Including rules: default
[gosec] 2020/02/02 12:32:41 Excluding rules: default
[gosec] 2020/02/02 12:32:41 Import directory: /Users/koddr/CodeProjects/fiber
[gosec] 2020/02/02 12:32:42 Checking package: fiber
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/application.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/context.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/listen.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/methods.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/request.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/response.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/router.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/static.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/status.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/types.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/utils.go
[gosec] 2020/02/02 12:32:42 Import directory: /Users/koddr/CodeProjects/fiber/middleware
[gosec] 2020/02/02 12:32:42 Checking package: middleware
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/middleware/cors.go
[gosec] 2020/02/02 12:32:42 Checking file: /Users/koddr/CodeProjects/fiber/middleware/helmet.go

Results:

[/Users/koddr/CodeProjects/fiber/listen.go:101] - G204 (CWE-78): Subprocess launched with function call as argument or cmd arguments (Confidence: HIGH, Severity: MEDIUM)
  > exec.Command(os.Args[0], "-prefork", "-child")

[/Users/koddr/CodeProjects/fiber/utils.go:82] - G103 (CWE-242): Use of unsafe calls should be audited (Confidence: HIGH, Severity: LOW)
  > unsafe.Pointer(&b)

[/Users/koddr/CodeProjects/fiber/utils.go:86] - G103 (CWE-242): Use of unsafe calls should be audited (Confidence: HIGH, Severity: LOW)
  > unsafe.Pointer(&s)

Summary:
   Files: 13
   Lines: 1671
   Nosec: 0
  Issues: 3

🤔 always get empty JSON response

Question description

  • I always got empty {} from JSON response.
  • no error is returned from the c.JSON() method.
  • I tested in Postman, the response is always an empty object like {}. with JSONP method, the response is always callback{}.
  • I don't know what happened or how to dig into this problem.
  • version: 1.7.0

Code snippet (optional)

type status struct {
	code    int32
	message string
}

...
       data := status{
		code:    2,
		message: "hello wolrd",
	}
	if err := c.JSON(data); err != nil {
		log.Printf("error in response %v", err)
	}

Add a License

Is your feature request related to a problem?
By default in most jurisdictions, any creative endeavor is copyrighted ("all rights reserved").
This makes using the project difficult, legally speaking, especially in environments where that's a concern (even if no one has the intention of starting a legal action).

Describe the solution you'd like
Add a LICENSE file.
Optionally, also have some form of CLA or similar (at least for already-contributed-contributors).
I personally prefer the Unlicense (available under choose-a-license), but any license would be fine.

Describe alternatives you've considered
Alternatively, you could grant individual licenses to anyone that asks, but that places undue burden on the project maintainers.
Regarding license choices, other popular alternatives include MIT and GPL3.

Additional context

🌐 Translate Fiber (i18n)

💡 Translation status

Fiber README is already translated into 9 languages:

  • 🇷🇺 Russian (RU)
  • 🇪🇸 Spanish (ES)
  • 🇨🇳 Chinese (ZH_CH)
  • 🇯🇵 Japanese (JA)
  • 🇵🇹 Portuguese (PT)
  • 🇩🇪 German (DE)
  • 🇰🇷 South Korean (KO)
  • 🇫🇷 French (FR)
  • 🇹🇷 Turkish (TR)

Fiber official documentation is already translated into 4 languages:

❗️ This translations on hold. We're preparing to re-write English docs after release Fiber v1.8.

- [x] 🇷🇺 Russian (RU)
- [ ] 🇪🇸 Spanish (ES)
- [x] 🇨🇳 Chinese (ZH_CH)
- [ ] 🇯🇵 Japanese (JA)
- [ ] 🇵🇹 Portuguese (PT)
- [ ] 🇩🇪 German (DE)
- [x] 🇰🇷 South Korean (KO)
- [x] 🇫🇷 French (FR)
- [ ] 🇹🇷 Turkish (TR)

✨ Add new translation

Anyone, who wants to add a new translation for Fiber, must follow these simple rules:

  1. The translation must fully follow the narrative, structure and style of presentation as in the main .github/README.md file.
  2. To be added to the master branch, the translation must be completely finished and double-checked.
  3. IT-specific phrases and comments in code snippets may not be translated.

Recommendations for PR description:

  • Add link to flag for your language or country (we use flag-icon-css with 4x3 format, for example, EN lang flag).
  • Add some words about tools, which you used to validate translation (like Google Translator, GitLocalize or DeepL).

✏️ Update translation, when new features are shipped

For current Fiber translators: please read the release notes of new official versions to update Fiber docs and .github/README.md file for your language!

💭 Improve/fix translation

If you find a translation error or want to improve translation, please make a fork of this repository, edit the corresponding README file in .github folder and send PR.

✍️ Translators list

Click to see translators list

🇷🇺 Russian

🇪🇸 Spanish

🇨🇳 Chinese

🇯🇵 Japanese

🇵🇹 Portuguese

🇩🇪 German

🇰🇷 South Korean

🇫🇷 French

🇹🇷 Turkish

This list will be update by Fiber authors, after merge your PR to master branch.

⚠️ Warnings about liability

  • All translations are done by volunteers, who are not indifferent to Fiber.
  • Fiber authors are not responsible for these translations, other than English, because they simply does not speak all these languages.

🧬 v1.8.1 changelog

Fiber v1.8.1

go get -u github.com/gofiber/fiber/...

[NEW] app.Settings.Immutable / https://fiber.wiki/application#settings
[NEW] app.Settings.Compression / https://fiber.wiki/application#settings

[NEW] Ctx.Compress / https://fiber.wiki/context#compress
[NEW] Ctx.Range / https://fiber.wiki/context#range heart @hanFengSan

[NEW] middleware.BasicAuth / https://fiber.wiki/middleware#basicauth
[NEW] middleware.CORS / https://fiber.wiki/middleware#cors
[NEW] middleware.Limiter / https://fiber.wiki/middleware#limiter
[NEW] middleware.Logger / https://fiber.wiki/middleware#logger
[NEW] middleware.RequestID / https://fiber.wiki/middleware#requestid
[NEW] middleware.Helmet / https://fiber.wiki/middleware#helmet

[FIX] Internal optimizations

🔥 add an interface for serving a custom net.Listener

Is your feature request related to a problem?
no
Describe the solution you'd like
something along the lines of

app := fiber.New()
ln, err := net.Listen("unix", "/tmp/sock.d")
app.Serve(ln)

Describe alternatives you've considered
editing the source code to add this functionality directly
Additional context

🔥 Support GZip / Deflate

Is your feature request related to a problem?
Now, the gzip is built in Static(),so I can't customize which paths to open gzip and which file sizes to open gzip

Describe the solution you'd like
In my project,i need open gzip for staticfiles,at the same time, i want open gzip for restful api module(when the response is bigger than 4kb)

Describe alternatives you've considered
gzip be removed from Static() and exist as a official middleware

Additional context

🐞 Color residue

Fiber version/commit
v1.4.2

Issue description
When I run the build binary and exit color residue.(cmd, powershell,powershell core)

Expected behavior
no color residue

Steps to reproduce
In windows: run binary

Code snippet

package main

import "github.com/gofiber/fiber"

func main() {
	app := fiber.New()

	app.Get("/", func(c *fiber.Ctx) {
		c.Send("Hello World!")
	})

	app.Listen("localhost:8080")
}

image

🔥 Consider adding support for custom Context

Is your feature request related to a problem?
I find myself in need to instantiate a validator and pass it to all the routes. I don't want to have any singletons in the application and so I am looking for a way to extend fiber.Context.

Describe the solution you'd like
I would like to be able to extend the Context with my own custom Context which contains a 'Validator' property which I can set at server startup. The custom Context would be passed to all the routes and I could access the custom properties when needed in my routes.

Describe alternatives you've considered
The alternative is to have a singleton that I can access from my routes. But we all know why Singletons are not a good idea.

Another alternative would be to have a middleware to do this, but I don't want to instantiate a validator on every request.

🤔 How to register a Prometheus handler

I'm trying to register the Prometheus handler to track some metrics from the application I'm writing but I cannot find a way. I managed to to the following:

package main

import (
  "github.com/gofiber/fiber"
  "github.com/prometheus/client_golang/prometheus/promhttp"
  "github.com/valyala/fasthttp/fasthttpadaptor"

func main() {
  app := fiber.New()
  
  p := fasthttpadaptor.NewFastHTTPHandler(promhttp.Handler())

  app.Get("/metrics", func(c *fiber.Ctx) {
    p(c.Fasthttp)
  })

  app.Get("/", func(c *fiber.Ctx){
    c.Send("Hello, World!")
  })

  app.Get("/404", func(c *fiber.Ctx){
    c.Status(4040).Send("Where did I put it?")
  })

  app.Listen(3000)
}

And it does respond to the requests on /metrics with some data that seems reasonable. Only problem it doesn't seem to count the responses correctly.

(the two endpoints / and /404 are there exactly to try it).

🐞 static.go path wildcard support

Fiber version/commit
v1.4.0
Issue description
static.go line 36 can't support "/static/*"
Expected behavior

Steps to reproduce

Code snippet
// Check if wildcard for single files
if prefix == "" || prefix == "/" {
wildcard = true
}

   // line 76
  //  if prefix is "/*"  and in windows then generate \*\xxx\a.js
package main

func main() {

}

🔥 Add some middleware

Is your feature request related to a problem?

Describe the solution you'd like
Looger、Recovery(is necessary in the development)
Ggzip(Currently Static() provides compression, but cannot be customized)
CORS、CSRF、JWT Auth etc...

Describe alternatives you've considered
Are there plans for these middleware?

Additional context

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.