auth
auth/grant.go
Catch ErrClientNotFound. It's not a 500 error if the user specifies a Client that doesn't exist in the clientStore. That's a 400, with an error that should be rendered for the user.
| paddy@26 | 1 package auth |
| paddy@26 | 2 |
| paddy@26 | 3 import ( |
| paddy@29 | 4 "errors" |
| paddy@26 | 5 "time" |
| paddy@26 | 6 |
| paddy@45 | 7 "code.secondbit.org/uuid" |
| paddy@26 | 8 ) |
| paddy@26 | 9 |
| paddy@29 | 10 var ( |
| paddy@57 | 11 // ErrNoGrantStore is returned when a Context tries to act on a grantStore without setting one first. |
| paddy@57 | 12 ErrNoGrantStore = errors.New("no grantStore was specified for the Context") |
| paddy@57 | 13 // ErrGrantNotFound is returned when a Grant is requested but not found in the grantStore. |
| paddy@57 | 14 ErrGrantNotFound = errors.New("grant not found in grantStore") |
| paddy@57 | 15 // ErrGrantAlreadyExists is returned when a Grant is added to a grantStore, but another Grant with the |
| paddy@57 | 16 // same Code already exists in the grantStore. |
| paddy@57 | 17 ErrGrantAlreadyExists = errors.New("grant already exists in grantStore") |
| paddy@29 | 18 ) |
| paddy@29 | 19 |
| paddy@57 | 20 // Grant represents an authorization grant made by a user to a Client, to |
| paddy@57 | 21 // access user data within a defined Scope for a limited amount of time. |
| paddy@26 | 22 type Grant struct { |
| paddy@26 | 23 Code string |
| paddy@26 | 24 Created time.Time |
| paddy@26 | 25 ExpiresIn int32 |
| paddy@26 | 26 ClientID uuid.ID |
| paddy@26 | 27 Scope string |
| paddy@26 | 28 RedirectURI string |
| paddy@26 | 29 State string |
| paddy@26 | 30 } |
| paddy@26 | 31 |
| paddy@57 | 32 type grantStore interface { |
| paddy@57 | 33 getGrant(code string) (Grant, error) |
| paddy@57 | 34 saveGrant(grant Grant) error |
| paddy@57 | 35 deleteGrant(code string) error |
| paddy@26 | 36 } |
| paddy@29 | 37 |
| paddy@57 | 38 func (m *memstore) getGrant(code string) (Grant, error) { |
| paddy@29 | 39 m.grantLock.RLock() |
| paddy@29 | 40 defer m.grantLock.RUnlock() |
| paddy@29 | 41 grant, ok := m.grants[code] |
| paddy@29 | 42 if !ok { |
| paddy@29 | 43 return Grant{}, ErrGrantNotFound |
| paddy@29 | 44 } |
| paddy@29 | 45 return grant, nil |
| paddy@29 | 46 } |
| paddy@29 | 47 |
| paddy@57 | 48 func (m *memstore) saveGrant(grant Grant) error { |
| paddy@29 | 49 m.grantLock.Lock() |
| paddy@29 | 50 defer m.grantLock.Unlock() |
| paddy@29 | 51 _, ok := m.grants[grant.Code] |
| paddy@29 | 52 if ok { |
| paddy@29 | 53 return ErrGrantAlreadyExists |
| paddy@29 | 54 } |
| paddy@29 | 55 m.grants[grant.Code] = grant |
| paddy@29 | 56 return nil |
| paddy@29 | 57 } |
| paddy@29 | 58 |
| paddy@57 | 59 func (m *memstore) deleteGrant(code string) error { |
| paddy@29 | 60 m.grantLock.Lock() |
| paddy@29 | 61 defer m.grantLock.Unlock() |
| paddy@29 | 62 _, ok := m.grants[code] |
| paddy@29 | 63 if !ok { |
| paddy@29 | 64 return ErrGrantNotFound |
| paddy@29 | 65 } |
| paddy@29 | 66 delete(m.grants, code) |
| paddy@29 | 67 return nil |
| paddy@29 | 68 } |