From dae618585726ecc98e9983a6aa1a1de2e4d24b0a Mon Sep 17 00:00:00 2001 From: Jan Bader Date: Tue, 1 Mar 2022 18:33:46 +0000 Subject: [PATCH] Prevent startup on empty secret --- cmd/budgeteer/main.go | 11 +++++++---- jwt/login.go | 24 ++++++++++++++++++------ 2 files changed, 25 insertions(+), 10 deletions(-) diff --git a/cmd/budgeteer/main.go b/cmd/budgeteer/main.go index af132b3..208d455 100644 --- a/cmd/budgeteer/main.go +++ b/cmd/budgeteer/main.go @@ -29,11 +29,14 @@ func main() { panic("couldn't open static files") } + tokenVerifier, err := jwt.NewTokenVerifier(cfg.SessionSecret) + if err != nil { + panic("couldn't create token verifier") + } + handler := &server.Handler{ - Service: queries, - TokenVerifier: &jwt.TokenVerifier{ - Secret: cfg.SessionSecret, - }, + Service: queries, + TokenVerifier: tokenVerifier, CredentialsVerifier: &bcrypt.Verifier{}, StaticFS: http.FS(static), } diff --git a/jwt/login.go b/jwt/login.go index bbb44c8..d58baef 100644 --- a/jwt/login.go +++ b/jwt/login.go @@ -11,8 +11,20 @@ import ( ) // TokenVerifier verifies Tokens. -type TokenVerifier struct { - Secret string +type tokenVerifier struct { + secret string +} + +var ErrEmptySecret = fmt.Errorf("secret is required") + +func NewTokenVerifier(secret string) (*tokenVerifier, error) { + if secret == "" { + return nil, ErrEmptySecret + } + + return &tokenVerifier{ + secret: secret, + }, nil } // Token contains everything to authenticate a user. @@ -28,7 +40,7 @@ const ( ) // CreateToken creates a new token from username and name. -func (tv *TokenVerifier) CreateToken(user *postgres.User) (string, error) { +func (tv *tokenVerifier) CreateToken(user *postgres.User) (string, error) { token := jwt.NewWithClaims(jwt.SigningMethodHS256, jwt.MapClaims{ "usr": user.Email, "name": user.Name, @@ -37,7 +49,7 @@ func (tv *TokenVerifier) CreateToken(user *postgres.User) (string, error) { }) // Generate encoded token and send it as response. - t, err := token.SignedString([]byte(tv.Secret)) + t, err := token.SignedString([]byte(tv.secret)) if err != nil { return "", fmt.Errorf("create token: %w", err) } @@ -52,12 +64,12 @@ var ( ) // VerifyToken verifys a given string-token. -func (tv *TokenVerifier) VerifyToken(tokenString string) (budgeteer.Token, error) { //nolint:ireturn +func (tv *tokenVerifier) VerifyToken(tokenString string) (budgeteer.Token, error) { //nolint:ireturn token, err := jwt.Parse(tokenString, func(token *jwt.Token) (interface{}, error) { if _, ok := token.Method.(*jwt.SigningMethodHMAC); !ok { return nil, fmt.Errorf("method '%v': %w", token.Header["alg"], ErrUnexpectedSigningMethod) } - return []byte(tv.Secret), nil + return []byte(tv.secret), nil }) if err != nil { return nil, fmt.Errorf("parse jwt: %w", err)