httpauth

package module
v1.3.2 Latest Latest
Warning

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

Go to latest
Published: Feb 10, 2016 License: MIT Imports: 12 Imported by: 0

README

Go Session Authentication

Build Status Coverage GoDoc Version 2.0.0

See git tags/releases for information about potentially breaking change.

This package uses the Gorilla web toolkit's sessions package to implement a user authentication and authorization system for Go web servers.

Multiple user data storage backends are available, and new ones can be implemented relatively easily.

Access can be restricted by a users' role.

Uses bcrypt for password hashing.

var (
    aaa httpauth.Authorizer
)

func login(rw http.ResponseWriter, req *http.Request) {
    username := req.PostFormValue("username")
    password := req.PostFormValue("password")
    if err := aaa.Login(rw, req, username, password, "/"); err != nil && err.Error() == "already authenticated" {
        http.Redirect(rw, req, "/", http.StatusSeeOther)
    } else if err != nil {
        fmt.Println(err)
        http.Redirect(rw, req, "/login", http.StatusSeeOther)
    }
}

Run go run server.go from the examples directory and visit localhost:8009 for an example. You can login with the username "admin" and password "adminadmin".

Tests can be run by simulating Travis CI's build environment. There's a very unsafe script --- start-test-env.sh that will do this for you.

You should follow me on Twitter. Appreciate this package?

TODO
  • User roles - modification
  • SMTP email validation (key based)
  • More backends
  • Possible remove dependance on bcrypt

Documentation

Overview

Package httpauth implements cookie/session based authentication and authorization. Intended for use with the net/http or github.com/gorilla/mux packages, but may work with github.com/codegangsta/martini as well. Credentials are stored as a username + password hash, computed with bcrypt.

Three user storage systems are currently implemented: file based (encoding/gob), sql databases (database/sql), and MongoDB databases.

Access can be restricted by a users' role. A higher role will give more access.

Users can be redirected to the page that triggered an authentication error.

Messages describing the reason a user could not authenticate are saved in a cookie, and can be accessed with the Messages function.

Example source can be found at https://github.com/apexskier/httpauth/blob/master/examples/server.go

Index

Constants

This section is empty.

Variables

View Source
var (
	ErrDeleteNull  = mkerror("deleting non-existant user")
	ErrMissingUser = mkerror("can't find user")
)

ErrDeleteNull is returned by DeleteUser when that user didn't exist at the time of call. ErrMissingUser is returned by Users when a user is not found.

View Source
var (
	ErrMissingBackend = errors.New("gobfilebackend: missing backend")
)

ErrMissingBackend is returned by NewGobFileAuthBackend when the file doesn't exist. Be sure to create (or touch) it if using brand new backend or resetting backend.

View Source
var (
	ErrMissingLeveldbBackend = errors.New("leveldbauthbackend: missing backend")
)

ErrMissingLeveldbBackend is returned by NewLeveldbAuthBackend when the file doesn't exist. Be sure to create (or touch) it if using brand new backend or resetting backend.

Functions

This section is empty.

Types

type AuthBackend

type AuthBackend interface {
	SaveUser(u UserData) error
	User(username string) (user UserData, e error)
	Users() (users []UserData, e error)
	DeleteUser(username string) error
	Close()
}

The AuthBackend interface defines a set of methods an AuthBackend must implement.

type Authorizer

type Authorizer struct {
	// contains filtered or unexported fields
}

Authorizer structures contain the store of user session cookies a reference to a backend storage system.

func NewAuthorizer

func NewAuthorizer(backend AuthBackend, key []byte, defaultRole string, roles map[string]Role) (Authorizer, error)

NewAuthorizer returns a new Authorizer given an AuthBackend, a cookie store key, a default user role, and a map of roles. If the key changes, logged in users will need to reauthenticate.

Roles are a map of string to httpauth.Role values (integers). Higher Role values have more access.

Example roles:

var roles map[string]httpauth.Role
roles["user"] = 2
roles["admin"] = 4
roles["moderator"] = 3

func (Authorizer) Authorize

func (a Authorizer) Authorize(rw http.ResponseWriter, req *http.Request, redirectWithMessage bool) error

Authorize checks if a user is logged in and returns an error on failed authentication. If redirectWithMessage is set, the page being authorized will be saved and a "Login to do that." message will be saved to the messages list. The next time the user logs in, they will be redirected back to the saved page.

func (Authorizer) AuthorizeRole

func (a Authorizer) AuthorizeRole(rw http.ResponseWriter, req *http.Request, role string, redirectWithMessage bool) error

AuthorizeRole runs Authorize on a user, then makes sure their role is at least as high as the specified one, failing if not.

func (Authorizer) CurrentUser

func (a Authorizer) CurrentUser(rw http.ResponseWriter, req *http.Request) (user UserData, e error)

CurrentUser returns the currently logged in user and a boolean validating the information.

func (Authorizer) DeleteUser

func (a Authorizer) DeleteUser(username string) error

DeleteUser removes a user from the Authorize. ErrMissingUser is returned if the user to be deleted isn't found.

func (Authorizer) Login

func (a Authorizer) Login(rw http.ResponseWriter, req *http.Request, u string, p string, dest string) error

Login logs a user in. They will be redirected to dest or to the last location an authorization redirect was triggered (if found) on success. A message will be added to the session on failure with the reason.

func (Authorizer) Logout

func (a Authorizer) Logout(rw http.ResponseWriter, req *http.Request) error

Logout clears an authentication session and add a logged out message.

func (Authorizer) Messages

func (a Authorizer) Messages(rw http.ResponseWriter, req *http.Request) []string

Messages fetches a list of saved messages. Use this to get a nice message to print to the user on a login page or registration page in case something happened (username taken, invalid credentials, successful logout, etc).

func (Authorizer) Register

func (a Authorizer) Register(rw http.ResponseWriter, req *http.Request, user UserData, password string) error

Register and save a new user. Returns an error and adds a message if the username is in use.

Pass in a instance of UserData with at least a username and email specified. If no role is given, the default one is used.

func (Authorizer) Update

func (a Authorizer) Update(rw http.ResponseWriter, req *http.Request, u string, p string, e string) error

Update changes data for an existing user. The behavior of the update varies depending on how the arguments are passed:

If an empty username u is passed then it updates the current user from the session
  (self-edit scenario)
If the username u is passed explicitly then it updates the passed username
  (admin update scenario)
If an empty password p is passed then it keeps the original rather than
  regenerating the hash, if a new password is passed then it regenerates the hash.
If an empty email e is passed then it keeps the orginal rather than updating it,
  if a new email is passedn then it updates it.

type GobFileAuthBackend

type GobFileAuthBackend struct {
	// contains filtered or unexported fields
}

GobFileAuthBackend stores user data and the location of the gob file.

func NewGobFileAuthBackend

func NewGobFileAuthBackend(filepath string) (b GobFileAuthBackend, e error)

NewGobFileAuthBackend initializes a new backend by loading a map of users from a file. If the file doesn't exist, returns an error.

func (GobFileAuthBackend) Close

func (b GobFileAuthBackend) Close()

Close cleans up the backend. Currently a no-op for gobfiles.

func (GobFileAuthBackend) DeleteUser

func (b GobFileAuthBackend) DeleteUser(username string) error

DeleteUser removes a user, raising ErrDeleteNull if that user was missing.

func (GobFileAuthBackend) SaveUser

func (b GobFileAuthBackend) SaveUser(user UserData) error

SaveUser adds a new user, replacing one with the same username, and saves a gob file.

func (GobFileAuthBackend) User

func (b GobFileAuthBackend) User(username string) (user UserData, e error)

User returns the user with the given username. Error is set to ErrMissingUser if user is not found.

func (GobFileAuthBackend) Users

func (b GobFileAuthBackend) Users() (us []UserData, e error)

Users returns a slice of all users.

type LeveldbAuthBackend added in v1.2.1

type LeveldbAuthBackend struct {
	// contains filtered or unexported fields
}

LeveldbAuthBackend stores user data and the location of a leveldb file.

Current implementation holds all user data in memory, flushing to leveldb as a single value to the key "httpauth::userdata" on saves.

func NewLeveldbAuthBackend added in v1.2.1

func NewLeveldbAuthBackend(filepath string) (b LeveldbAuthBackend, e error)

NewLeveldbAuthBackend initializes a new backend by loading a map of users from a file. If the file doesn't exist, returns an error.

func (LeveldbAuthBackend) Close added in v1.2.1

func (b LeveldbAuthBackend) Close()

