secure

package module
v0.0.0-...-c41730b Latest Latest
Warning

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

Go to latest
Published: May 22, 2017 License: LGPL-3.0 Imports: 11 Imported by: 16

README

secure

Package secure manages client side session tokens for stateless web applications.

GoDoc

Documentation

Overview

Package secure manages authentication cookies for stateless web applications, and form tokens for CSRF protection.

An encrypted connection (https) is required.

Call 'Configure()' once to provide the information for the package to operate, including the type of the authentication data that will be used. The actual configuration parameters are stored in a 'Config' type struct. The 'DB' interface syncs the Config to an external database, and automatically rotates security keys.

Once configured, call 'Authentication()' to retrieve the data from the cookie. It will redirect to a login page if no valid cookie is present (unless the 'optional' argument was 'true'). 'LogIn()' creates a new cookie, stores the provided data in it, and redirects back to the page that required the authentication. 'Update()' updates the authentication data in the current cookie. 'LogOut()' deletes the cookie.

You'll probably want to wrap 'Authentication()' in a function that converts the 'interface{}' result to the type that you use for the cookie data.

Index

Constants

View Source
const FormValueName = "_formtoken"

FormValueName is the name of the FormValue that is checked in PUT, POST, PATCH, and DELETE handles.

Variables

View Source
var (

	// ErrTokenNotSaved is returned by LogIn() if it couldn't set the cookie.
	ErrTokenNotSaved = errors.New("secure: failed to save the session cookie")

	// ErrNoTLS is returned by LogIn() if the connection isn't encrypted
	// (https)
	ErrNoTLS = errors.New("secure: logging in requires an encrypted conection")
)

Functions

func Authentication

func Authentication(r *http.Request) interface{}

Authentication returns the record that was stored in the cookie on LogIn().

Call from a Handle wrapped in secure.Handle or secure.IfHandle.

func Configure

func Configure(record interface{}, dbImpl DB, validateFunc ValidateCookie, opt_config ...*Config)

Configure configures the package and must be called once before calling any other function in this package.

'record' is an arbitrary (can be empty) instance of the type of the authentication data that will be passed to Login() to store in the cookie. It's needed to get its type registered with the serialisation package used (encoding/gob).

'dbImpl' is the implementation of the DB interface to sync the configuration and rotate the keys.

'validate' is the function that regularly verifies the cookie data.

'opt_config' is the Config instance to start with. If omitted, the config from the db is used, or else the default config.

func Handle

func Handle(handle httprouter.Handle) httprouter.Handle

secure.Handle ensures the client is logged in when accessing a certian route, redirecting to the log in page if not. The given Handle function should call Authentication() to get the client's account details.

If the cookie is missing, the session has timed out, or the cookie data is invalidated though the ValidateCookie function, the response then gets status 403 Forbidden, and the browser will redirect to config.LogInPath.

func IfHandle

func IfHandle(authenticatedHandle httprouter.Handle, unauthenticatedHandle httprouter.Handle) httprouter.Handle

secure.IfHandle calls the one Handle function for logged-in clients, and the other for logged-out clients.

func LogIn

func LogIn(w http.ResponseWriter, r *http.Request, record interface{}) (err error)

LogIn creates the cookie and sets the cookie. It redirects back to the path where Authenticate() was called.

'record' is the authentication data to store in the cookie, as returned by Authentication()

func LogOut

func LogOut(w http.ResponseWriter, r *http.Request, redirect bool)

LogOut deletes the cookie. If 'redirect' is 'true', the request is redirected to config.LogOutPath.

func Update

func Update(w http.ResponseWriter, r *http.Request, record interface{}) (err error)

Update updates the authentication data in the cookie.

Types

type Config

type Config struct {

	// Session manages session cryptography.
	Session *Session

	// Token manages token cryptography.
	Token *Token
}

Config holds the package's configuration parameters. Can be synced with an external database, through the DB interface.

type DB

type DB interface {

	// Fetch fetches a Config instance from the database.
	Fetch(dst *Config) error

	// Upsert inserts a Config instance into the database if none is present
	// on Configure(). Upsert updates the CookieKeyPairs and CookieTimeStamp values on key
	// rotation time.
	Upsert(src *Config) error
}

DB is the interface to implement for syncing the configuration parameters.

