add: update handling

This commit is contained in:
$(pass /github/name)
2024-09-20 08:29:00 +02:00
parent 62624cd0f8
commit 00facf8758
4 changed files with 406 additions and 157 deletions

View File

@@ -1,17 +1,18 @@
package controllers
import (
"fmt"
"GoMembership/internal/config"
"GoMembership/internal/constants"
"GoMembership/internal/middlewares"
"GoMembership/internal/models"
"GoMembership/internal/services"
"GoMembership/internal/utils"
"net/http"
"github.com/gin-gonic/gin"
"GoMembership/pkg/errors"
"GoMembership/pkg/logger"
)
@@ -27,12 +28,80 @@ type RegistrationData struct {
User models.User `json:"user"`
}
func (uc *UserController) CurrentUserHandler(c *gin.Context) {
userIDString, ok := c.Get("user_id")
if !ok || userIDString == nil {
logger.Error.Printf("Error getting user_id from header")
func (uc *UserController) UpdateHandler(c *gin.Context) {
var user models.User
if err := c.ShouldBindJSON(&user); err != nil {
logger.Error.Printf("Couldn't decode input: %v", err)
c.JSON(http.StatusBadRequest, gin.H{"error": "Couldn't decode request data"})
return
}
userID := userIDString.(float64)
tokenString, err := c.Cookie("jwt")
if err != nil {
logger.Error.Printf("No Auth token: %v\n", err)
c.JSON(http.StatusUnauthorized, gin.H{"error": "No Auth token"})
c.Abort()
return
}
_, claims, err := middlewares.ExtractContentFrom(tokenString)
if err != nil {
logger.Error.Printf("Error retrieving token and claims from JWT")
c.JSON(http.StatusInternalServerError, gin.H{"error": "JWT parsing error"})
return
}
jwtUserID := int64((*claims)["user_id"].(float64))
userRole := int8((*claims)["role_id"].(float64))
if user.ID == 0 {
logger.Error.Printf("No User.ID in request from user with id: %v, aborting", jwtUserID)
c.JSON(http.StatusBadRequest, gin.H{"error": "No user id provided"})
return
}
if user.ID != jwtUserID && userRole < constants.Roles.Editor {
c.JSON(http.StatusForbidden, gin.H{"error": "You are not authorized to update this user"})
return
}
// TODO: If it's not an admin, prevent changes to critical fields
// if userRole != constants.Roles.Admin {
// existingUser, err := uc.Service.GetUserByID(jwtUserID)
// if err != nil {
// c.JSON(http.StatusInternalServerError, gin.H{"error": "Error retrieving user data"})
// return
// }
// user.Email = existingUser.Email
// user.RoleID = existingUser.RoleID
// }
updatedUser, err := uc.Service.UpdateUser(&user)
if err != nil {
switch err {
case errors.ErrUserNotFound:
c.JSON(http.StatusNotFound, gin.H{"error": "User not found"})
case errors.ErrInvalidUserData:
c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid user data"})
default:
logger.Error.Printf("Failed to update user: %v", err)
c.JSON(http.StatusInternalServerError, gin.H{"error": "Internal Server error"})
}
return
}
c.JSON(http.StatusAccepted, gin.H{"message": "User updated successfully", "user": updatedUser})
}
func (uc *UserController) CurrentUserHandler(c *gin.Context) {
userIDInterface, ok := c.Get("user_id")
if !ok || userIDInterface == nil {
logger.Error.Printf("Error getting user_id from header")
c.JSON(http.StatusInternalServerError, gin.H{"error": "Missing or invalid user ID type"})
return
}
userID, ok := userIDInterface.(int64)
if !ok {
logger.Error.Printf("Error: user_id is not of type int64")
c.JSON(http.StatusInternalServerError, gin.H{"error": "Invalid user ID type"})
return
}
user, err := uc.Service.GetUserByID(int64(userID))
if err != nil {
logger.Error.Printf("Error retrieving valid user: %v", err)
@@ -44,7 +113,13 @@ func (uc *UserController) CurrentUserHandler(c *gin.Context) {
}
func (uc *UserController) LogoutHandler(c *gin.Context) {
// just clear the JWT cookie
tokenString, err := c.Cookie("jwt")
if err != nil {
logger.Error.Printf("unable to get token from cookie: %#v", err)
}
middlewares.InvalidateSession(tokenString)
c.SetCookie("jwt", "", -1, "/", "", true, true)
c.JSON(http.StatusOK, gin.H{"message": "Logged out successfully"})
}
@@ -82,25 +157,17 @@ func (uc *UserController) LoginHandler(c *gin.Context) {
return
}
token, err := middlewares.GenerateToken(user.ID)
logger.Error.Printf("jwtsevret: %v", config.Auth.JWTSecret)
token, err := middlewares.GenerateToken(config.Auth.JWTSecret, user, "")
if err != nil {
c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to generate JWT token"})
return
}
c.SetCookie(
"jwt",
token,
10*60, // 10 minutes
"/",
"",
true,
true,
)
utils.SetCookie(c, token)
c.JSON(http.StatusOK, gin.H{
"message": "Login successful",
"set-token": token,
"message": "Login successful",
})
}
@@ -118,7 +185,7 @@ func (uc *UserController) RegisterUser(c *gin.Context) {
c.JSON(http.StatusNotAcceptable, gin.H{"error": "No subscription model provided"})
return
}
logger.Error.Printf("user.membership: %#v", regData.User.Membership)
selectedModel, err := uc.MembershipService.GetModelByName(&regData.User.Membership.SubscriptionModel.Name)
if err != nil {
logger.Error.Printf("%v:No subscription model found: %#v", regData.User.Email, err)
@@ -134,7 +201,7 @@ func (uc *UserController) RegisterUser(c *gin.Context) {
id, token, err := uc.Service.RegisterUser(&regData.User)
if err != nil {
logger.Error.Printf("Couldn't register User(%v): %v", regData.User.Email, err)
c.JSON(int(id), gin.H{"error": fmt.Sprintf("Couldn't register User: %v", err)})
c.JSON(int(id), gin.H{"error": "Couldn't register User"})
return
}
regData.User.ID = id
@@ -194,7 +261,7 @@ func (uc *UserController) VerifyMailHandler(c *gin.Context) {
c.HTML(http.StatusUnauthorized, "verification_error.html", gin.H{"ErrorMessage": "Emailadresse wurde schon bestätigt. Sollte dies nicht der Fall sein, wende Dich bitte an info@carsharing-hasloh.de."})
return
}
logger.Info.Printf("User: %#v", user)
logger.Info.Printf("VerificationMailHandler User: %#v", user.Email)
uc.EmailService.SendWelcomeEmail(user)
c.HTML(http.StatusOK, "verification_success.html", gin.H{"FirstName": user.FirstName})