125 lines
2.9 KiB
Go
125 lines
2.9 KiB
Go
package domainservice
|
|
|
|
import (
|
|
"bbs-backend/common/errcode"
|
|
"bbs-backend/dal/dao"
|
|
"bbs-backend/dal/model"
|
|
"bbs-backend/logic/do"
|
|
"crypto/rand"
|
|
"encoding/base64"
|
|
"errors"
|
|
"golang.org/x/crypto/argon2"
|
|
"gorm.io/gorm"
|
|
)
|
|
|
|
func RegisterUserDomainService(user *model.User) error {
|
|
// 创建领域对象
|
|
userDO := &do.User{
|
|
Username: user.Username,
|
|
Email: user.Email,
|
|
Password: user.Password,
|
|
}
|
|
|
|
// 验证领域对象
|
|
if err := userDO.Validate("Username", "Email", "Password"); err != nil {
|
|
return errcode.ErrInvalidUsername
|
|
}
|
|
|
|
// 检查用户是否已存在
|
|
_, err := dao.GetUserByUsername(userDO.Username)
|
|
if err != nil && !errors.Is(err, gorm.ErrRecordNotFound) {
|
|
return errcode.ErrInternalServerError
|
|
}
|
|
|
|
// 如果用户不存在,继续注册
|
|
salt := make([]byte, 16)
|
|
_, err = rand.Read(salt)
|
|
if err != nil {
|
|
return errcode.ErrInternalServerError
|
|
}
|
|
|
|
hashedPassword := argon2.IDKey([]byte(userDO.Password), salt, 1, 64*1024, 4, 32)
|
|
user.Password = base64.StdEncoding.EncodeToString(hashedPassword)
|
|
user.Salt = base64.StdEncoding.EncodeToString(salt)
|
|
|
|
err = dao.CreateUser(user)
|
|
if err != nil {
|
|
if errors.Is(err, dao.ErrUsernameExists) {
|
|
return errcode.ErrUsernameExists
|
|
}
|
|
if errors.Is(err, dao.ErrEmailExists) {
|
|
return errcode.ErrEmailExists
|
|
}
|
|
return errcode.ErrInternalServerError
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func LoginUserDomainService(username, password string) (*model.User, error) {
|
|
// 创建领域对象
|
|
userDO := &do.User{
|
|
Username: username,
|
|
Password: password,
|
|
}
|
|
|
|
// 验证领域对象
|
|
if err := userDO.Validate("Username", "Password"); err != nil {
|
|
return nil, errcode.ErrInvalidUsername
|
|
}
|
|
|
|
// 检查用户是否存在
|
|
user, err := dao.GetUserByUsername(userDO.Username)
|
|
if err != nil {
|
|
if errors.Is(err, gorm.ErrRecordNotFound) {
|
|
return nil, errcode.ErrUserNotFound
|
|
}
|
|
return nil, errcode.ErrInternalServerError
|
|
}
|
|
|
|
salt, err := base64.StdEncoding.DecodeString(user.Salt)
|
|
if err != nil {
|
|
return nil, errcode.ErrUnauthorized
|
|
}
|
|
|
|
hashedPassword := argon2.IDKey([]byte(userDO.Password), salt, 1, 64*1024, 4, 32)
|
|
if base64.StdEncoding.EncodeToString(hashedPassword) != user.Password {
|
|
return nil, errcode.ErrUnauthorized
|
|
}
|
|
|
|
return user, nil
|
|
}
|
|
|
|
func GetUserInfoDomainService(userID uint) (*model.User, error) {
|
|
// 检查用户是否存在
|
|
user, err := dao.GetUserByID(userID)
|
|
if err != nil {
|
|
if errors.Is(err, gorm.ErrRecordNotFound) {
|
|
return nil, errcode.ErrUserNotFound
|
|
}
|
|
return nil, errcode.ErrInternalServerError
|
|
}
|
|
|
|
return user, nil
|
|
}
|
|
|
|
func UpdateUserDomainService(user *model.User, fieldsToUpdate ...string) error {
|
|
// 创建领域对象
|
|
userDO := &do.User{
|
|
Username: user.Username,
|
|
Email: user.Email,
|
|
Password: user.Password,
|
|
}
|
|
|
|
// 验证领域对象
|
|
if err := userDO.Validate(fieldsToUpdate...); err != nil {
|
|
return errcode.ErrInvalidUsername
|
|
}
|
|
|
|
err := dao.UpdateUser(user)
|
|
if err != nil {
|
|
return errcode.ErrInternalServerError
|
|
}
|
|
|
|
return nil
|
|
}
|