2023-01-06 04:36:42 +03:00
|
|
|
module main
|
|
|
|
|
|
|
|
import crypto.hmac
|
|
|
|
import crypto.sha256
|
|
|
|
import crypto.bcrypt
|
|
|
|
import encoding.base64
|
|
|
|
import json
|
|
|
|
import databases
|
|
|
|
import time
|
|
|
|
|
|
|
|
struct JwtHeader {
|
|
|
|
alg string
|
|
|
|
typ string
|
|
|
|
}
|
|
|
|
|
|
|
|
struct JwtPayload {
|
|
|
|
sub string // (subject) = Entity to whom the token belongs, usually the user ID;
|
|
|
|
iss string // (issuer) = Token issuer;
|
|
|
|
exp string // (expiration) = Timestamp of when the token will expire;
|
|
|
|
iat time.Time // (issued at) = Timestamp of when the token was created;
|
|
|
|
aud string // (audience) = Token recipient, represents the application that will use it.
|
|
|
|
name string
|
|
|
|
roles string
|
|
|
|
permissions string
|
|
|
|
}
|
|
|
|
|
|
|
|
fn (mut app App) service_auth(username string, password string) !string {
|
|
|
|
mut db := databases.create_db_connection() or {
|
|
|
|
eprintln(err)
|
|
|
|
panic(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
defer {
|
2023-01-19 10:45:07 +03:00
|
|
|
db.close() or { panic(err) }
|
2023-01-06 04:36:42 +03:00
|
|
|
}
|
|
|
|
|
2023-03-22 10:48:01 +03:00
|
|
|
users := sql db {
|
|
|
|
select from User where username == username
|
2023-04-04 08:23:06 +03:00
|
|
|
}!
|
2023-03-22 10:48:01 +03:00
|
|
|
user := users.first()
|
2023-01-06 04:36:42 +03:00
|
|
|
if user.username != username {
|
|
|
|
return error('user not found')
|
|
|
|
}
|
|
|
|
|
|
|
|
if !user.active {
|
|
|
|
return error('user is not active')
|
|
|
|
}
|
|
|
|
|
|
|
|
bcrypt.compare_hash_and_password(password.bytes(), user.password.bytes()) or {
|
|
|
|
return error('Failed to auth user, ${err}')
|
|
|
|
}
|
|
|
|
|
|
|
|
token := make_token(user)
|
|
|
|
return token
|
|
|
|
}
|
|
|
|
|
|
|
|
fn make_token(user User) string {
|
|
|
|
secret := 'SECRET_KEY' // os.getenv('SECRET_KEY')
|
|
|
|
|
|
|
|
jwt_header := JwtHeader{'HS256', 'JWT'}
|
|
|
|
jwt_payload := JwtPayload{
|
|
|
|
sub: '${user.id}'
|
|
|
|
name: '${user.username}'
|
|
|
|
iat: time.now()
|
|
|
|
}
|
|
|
|
|
|
|
|
header := base64.url_encode(json.encode(jwt_header).bytes())
|
|
|
|
payload := base64.url_encode(json.encode(jwt_payload).bytes())
|
|
|
|
signature := base64.url_encode(hmac.new(secret.bytes(), '${header}.${payload}'.bytes(),
|
|
|
|
sha256.sum, sha256.block_size).bytestr().bytes())
|
|
|
|
|
|
|
|
jwt := '${header}.${payload}.${signature}'
|
|
|
|
|
|
|
|
return jwt
|
|
|
|
}
|
|
|
|
|
|
|
|
fn auth_verify(token string) bool {
|
|
|
|
if token == '' {
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
secret := 'SECRET_KEY' // os.getenv('SECRET_KEY')
|
|
|
|
token_split := token.split('.')
|
|
|
|
|
|
|
|
signature_mirror := hmac.new(secret.bytes(), '${token_split[0]}.${token_split[1]}'.bytes(),
|
|
|
|
sha256.sum, sha256.block_size).bytestr().bytes()
|
|
|
|
|
|
|
|
signature_from_token := base64.url_decode(token_split[2])
|
|
|
|
|
|
|
|
return hmac.equal(signature_from_token, signature_mirror)
|
|
|
|
// return true
|
|
|
|
}
|