package lib import ( "encoding/base64" "fmt" "net/http" "strings" "time" "github.com/biscuit-auth/biscuit-go/v2" "github.com/biscuit-auth/biscuit-go/v2/parser" "github.com/labstack/echo/v4" ) func queryUser(authorizer biscuit.Authorizer) (biscuit.FactSet, error) { rule, err := parser.FromStringRule(`data($name) <- user($name)`) if err != nil { return nil, fmt.Errorf("failed to parse check: %v", err) } return authorizer.Query(rule) } func AuthMiddleware(skipper_auth func(echo.Context) bool) echo.MiddlewareFunc { return func(next echo.HandlerFunc) echo.HandlerFunc { return func(c echo.Context) error { if skipper_auth(c) { return next(c) } tokens := strings.Split(c.Request().Header.Get("Authorization"), " ") if len(tokens) != 2 { return c.String(http.StatusUnauthorized, "Header d'authentification manquant") } c.Set("token", tokens[1]) byteToken, _ := base64.URLEncoding.DecodeString(tokens[1]) b, err := biscuit.Unmarshal(byteToken) if err != nil { return c.JSON(http.StatusUnauthorized, err) } authorizer, err := b.Authorizer(PublicKey) if err != nil { return c.JSON(http.StatusUnauthorized, err) } now := time.Now() authorizerContents, err := parser.FromStringAuthorizerWithParams(` time(`+now.Format("2006-01-02T15:04:05Z")+`); allow if time($time), $time <= `+now.Format("2006-01-02T15:04:05Z")+`; `, map[string]biscuit.Term{}) if err != nil { return c.JSON(http.StatusUnauthorized, err) } authorizer.AddAuthorizer(authorizerContents) if err := authorizer.Authorize(); err != nil { return c.JSON(http.StatusUnauthorized, err) } fact, err := queryUser(authorizer) if err != nil { return c.JSON(http.StatusUnauthorized, err) } c.Set("username", strings.Split(fact[0].IDs[0].String(), "\"")[1]) return next(c) } } }