feat: add feature update user and update password
This commit is contained in:
parent
601dc1d088
commit
add86d7d83
71
dto/user.go
71
dto/user.go
|
@ -44,12 +44,13 @@ func ValidatePassword(password string) error {
|
|||
}
|
||||
|
||||
type RegisterUserInput struct {
|
||||
Username string `json:"username"`
|
||||
Name string `json:"name"`
|
||||
Email string `json:"email"`
|
||||
Phone string `json:"phone"`
|
||||
Password string `json:"password"`
|
||||
RoleId string `json:"roleId"`
|
||||
Username string `json:"username"`
|
||||
Name string `json:"name"`
|
||||
Email string `json:"email"`
|
||||
Phone string `json:"phone"`
|
||||
Password string `json:"password"`
|
||||
ConfirmPassword string `json:"confirm_password"`
|
||||
RoleId string `json:"roleId"`
|
||||
}
|
||||
|
||||
func (input *RegisterUserInput) Validate() error {
|
||||
|
@ -74,9 +75,67 @@ func (input *RegisterUserInput) Validate() error {
|
|||
return err
|
||||
}
|
||||
|
||||
if input.Password != input.ConfirmPassword {
|
||||
return errors.New("password dan confirm password tidak cocok")
|
||||
}
|
||||
|
||||
if input.RoleId == "" {
|
||||
return errors.New("roleId harus diisi")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
type UpdatePasswordInput struct {
|
||||
OldPassword string `json:"old_password"`
|
||||
NewPassword string `json:"new_password"`
|
||||
}
|
||||
|
||||
func (input *UpdatePasswordInput) Validate() error {
|
||||
|
||||
if input.OldPassword == "" {
|
||||
return errors.New("old password must be provided")
|
||||
}
|
||||
|
||||
if input.NewPassword == "" {
|
||||
return errors.New("new password must be provided")
|
||||
}
|
||||
|
||||
if len(input.NewPassword) < 8 {
|
||||
return errors.New("new password must be at least 8 characters long")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
type UpdateUserInput struct {
|
||||
Email string `json:"email"`
|
||||
Username string `json:"username"`
|
||||
Name string `json:"name"`
|
||||
Phone string `json:"phone"`
|
||||
}
|
||||
|
||||
func (input *UpdateUserInput) Validate() error {
|
||||
|
||||
if input.Email != "" {
|
||||
if err := ValidateEmail(input.Email); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
if input.Username == "" {
|
||||
return errors.New("username harus diisi")
|
||||
}
|
||||
|
||||
if input.Name == "" {
|
||||
return errors.New("name harus diisi")
|
||||
}
|
||||
|
||||
if input.Phone != "" {
|
||||
if err := ValidatePhone(input.Phone); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -11,6 +11,8 @@ func AppRouter(app *fiber.App) {
|
|||
app.Post("/login", controllers.Login)
|
||||
|
||||
app.Get("/user", middleware.AuthMiddleware, controllers.GetUserInfo)
|
||||
app.Put("/update-user", middleware.AuthMiddleware, controllers.UpdateUser)
|
||||
app.Post("/user/update-password", middleware.AuthMiddleware, controllers.UpdatePassword)
|
||||
|
||||
app.Get("/list-address", middleware.AuthMiddleware, controllers.GetListAddress)
|
||||
app.Get("/address/:id", middleware.AuthMiddleware, controllers.GetAddressByID)
|
||||
|
|
|
@ -27,9 +27,8 @@ func Register(c *fiber.Ctx) error {
|
|||
))
|
||||
}
|
||||
|
||||
err := services.RegisterUser(userInput.Username, userInput.Name, userInput.Email, userInput.Phone, userInput.Password, userInput.RoleId)
|
||||
err := services.RegisterUser(userInput.Username, userInput.Name, userInput.Email, userInput.Phone, userInput.Password, userInput.ConfirmPassword, userInput.RoleId)
|
||||
if err != nil {
|
||||
|
||||
if err.Error() == "email is already registered" {
|
||||
return c.Status(fiber.StatusConflict).JSON(utils.FormatResponse(
|
||||
fiber.StatusConflict,
|
||||
|
@ -51,6 +50,13 @@ func Register(c *fiber.Ctx) error {
|
|||
nil,
|
||||
))
|
||||
}
|
||||
if err.Error() == "password dan confirm password tidak cocok" {
|
||||
return c.Status(fiber.StatusBadRequest).JSON(utils.FormatResponse(
|
||||
fiber.StatusBadRequest,
|
||||
"Password dan confirm password tidak cocok",
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(utils.FormatResponse(
|
||||
fiber.StatusInternalServerError,
|
||||
|
@ -149,3 +155,77 @@ func GetUserInfo(c *fiber.Ctx) error {
|
|||
userResponse,
|
||||
))
|
||||
}
|
||||
|
||||
func UpdateUser(c *fiber.Ctx) error {
|
||||
var userInput dto.UpdateUserInput
|
||||
|
||||
if err := c.BodyParser(&userInput); err != nil {
|
||||
return c.Status(fiber.StatusBadRequest).JSON(utils.FormatResponse(
|
||||
fiber.StatusBadRequest,
|
||||
"Invalid input data",
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
if err := userInput.Validate(); err != nil {
|
||||
return c.Status(fiber.StatusBadRequest).JSON(utils.FormatResponse(
|
||||
fiber.StatusBadRequest,
|
||||
err.Error(),
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
userID := c.Locals("userID").(string)
|
||||
|
||||
err := services.UpdateUser(userID, userInput.Email, userInput.Username, userInput.Name, userInput.Phone)
|
||||
if err != nil {
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(utils.FormatResponse(
|
||||
fiber.StatusInternalServerError,
|
||||
err.Error(),
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
return c.Status(fiber.StatusOK).JSON(utils.FormatResponse(
|
||||
fiber.StatusOK,
|
||||
"User updated successfully",
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
func UpdatePassword(c *fiber.Ctx) error {
|
||||
var passwordInput dto.UpdatePasswordInput
|
||||
|
||||
if err := c.BodyParser(&passwordInput); err != nil {
|
||||
return c.Status(fiber.StatusBadRequest).JSON(utils.FormatResponse(
|
||||
fiber.StatusBadRequest,
|
||||
"Invalid input data",
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
if err := passwordInput.Validate(); err != nil {
|
||||
return c.Status(fiber.StatusBadRequest).JSON(utils.FormatResponse(
|
||||
fiber.StatusBadRequest,
|
||||
err.Error(),
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
userID := c.Locals("userID").(string)
|
||||
|
||||
err := services.UpdatePassword(userID, passwordInput.OldPassword, passwordInput.NewPassword)
|
||||
if err != nil {
|
||||
return c.Status(fiber.StatusInternalServerError).JSON(utils.FormatResponse(
|
||||
fiber.StatusInternalServerError,
|
||||
err.Error(),
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
||||
return c.Status(fiber.StatusOK).JSON(utils.FormatResponse(
|
||||
fiber.StatusOK,
|
||||
"Password updated successfully",
|
||||
nil,
|
||||
))
|
||||
}
|
||||
|
|
|
@ -83,3 +83,26 @@ func GetUserByID(userID string) (domain.User, error) {
|
|||
|
||||
return user, nil
|
||||
}
|
||||
|
||||
func UpdateUser(user *domain.User) error {
|
||||
if err := config.DB.Save(user).Error; err != nil {
|
||||
return errors.New("failed to save user")
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func UpdateUserPassword(userID, newPassword string) error {
|
||||
var user domain.User
|
||||
|
||||
if err := config.DB.Where("id = ?", userID).First(&user).Error; err != nil {
|
||||
return errors.New("user not found")
|
||||
}
|
||||
|
||||
user.Password = newPassword
|
||||
|
||||
if err := config.DB.Save(&user).Error; err != nil {
|
||||
return errors.New("failed to update password")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -11,7 +11,10 @@ import (
|
|||
"golang.org/x/crypto/bcrypt"
|
||||
)
|
||||
|
||||
func RegisterUser(username, name, email, phone, password, roleId string) error {
|
||||
func RegisterUser(username, name, email, phone, password, confirmPassword, roleId string) error {
|
||||
if password != confirmPassword {
|
||||
return errors.New("password dan confirm password tidak cocok")
|
||||
}
|
||||
|
||||
if repositories.IsEmailExist(email) {
|
||||
return errors.New("email is already registered")
|
||||
|
@ -46,7 +49,8 @@ func LoginUser(emailOrUsername, password string) (string, error) {
|
|||
return "", errors.New("invalid email/username or password")
|
||||
}
|
||||
|
||||
if err := bcrypt.CompareHashAndPassword([]byte(user.Password), []byte(password)); err != nil {
|
||||
err = bcrypt.CompareHashAndPassword([]byte(user.Password), []byte(password))
|
||||
if err != nil {
|
||||
return "", errors.New("invalid email/username or password")
|
||||
}
|
||||
|
||||
|
@ -78,3 +82,68 @@ func GetUserByID(userID string) (domain.User, error) {
|
|||
}
|
||||
return user, nil
|
||||
}
|
||||
|
||||
func UpdateUser(userID, email, username, name, phone string) error {
|
||||
|
||||
user, err := repositories.GetUserByID(userID)
|
||||
if err != nil {
|
||||
return errors.New("user not found")
|
||||
}
|
||||
|
||||
if email != "" && email != user.Email && repositories.IsEmailExist(email) {
|
||||
return errors.New("email is already registered")
|
||||
}
|
||||
|
||||
if username != "" && username != user.Username && repositories.IsUsernameExist(username) {
|
||||
return errors.New("username is already registered")
|
||||
}
|
||||
|
||||
if phone != "" && phone != user.Phone && repositories.IsPhoneExist(phone) {
|
||||
return errors.New("phone number is already registered")
|
||||
}
|
||||
|
||||
if email != "" {
|
||||
user.Email = email
|
||||
}
|
||||
if username != "" {
|
||||
user.Username = username
|
||||
}
|
||||
if name != "" {
|
||||
user.Name = name
|
||||
}
|
||||
if phone != "" {
|
||||
user.Phone = phone
|
||||
}
|
||||
|
||||
err = repositories.UpdateUser(&user)
|
||||
if err != nil {
|
||||
return errors.New("failed to update user")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func UpdatePassword(userID, oldPassword, newPassword string) error {
|
||||
|
||||
user, err := repositories.GetUserByID(userID)
|
||||
if err != nil {
|
||||
return errors.New("user not found")
|
||||
}
|
||||
|
||||
err = bcrypt.CompareHashAndPassword([]byte(user.Password), []byte(oldPassword))
|
||||
if err != nil {
|
||||
return errors.New("old password is incorrect")
|
||||
}
|
||||
|
||||
hashedPassword, err := bcrypt.GenerateFromPassword([]byte(newPassword), bcrypt.DefaultCost)
|
||||
if err != nil {
|
||||
return errors.New("failed to hash new password")
|
||||
}
|
||||
|
||||
err = repositories.UpdateUserPassword(userID, string(hashedPassword))
|
||||
if err != nil {
|
||||
return errors.New("failed to update password")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue