password

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

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

Go to latest
Published: Feb 13, 2016 License: Apache-2.0 Imports: 12 Imported by: 0

README

Password GoDoc Build Status

Username/password based authentication for web applications.

Installation

$ go get github.com/bentranter/password

Intro

Password provides a simple, JSON web token based authentication solution for web apps. When a user signs in to your web app, they'll receive a JSON web token in the response body. To access protected resources, they must send that token with the request.

Usage

Don't use this yet.

API Stability Guarantee

Until 1.0 is reached, API stability is not guaranteed. Once 1.0 is reached, the API will not change in backwards incompatible ways.

License

Password is licensed under the Apache v2.0 license. See the license file for more information.

Documentation

Overview

Package password implements a simple JSON web token based authentication system. It uses BoltDB as a default store for user information.

Background

The package revolves around the password.Authenticator interface. This interface implements only two methods: one for storing passwords, and one for retrieving them. This lets you use any backend to store your users, whether that be an in-memory store, Redis, Postgres, or something else altogether.

Usage

The functions defined in this library are designed to make it as easy as possible to create and authenticate users. They are all designed to be used with HTTP handlers:

// Grab the username and password from the request, and create a new user
// in the user store with those values
http.HandleFunc("/signup", func(w http.ResponseWriter, r *http.Request) {
	username := r.FormValue("Username")
	password := r.FormValue("Password")
	id, _ := password.New(username, password, UserStore)
	w.Write([]byte("New user: "+id))
})
...
// Sign in using a username and password. This will respond with a JSON web
// token if the user authenticates successfully
http.HandleFunc("/signin", func(w http.ResponseWriter, r *http.Request) {
	username := r.FormValue("Username")
	password := r.FormValue("Password")
	password.Authenticate(username, password, w, UserStore)
})
...
// Respond with the user's username. If they don't have a valid JSON web
// token, then this request will fail, saying the client is unauthorized
http.Handle("/whoami", password.Protected(
	func(ctx context.Context, w http.ResponseWriter, r *http.Request) {
		username := ctx.Value("id")
		fmt.Fprintf(w, "Your username: %s\n", username)
}))

In this example, "UserStore" would satisfy the password.Authenticator interface. For a reference implementation of this interface, see the example in the GitHub repository.

Index

Constants

This section is empty.

Variables

View Source
var (
	// ErrInvalidSigningMethod is the error returned when a token's signature
	// does match the signature used to sign the token header.
	ErrInvalidSigningMethod = errors.New("Invalid signing method")
	// ErrTokenInvalid means the signature didn't match.
	ErrTokenInvalid = errors.New("Token isn't valid")
)
View Source
var DefaultStore = newDB()

DefaultStore is the default database to store users, sessions, and CSRF tokens. It's a single BoltDB instance.

Functions

func Authenticate

func Authenticate(w http.ResponseWriter, id string, secret string, hashedSecret string)

Authenticate runs `Compare`, and writes the generated JSON web token to the response writer.

func Compare

func Compare(id string, secret string, hashedSecret string) (string, error)

Compare compares a hashed secret with a plaintext secret to see if they match. If they do, a JSON web token is generated with the given id.

func CreateUser

func CreateUser(id string, secret string) (string, error)

CreateUser creates a new user from a username/password combo

func ExpireCookie

func ExpireCookie(w http.ResponseWriter, r *http.Request)

ExpireCookie sets the expiry on the cookie. It will not send the request.

func GenToken

func GenToken(id string) (string, error)

GenToken generates a new JSON web token.

func Hash

func Hash(secret string) ([]byte, error)

Hash hashes and salts a plaintext secret using bcrypt.

func NewAuthenticatedUser

func NewAuthenticatedUser(w http.ResponseWriter, id string, secret string)

NewAuthenticatedUser creates a new user from a username/password combo, and generates a JSON web token. It writes the token in the body of the response as JSON.

func NewCookieAuthenticatedUser

func NewCookieAuthenticatedUser(w http.ResponseWriter, id string, secret string)

NewCookieAuthenticatedUser is just like NewAuthenticatedUser, but it sets a cookie on the response containing the JSON web token (instead of responding with the cookie in the body). It will not send the response!

func SetSigningKey

func SetSigningKey(key []byte)

SetSigningKey allows you to override the default HMAC signing key with one of your own. Every time this package is imported, a signing key is set randomly. That means that in between restarts, a new key is set, so you'd no longer be able to verify JSON web tokens created with that key. In order to reuse the signing key, you must set it yourself. Just call this function before creating any tokens, and you'll be good to go.

