auth

package
v0.3.4 Latest Latest
Warning

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

Go to latest
Published: Dec 27, 2024 License: MIT Imports: 11 Imported by: 0

README

rex.auth

Package auth provides session-based authentication middleware for the Rex router. It uses secure cookie sessions to maintain authentication state and supports storing custom user state in the session.

Installation

go get -u github.com/abiiranathan/rex

Basic usage:

	// First, register your user type for session storage
	auth.Register(User{})

	// Create the middleware with authentication key
	authMiddleware := auth.Cookie(auth.CookieConfig{
		KeyPairs: [][]byte{[]byte("your-32-byte-auth-key")},
		ErrorHandler: func(c *rex.Context) error {
			return c.Status(http.StatusUnauthorized).JSON(map[string]string{
				"error": "Unauthorized",
			})
		},
	})

	// Use the middleware in your router
	router := rex.NewRouter()
	router.Use(authMiddleware)

Login example:

	router.Post("/login", func(c *rex.Context) error {
		user := &User{ID: 1, Name: "John"}
		if err := auth.SetAuthState(c, user); err != nil {
			return err
		}
		return c.JSON(user)
	})

Access authenticated user:

	router.Get("/me", func(c *rex.Context) error {
		state, authenticated := auth.GetAuthState(c)
		if !authenticated {
			return c.Status(http.StatusUnauthorized)
		}
		user := state.(*User)
		return c.JSON(user)
	})

Logout example:

	router.Post("/logout", func(c *rex.Context) error {
		return auth.ClearAuthState(c)
	})

Security Notes:

  • Cookie sessions are encrypted and authenticated using the provided key pairs
  • HttpOnly and SameSite=Strict are enforced for security
  • Default session duration is 24 hours
  • Use cryptographically secure random bytes for key pairs
  • For production, use https://pkg.go.dev/crypto/rand to generate keys

Key Generation Example:

	key := make([]byte, 32)
	if _, err := rand.Read(key); err != nil {
		panic(err)
	}

For key rotation, you can provide multiple key pairs:

	authMiddleware := auth.Cookie(auth.CookieConfig{
		KeyPairs: [][]byte{
			[]byte("new-32-byte-auth-key"),
			[]byte("new-32-byte-encrypt-key"),
			[]byte("old-32-byte-auth-key"),
			[]byte("old-32-byte-encrypt-key"),
		},
		// ... other config
	})

Custom cookie options:

	authMiddleware := auth.Cookie(auth.CookieConfig{
		KeyPairs: [][]byte{[]byte("your-32-byte-auth-key")},
		Options: &sessions.Options{
			Path:     "/",
			Domain:   "example.com",
			MaxAge:   3600,
			Secure:   true,
		},
		// ... other config
	})

Skip authentication for specific routes:

	authMiddleware := auth.Cookie(auth.CookieConfig{
		KeyPairs: [][]byte{[]byte("your-32-or-64-byte-auth-key")},
		SkipAuth: func(req *http.Request) bool {
			return req.URL.Path == "/login" || req.URL.Path == "/signup"
		},
		// ... other config
	})

It also provides middleware for BasicAuth, JWT auth. Oauth2 support is coming soon.

Documentation

Overview

Package auth provides session-based authentication middleware for the Rex router. It uses secure cookie sessions to maintain authentication state and supports storing custom user state in the session. It also provide JWT and BasicAuth middleware. View the README for more information.

Index

Constants

This section is empty.

Variables

View Source
var ErrNotInitialized = errors.New("auth: Store not initialized")

Functions

func BasicAuth

func BasicAuth(username, password string, realm ...string) rex.Middleware

Basic Auth middleware. If the username and password are not correct, a 401 status code is sent. The realm is the realm to display in the login box. Default is "Restricted".

func ClearAuthState

func ClearAuthState(c *rex.Context) error

ClearAuthState deletes authentication state.

func Cookie(config CookieConfig) rex.Middleware

Cookie creates a new authentication middleware with the given configuration. Keys are defined in pairs to allow key rotation, but the common case is to set a single authentication key and optionally an encryption key.

You MUST register the type of state you want to store in the session by calling auth.Register or gob.Register before using this middleware.

func CreateJWTToken

func CreateJWTToken(secret string, payload any, exp time.Duration) (string, error)

CreateToken creates a new JWT token with the given payload and expiry duration. JWT is signed with the given secret key using the HMAC256 alegorithm.

func GetAuthState

func GetAuthState(c *rex.Context) (state any, authenticated bool)

GetAuthState returns the auth state for this request.

func GetPayload

func GetPayload(req *http.Request) any

Returns the payload from the request or nil if non-exists. Should be called inside the handler when JWT verification is complete.

func JWT

func JWT(secret string) rex.Middleware

JWT creates a JWT middleware with the given secret and options.

func Register

func Register(value any)

Register registers this type with GOB encoding. Otherwise you will get a panic trying to serialize your custom types. See gob.Register. Example usage: auth.Register(User{})

func SetAuthState

func SetAuthState(c *rex.Context, state any) error

SetAuthState stores user state for this request. It could be the user object, userId or anything serializable into a cookie. This is typically called following user login.

func VerifyJWToken

func VerifyJWToken(secret, tokenString string) (jwt.MapClaims, error)

VerifyJWToken verifies the given JWT token with the secret key. Returns the claims if the token is valid, otherwise an error. The token is verified using the HMAC256 algorithm. The default claims are stored in the "payload" key and the expiry time in the "exp" key.

Types

type CookieConfig

type CookieConfig struct {
	// KeyPairs are the authentication and encryption key pairs.
	// The first key is used for authentication and the second key(if provided) for encryption
	KeyPairs [][]byte

	// Cookie options.
	// Default: HttpOnly=true, SameSite=Strict(always), MaxAge=24hrs, Domain=/,secure=false
	Options *sessions.Options

	// Skip authentication for certain requests
	SkipAuth func(req *http.Request) bool

	// Called when authentication fails
	ErrorHandler func(c *rex.Context) error
}

Jump to

Keyboard shortcuts

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