package transport import ( "strconv" "github.com/gin-gonic/gin" "github.com/geo-platform/tenant-api/internal/ops/app" "github.com/geo-platform/tenant-api/internal/shared/response" ) type createAccountRequest struct { Username string `json:"username" binding:"required"` Password string `json:"password" binding:"required"` DisplayName string `json:"display_name"` Email string `json:"email"` Role string `json:"role"` } type updateProfileRequest struct { DisplayName string `json:"display_name" binding:"required"` Email string `json:"email"` } type setStatusRequest struct { Status string `json:"status" binding:"required"` } type resetPasswordRequest struct { Password string `json:"password" binding:"required"` } type changeOwnPasswordRequest struct { OldPassword string `json:"old_password" binding:"required"` NewPassword string `json:"new_password" binding:"required"` } func listAccountsHandler(svc *app.AccountService) gin.HandlerFunc { return func(c *gin.Context) { page, _ := strconv.Atoi(c.DefaultQuery("page", "1")) size, _ := strconv.Atoi(c.DefaultQuery("size", "20")) result, err := svc.List(c.Request.Context(), app.ListInput{ Keyword: c.Query("keyword"), Status: c.Query("status"), Page: page, Size: size, }) if err != nil { response.Error(c, err) return } response.Success(c, result) } } func createAccountHandler(svc *app.AccountService) gin.HandlerFunc { return func(c *gin.Context) { var body createAccountRequest if err := c.ShouldBindJSON(&body); err != nil { response.Error(c, response.ErrBadRequest(40000, "invalid_payload", err.Error())) return } actor := actorFromGin(c) detail, err := svc.Create(c.Request.Context(), actor, app.CreateInput{ Username: body.Username, Password: body.Password, DisplayName: body.DisplayName, Email: body.Email, Role: body.Role, }) if err != nil { response.Error(c, err) return } response.Success(c, detail) } } func getAccountHandler(svc *app.AccountService) gin.HandlerFunc { return func(c *gin.Context) { id, err := parseIDParam(c) if err != nil { response.Error(c, err) return } detail, err := svc.Get(c.Request.Context(), id) if err != nil { response.Error(c, err) return } response.Success(c, detail) } } func updateAccountProfileHandler(svc *app.AccountService) gin.HandlerFunc { return func(c *gin.Context) { id, err := parseIDParam(c) if err != nil { response.Error(c, err) return } var body updateProfileRequest if err := c.ShouldBindJSON(&body); err != nil { response.Error(c, response.ErrBadRequest(40000, "invalid_payload", err.Error())) return } if err := svc.UpdateProfile(c.Request.Context(), actorFromGin(c), id, app.UpdateProfileInput{ DisplayName: body.DisplayName, Email: body.Email, }); err != nil { response.Error(c, err) return } response.Success(c, gin.H{"id": id}) } } func setAccountStatusHandler(svc *app.AccountService) gin.HandlerFunc { return func(c *gin.Context) { id, err := parseIDParam(c) if err != nil { response.Error(c, err) return } var body setStatusRequest if err := c.ShouldBindJSON(&body); err != nil { response.Error(c, response.ErrBadRequest(40000, "invalid_payload", err.Error())) return } if err := svc.SetStatus(c.Request.Context(), actorFromGin(c), id, body.Status); err != nil { response.Error(c, err) return } response.Success(c, gin.H{"id": id, "status": body.Status}) } } func resetAccountPasswordHandler(svc *app.AccountService) gin.HandlerFunc { return func(c *gin.Context) { id, err := parseIDParam(c) if err != nil { response.Error(c, err) return } var body resetPasswordRequest if err := c.ShouldBindJSON(&body); err != nil { response.Error(c, response.ErrBadRequest(40000, "invalid_payload", err.Error())) return } if err := svc.ResetPassword(c.Request.Context(), actorFromGin(c), id, body.Password); err != nil { response.Error(c, err) return } response.Success(c, gin.H{"id": id}) } } func changeOwnPasswordHandler(svc *app.AccountService) gin.HandlerFunc { return func(c *gin.Context) { var body changeOwnPasswordRequest if err := c.ShouldBindJSON(&body); err != nil { response.Error(c, response.ErrBadRequest(40000, "invalid_payload", err.Error())) return } if err := svc.ChangeOwnPassword(c.Request.Context(), actorFromGin(c), app.ChangeOwnPasswordInput{ OldPassword: body.OldPassword, NewPassword: body.NewPassword, }); err != nil { response.Error(c, err) return } response.Success(c, gin.H{"ok": true}) } } func parseIDParam(c *gin.Context) (int64, error) { idStr := c.Param("id") id, err := strconv.ParseInt(idStr, 10, 64) if err != nil || id <= 0 { return 0, response.ErrBadRequest(40001, "invalid_id", "无效的 ID") } return id, nil }