Close cleans up the backend. Currently a no-op for gobfiles.

func (LeveldbAuthBackend) DeleteUser added in v1.2.1

func (b LeveldbAuthBackend) DeleteUser(username string) error

DeleteUser removes a user, raising ErrDeleteNull if that user was missing.

func (LeveldbAuthBackend) SaveUser added in v1.2.1

func (b LeveldbAuthBackend) SaveUser(user UserData) error

SaveUser adds a new user, replacing one with the same username, and flushes to the db.

func (LeveldbAuthBackend) User added in v1.2.1

func (b LeveldbAuthBackend) User(username string) (user UserData, e error)

User returns the user with the given username. Error is set to ErrMissingUser if user is not found.

func (LeveldbAuthBackend) Users added in v1.2.1

func (b LeveldbAuthBackend) Users() (us []UserData, e error)

Users returns a slice of all users.

type MongodbAuthBackend

type MongodbAuthBackend struct {
	// contains filtered or unexported fields
}

MongodbAuthBackend stores database connection information.

func NewMongodbBackend

func NewMongodbBackend(mongoURL string, database string) (b MongodbAuthBackend, e error)

NewMongodbBackend initializes a new backend. Be sure to call Close() on this to clean up the mongodb connection. Example:

backend = httpauth.MongodbAuthBackend("mongodb://127.0.0.1/", "auth")
defer backend.Close()

func (MongodbAuthBackend) Close

func (b MongodbAuthBackend) Close()

Close cleans up the backend once done with. This should be called before program exit.

func (MongodbAuthBackend) DeleteUser

func (b MongodbAuthBackend) DeleteUser(username string) error

DeleteUser removes a user. ErrNotFound is returned if the user isn't found.

func (MongodbAuthBackend) SaveUser

func (b MongodbAuthBackend) SaveUser(user UserData) error

SaveUser adds a new user, replacing if the same username is in use.

func (MongodbAuthBackend) User

func (b MongodbAuthBackend) User(username string) (user UserData, e error)

User returns the user with the given username. Error is set to ErrMissingUser if user is not found.

func (MongodbAuthBackend) Users

func (b MongodbAuthBackend) Users() (us []UserData, e error)

Users returns a slice of all users.

type Role

type Role int

Role represents an interal role. Roles are essentially a string mapped to an integer. Roles must be greater than zero.

type SqlAuthBackend

type SqlAuthBackend struct {
	// contains filtered or unexported fields
}

SqlAuthBackend database and database connection information.

func NewSqlAuthBackend

func NewSqlAuthBackend(driverName, dataSourceName string) (b SqlAuthBackend, e error)

NewSqlAuthBackend initializes a new backend by testing the database connection and making sure the storage table exists. The table is called goauth.

Returns an error if connecting to the database fails, pinging the database fails, or creating the table fails.

This uses the databases/sql package to open a connection. Its parameters should match the sql.Open function. See http://golang.org/pkg/database/sql/#Open for more information.

Be sure to import "database/sql" and your driver of choice. If you're not using sql for your own purposes, you'll need to use the underscore to import for side effects; see http://golang.org/doc/effective_go.html#blank_import.

func (SqlAuthBackend) Close

func (b SqlAuthBackend) Close()

Close cleans up the backend by terminating the database connection.

func (SqlAuthBackend) DeleteUser

func (b SqlAuthBackend) DeleteUser(username string) error

DeleteUser removes a user, raising ErrDeleteNull if that user was missing.

func (SqlAuthBackend) SaveUser

func (b SqlAuthBackend) SaveUser(user UserData) (err error)

SaveUser adds a new user, replacing one with the same username.

func (SqlAuthBackend) User

func (b SqlAuthBackend) User(username string) (user UserData, e error)

User returns the user with the given username. Error is set to ErrMissingUser if user is not found.

func (SqlAuthBackend) Users

func (b SqlAuthBackend) Users() (us []UserData, e error)

Users returns a slice of all users.

type UserData

type UserData struct {
	Username string `bson:"Username"`
	Email    string `bson:"Email"`
	Hash     []byte `bson:"Hash"`
	Role     string `bson:"Role"`
}

UserData represents a single user. It contains the users username, email, and role as well as a hash of their password. When creating users, you should not specify a hash; it will be generated in the Register and Update functions.

Directories

Path Synopsis

Jump to

Keyboard shortcuts

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