Syncing is executed every config.SyncInterval. If parameter values are changed in the database, the new values get synced to all servers that run the application.

type FormToken

type FormToken struct {

	// IP is the client's IP address.
	IP string

	// Path is the path on this server the token is valid for.
	Path string

	// Timestamp is when the token was created.
	Timestamp time.Time
}

A FormToken is a secured identification of a request, suitable for protection against cross site request forgery.

func NewFormToken

func NewFormToken(r *http.Request, opt_path ...string) *FormToken

NewFormToken initialises a new FormToken. The opt_path argument overrides the default r.URL.Path.

func (*FormToken) Parse

func (f *FormToken) Parse(s string) error

Parse populates the data fields from an encrypted token string.

func (*FormToken) String

func (f *FormToken) String() string

String returns the encrypted token string.

type Keys

type Keys struct {

	// KeyPairs holds 3 key pairs: current, previous, and next.
	KeyPairs [][]byte

	// Start is when the current key pair became current.
	Start time.Time

	// TimeOut is how much time Start the key pairs should be rotated.
	TimeOut time.Duration
}

Keys manages rotating cryptographic keys.

type SecureRouter

type SecureRouter struct {
	*httprouter.Router
}

A SecureRouter is a secured httprouter. PUT, POST, PATCH, and DELETE handles check for a valid FormToken encrypted token string in the request's "_formtoken" FormValue.

func Router

func Router() *SecureRouter

Router returns the secure router.

func (*SecureRouter) DELETE

func (r *SecureRouter) DELETE(path string, handle httprouter.Handle)

DELETE registers a handler for a DELETE request to the given path. The handler is only run if the request carries a valid form token.

func (*SecureRouter) GET

func (r *SecureRouter) GET(path string, handle httprouter.Handle)

GET registers a handler for a GET request to the given path.

func (*SecureRouter) HEAD

func (r *SecureRouter) HEAD(path string, handle httprouter.Handle)

HEAD registers a handler for a HEAD request to the given path.

func (*SecureRouter) OPTIONS

func (r *SecureRouter) OPTIONS(path string, handle httprouter.Handle)

OPTIONS registers a handler for a OPTIONS request to the given path.

func (*SecureRouter) PATCH

func (r *SecureRouter) PATCH(path string, handle httprouter.Handle)

PATCH registers a handler for a PATCH request to the given path. The handler is only run if the request carries a valid form token.

func (*SecureRouter) POST

func (r *SecureRouter) POST(path string, handle httprouter.Handle)

POST registers a handler for a POST request to the given path. The handler is only run if the request carries a valid form token.

func (*SecureRouter) PUT

func (r *SecureRouter) PUT(path string, handle httprouter.Handle)

PUT registers a handler for a PUT request to the given path. The handler is only run if the request carries a valid form token.

type Session

type Session struct {

	// Keys encapsulates the rotating key data & functionality.
	*Keys

	// LogInPath is the URL where Authentication() redirects to; a log in form
	// should be served here.
	// Default value is "/session".
	LogInPath string

	// LogOutPath is the URL where LogOut() redirects to.
	// Default value is "/".
	LogOutPath string

	// ValidateTimeOut determines whether it's time to have the
	// cookie data checked by the ValidateCookie function.
	// Default value is 5 minutes.
	ValidateTimeOut time.Duration
	// contains filtered or unexported fields
}

A Session value is stored in the Config to manage session cryptography.

type Token

type Token struct {

	// Keys encapsulates the rotating key data & functionality.
	*Keys
	// contains filtered or unexported fields
}

A Token value is stored in the Config to manage token cryptography.

type ValidateCookie

type ValidateCookie func(src interface{}) (dst interface{}, valid bool)

ValidateCookie is the type of the function passed to Configure(), that gets called to have the application test whether the cookie data is still valid (e.g. to prevent continued access with a cookie that was created with an old password)

'src' is the authentication data from the cookie.

'dst' is the fresh authentication data to replace the cookie data with.

'valid' is whether the old data was good enough to keep the current cookie.

Default implementation always returns the cookie data as is, and true, which is significantly insecure.

Each successful validation stores a timestamp in the cookie. ValidateCookie is called on Authentication, if the time since the validation timestamp > config.SyncInterval

Jump to

Keyboard shortcuts

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