Types

type Authenticator

type Authenticator interface {
	Store(id string, secret string) (string, error)
	Retrieve(id string, secret string) (string, error)
}

Authenticator is the interface that implements the methods for storing and retrieving passwords.

type BoltSession

type BoltSession struct {
	DB         *bolt.DB
	BucketName []byte
}

BoltSession is the session DB for Bolt.

func (*BoltSession) Get

func (s *BoltSession) Get()

func (*BoltSession) New

func (s *BoltSession) New(r *http.Request)

func (*BoltSession) Save

func (s *BoltSession) Save()

type BoltUser

type BoltUser struct {
	DB         *bolt.DB
	BucketName []byte
}

BoltUser is the user DB for Bolt.

func NewBoltUserStore

func NewBoltUserStore() *BoltUser

NewBoltUserStore creates a new instance of BoltUser.

func (*BoltUser) All

func (b *BoltUser) All()

func (*BoltUser) Create

func (b *BoltUser) Create(u *User) ([]byte, error)

Create creates a new user in the DB

func (*BoltUser) Delete

func (b *BoltUser) Delete()

func (*BoltUser) Find

func (b *BoltUser) Find()

func (*BoltUser) Update

func (b *BoltUser) Update()

type CookieProtect

type CookieProtect func(ctx context.Context, w http.ResponseWriter, r *http.Request)

CookieProtect is the same as `Protect`, but it looks for the token in the `user-cookie` instead of the Authorization header. It's meant to be used with the `NewCookieAuthenticatedUser` function.

func (CookieProtect) ServeHTTP

func (fn CookieProtect) ServeHTTP(w http.ResponseWriter, r *http.Request)

type Protect

type Protect func(ctx context.Context, w http.ResponseWriter, r *http.Request)

Protect is middleware that checks to see if the incoming request has a valid JSON web token. If it does, it executes the next `http.HandlerFunc`, and passes it a `context.Context` with the field "id" assigned to the current user id.

func (Protect) ServeHTTP

func (fn Protect) ServeHTTP(w http.ResponseWriter, r *http.Request)

type RedisSession

type RedisSession struct {
	DB redis.Conn
}

RedisSession is the session DB for Redis.

func (*RedisSession) Get

func (s *RedisSession) Get()

func (*RedisSession) New

func (s *RedisSession) New(r *http.Request)

func (*RedisSession) Save

func (s *RedisSession) Save()

type RedisUser

type RedisUser struct {
	DB redis.Conn
}

RedisUser is the user DB for Redis.

func (*RedisUser) All

func (u *RedisUser) All()

func (*RedisUser) Create

func (u *RedisUser) Create()

func (*RedisUser) Delete

func (u *RedisUser) Delete()

func (*RedisUser) Find

func (u *RedisUser) Find()

func (*RedisUser) Update

func (u *RedisUser) Update()

type Session

type Session struct{}

Session represents a single session on the server.

type SessionStore

type SessionStore interface {
	Get()
	New(r *http.Request)
	Save()
}

SessionStore stores sessions in DBs

type Store

type Store struct {
	DB               *bolt.DB
	BucketName       string
	CookieBucketName string
	Bucket           *bolt.Bucket
	CookieBucket     *bolt.Bucket
}

Store contains a reference to the default store for Password, and satiesfies the Authenticator interface.

func (*Store) Retrieve

func (s *Store) Retrieve(id string, secret string) (string, error)

Retrieve retrieves the given id and secret from Bolt. It will compare the plaintext password with the hashed password.

@TODO: If the majority of DB drivers use byte slices in their drivers, switch to that. I should look at mgo, redis, gorethink, and the sql ones.

func (*Store) Store

func (s *Store) Store(id string, secret string) (string, error)

Store stores the given id and secret in Bolt. It will hash the secret using bcrypt before storing it.

type User

type User struct {
	ID          []byte
	Password    []byte
	Name        []byte
	Email       []byte
	DateCreated time.Time
	LastLogin   time.Time
	PhoneNumber []byte
}

User represents a single user

type UserStore

type UserStore interface {
	All() []*User
	Create(u *User) ([]byte, error)
	Find(id []byte) *User
	Update(id []byte) error
	Delete(id []byte) error
}

UserStore stores users in DBs

Directories

Path Synopsis

Jump to

Keyboard shortcuts

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