More work on auth system
This commit is contained in:
parent
2afb14c4b3
commit
7d385e48de
4 changed files with 37 additions and 5 deletions
|
@ -17,5 +17,7 @@ type Authenticator struct {
|
|||
}
|
||||
|
||||
func calcAccessExpirationTimestamp() time.Time {
|
||||
// For now, the default expiration is one month after creation
|
||||
// though "never" might also be a good option
|
||||
return time.Now().Add(time.Hour * 24 * 30)
|
||||
}
|
||||
|
|
|
@ -9,4 +9,6 @@ var (
|
|||
ErrUnsupportedAuthMethod = errors.New("authentication method not supported for this user")
|
||||
ErrInvalidCombination = errors.New("invalid account and token combination")
|
||||
ErrProcessTimeout = errors.New("authentication process timed out")
|
||||
// A user may not login, for whatever reason
|
||||
ErrCantLogin = errors.New("user can't login")
|
||||
)
|
||||
|
|
|
@ -5,10 +5,12 @@ import (
|
|||
|
||||
"git.mstar.dev/mstar/goutils/other"
|
||||
"git.mstar.dev/mstar/goutils/sliceutils"
|
||||
"github.com/google/uuid"
|
||||
"golang.org/x/crypto/bcrypt"
|
||||
"gorm.io/gorm"
|
||||
"gorm.io/gorm/clause"
|
||||
|
||||
"git.mstar.dev/mstar/linstrom/storage-new"
|
||||
"git.mstar.dev/mstar/linstrom/storage-new/dbgen"
|
||||
"git.mstar.dev/mstar/linstrom/storage-new/models"
|
||||
)
|
||||
|
@ -79,8 +81,10 @@ func (a *Authenticator) StartPasswordLogin(
|
|||
username string,
|
||||
password string,
|
||||
) (nextState LoginNextState, token string, err error) {
|
||||
var acc *models.User
|
||||
acc, err = dbgen.User.Where(dbgen.User.Username.Eq(username)).First()
|
||||
if ok, err := a.canUsernameLogin(username); !ok {
|
||||
return LoginNextFailure, "", other.Error("auth", "user may not login", err)
|
||||
}
|
||||
acc, err := dbgen.User.Where(dbgen.User.Username.Eq(username)).First()
|
||||
switch err {
|
||||
case nil:
|
||||
break
|
||||
|
@ -143,10 +147,10 @@ func (a *Authenticator) StartPasswordLogin(
|
|||
loginToken := models.LoginProcessToken{
|
||||
User: *acc,
|
||||
UserId: acc.ID,
|
||||
ExpiresAt: time.Now().Add(time.Minute * 5),
|
||||
ExpiresAt: calcAccessExpirationTimestamp(),
|
||||
Token: uuid.NewString(),
|
||||
}
|
||||
err = dbgen.LoginProcessToken.Clauses(clause.OnConflict{DoNothing: true}).
|
||||
Omit(dbgen.LoginProcessToken.Token).
|
||||
err = dbgen.LoginProcessToken.Clauses(clause.OnConflict{UpdateAll: true}).
|
||||
Create(&loginToken)
|
||||
|
||||
if err != nil {
|
||||
|
@ -159,3 +163,24 @@ func (a *Authenticator) StartPasswordLogin(
|
|||
|
||||
return nextStates, loginToken.Token, nil
|
||||
}
|
||||
|
||||
func (a *Authenticator) canUsernameLogin(username string) (bool, error) {
|
||||
acc, err := dbgen.User.Where(dbgen.User.Username.Eq(username)).First()
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
if !acc.FinishedRegistration {
|
||||
return false, ErrCantLogin
|
||||
}
|
||||
|
||||
// TODO: Check roles too
|
||||
finalRole := storage.CollapseRolesIntoOne(
|
||||
sliceutils.Map(acc.Roles, func(t models.UserToRole) models.Role {
|
||||
return t.Role
|
||||
})...)
|
||||
if finalRole.CanLogin != nil && !*finalRole.CanLogin {
|
||||
return false, ErrCantLogin
|
||||
}
|
||||
|
||||
return true, nil
|
||||
}
|
||||
|
|
|
@ -15,6 +15,9 @@ import (
|
|||
)
|
||||
|
||||
func (a *Authenticator) StartPasskeyLogin(username string) (*protocol.CredentialAssertion, error) {
|
||||
if ok, err := a.canUsernameLogin(username); !ok {
|
||||
return nil, other.Error("auth", "user may not login", err)
|
||||
}
|
||||
acc, err := dbgen.User.Where(dbgen.User.Username.Eq(username)).First()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
|
Loading…
Reference in a new issue