批量更新,增加用户管理

This commit is contained in:
2025-11-01 17:57:34 +08:00
parent 186dcb86d9
commit bfba8d7ad6
28 changed files with 2307 additions and 2377 deletions
+11 -390
View File
@@ -2,9 +2,10 @@ package controllers
import (
"encoding/json"
"fmt"
"server/models"
"time"
"github.com/beego/beego/v2/client/orm"
beego "github.com/beego/beego/v2/server/web"
)
@@ -16,16 +17,16 @@ type AuthController struct {
beego.Controller
}
// Login 处理登录请求(支持租户模式,使用租户名称)
// Login 处理登录请求
func (c *AuthController) Login() {
var username, password, tenantName string
// 优先尝试从URL参数获取Apifox测试方式)
// 优先尝试从URL参数获取
username = c.GetString("username")
password = c.GetString("password")
tenantName = c.GetString("tenant_name")
// 如果URL参数为空,尝试从JSON请求体获取(前端方式)
// 如果URL参数为空,尝试从JSON请求体获取
if username == "" || password == "" || tenantName == "" {
var loginData struct {
Username string `json:"username"`
@@ -60,28 +61,17 @@ func (c *AuthController) Login() {
return
}
// 添加日志调试
fmt.Println("接收到的登录请求:")
fmt.Println("用户名:", username)
fmt.Println("租户名称:", tenantName)
// 验证用户(先验证租户,再验证租户下的用户)
fmt.Println("开始验证用户:", username, "租户:", tenantName)
user, err := models.ValidateUser(username, password, tenantName)
fmt.Println("验证结果:", err)
if user != nil {
fmt.Println("用户信息:ID=", user.Id, "Username=", user.Username, "TenantId=", user.TenantId)
}
if err != nil {
// 登录失败
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": err.Error(),
"data": nil,
}
} else {
// 使用models包中的GenerateToken函数生成token(包含租户ID
// 使用models包中的GenerateToken函数生成token
tokenString, err := models.GenerateToken(user.Id, user.Username, user.TenantId)
if err != nil {
@@ -91,7 +81,11 @@ func (c *AuthController) Login() {
"data": nil,
}
} else {
// 登录成功
// 登录成功,写当前时间到last_login_time,并增加login_count
loginTime := time.Now()
o := orm.NewOrm()
_, _ = o.Raw("UPDATE yz_users SET last_login_time = ?, login_count = IFNULL(login_count,0)+1 WHERE id = ?", loginTime, user.Id).Exec()
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "登录成功",
@@ -114,85 +108,6 @@ func (c *AuthController) Login() {
c.ServeJSON()
}
// ResetPassword 重置用户密码(支持租户模式)
func (c *AuthController) ResetPassword() {
// 获取请求参数
username := c.GetString("username")
superPassword := c.GetString("superPassword")
tenantId, _ := c.GetInt("tenant_id", 0)
// 如果URL参数中没有租户ID,尝试从JSON请求体获取
if tenantId == 0 {
var resetData struct {
Username string `json:"username"`
SuperPassword string `json:"superPassword"`
TenantId int `json:"tenant_id"`
}
if err := json.Unmarshal(c.Ctx.Input.RequestBody, &resetData); err == nil {
username = resetData.Username
superPassword = resetData.SuperPassword
tenantId = resetData.TenantId
}
}
if tenantId <= 0 {
c.Data["json"] = map[string]interface{}{"success": false, "message": "租户ID不能为空"}
c.ServeJSON()
return
}
// 调用模型方法
err := models.ResetPassword(username, superPassword, tenantId)
if err != nil {
c.Data["json"] = map[string]interface{}{"success": false, "message": err.Error()}
} else {
c.Data["json"] = map[string]interface{}{"success": true, "message": "密码重置成功"}
}
c.ServeJSON()
}
// ChangePassword 修改用户密码(支持租户模式)
func (c *AuthController) ChangePassword() {
// 获取请求参数
username := c.GetString("username")
oldPassword := c.GetString("oldPassword")
newPassword := c.GetString("newPassword")
tenantId, _ := c.GetInt("tenant_id", 0)
// 如果URL参数中没有租户ID,尝试从JSON请求体获取
if tenantId == 0 {
var changeData struct {
Username string `json:"username"`
OldPassword string `json:"oldPassword"`
NewPassword string `json:"newPassword"`
TenantId int `json:"tenant_id"`
}
if err := json.Unmarshal(c.Ctx.Input.RequestBody, &changeData); err == nil {
username = changeData.Username
oldPassword = changeData.OldPassword
newPassword = changeData.NewPassword
tenantId = changeData.TenantId
}
}
if tenantId <= 0 {
c.Data["json"] = map[string]interface{}{"success": false, "message": "租户ID不能为空"}
c.ServeJSON()
return
}
// 调用模型方法
err := models.ChangePassword(username, oldPassword, newPassword, tenantId)
if err != nil {
c.Data["json"] = map[string]interface{}{"success": false, "message": err.Error()}
} else {
c.Data["json"] = map[string]interface{}{"success": true, "message": "密码修改成功"}
}
c.ServeJSON()
}
// Logout 处理登出请求
func (c *AuthController) Logout() {
// 在实际应用中,这里需要处理JWT或Session的清除
@@ -202,297 +117,3 @@ func (c *AuthController) Logout() {
}
c.ServeJSON()
}
// FindAllUsers 获取所有用户(支持按租户过滤)
func (c *AuthController) FindAllUsers() {
// 从查询参数获取租户ID(可选)
tenantId, _ := c.GetInt("tenant_id", 0)
users := models.FindAllUsers(tenantId)
c.Data["json"] = map[string]interface{}{
"success": true,
"message": "获取用户列表成功",
"data": users,
}
c.ServeJSON()
}
// GetUserByUsername 通过用户名查询用户信息(支持租户模式)
func (c *AuthController) GetUserByUsername() {
// 获取请求参数中的用户名和租户ID
username := c.GetString("username")
tenantId, _ := c.GetInt("tenant_id", 0)
if username == "" {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户名不能为空",
"data": nil,
}
c.ServeJSON()
return
}
if tenantId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "租户ID不能为空",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法查询用户
user, err := models.GetUserByUsername(username, tenantId)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "查询用户失败: " + err.Error(),
"data": nil,
}
} else if user == nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户不存在",
"data": nil,
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "查询成功",
"data": map[string]interface{}{
"id": user.Id,
"username": user.Username,
"email": user.Email,
"avatar": user.Avatar,
"nickname": user.Nickname,
"tenant_id": user.TenantId,
},
}
}
c.ServeJSON()
}
// AddUser 添加新用户(支持租户模式)
func (c *AuthController) AddUser() {
// 定义接收用户数据的结构体(与JSON请求体对应)
var userData struct {
Username string `json:"username"`
Password string `json:"password"`
Email string `json:"email"`
Nickname string `json:"nickname"`
Avatar string `json:"avatar"`
TenantId int `json:"tenant_id"`
}
// 解析请求体JSON数据
err := json.Unmarshal(c.Ctx.Input.RequestBody, &userData)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "请求参数格式错误: " + err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
// 校验必要参数
if userData.Username == "" {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户名不能为空",
"data": nil,
}
c.ServeJSON()
return
}
if userData.Password == "" {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "密码不能为空",
"data": nil,
}
c.ServeJSON()
return
}
if userData.TenantId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "租户ID不能为空",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法添加用户(传递参数,接收新用户对象)
newUser, err := models.AddUser(
userData.Username,
userData.Password,
userData.Email,
userData.Nickname,
userData.Avatar,
userData.TenantId,
)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "添加用户失败: " + err.Error(),
"data": nil,
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "用户添加成功",
"data": map[string]interface{}{
"id": newUser.Id,
"username": newUser.Username,
"email": newUser.Email,
"nickname": newUser.Nickname,
"avatar": newUser.Avatar,
"tenant_id": newUser.TenantId,
},
}
}
c.ServeJSON()
}
// UpdateUser 更新用户信息(支持租户模式)
func (c *AuthController) UpdateUser() {
// 定义接收更新数据的结构体
var updateData struct {
Id int `json:"id"` // 必须包含用户ID,用于定位要更新的用户
Username string `json:"username"` // 可选更新字段
Email string `json:"email"` // 可选更新字段
Nickname string `json:"nickname"` // 可选更新字段
Avatar string `json:"avatar"` // 可选更新字段
TenantId int `json:"tenant_id"` // 必须包含租户ID,用于验证用户归属
}
// 解析请求体JSON
err := json.Unmarshal(c.Ctx.Input.RequestBody, &updateData)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "请求参数格式错误: " + err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
// 校验必要参数(用户ID和租户ID不能为空)
if updateData.Id == 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户ID不能为空",
"data": nil,
}
c.ServeJSON()
return
}
if updateData.TenantId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "租户ID不能为空",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法更新用户
updatedUser, err := models.UpdateUser(
updateData.Id,
updateData.Username,
updateData.Email,
updateData.Nickname,
updateData.Avatar,
updateData.TenantId,
)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "更新用户失败: " + err.Error(),
"data": nil,
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "用户更新成功",
"data": map[string]interface{}{
"id": updatedUser.Id,
"username": updatedUser.Username,
"email": updatedUser.Email,
"nickname": updatedUser.Nickname,
"avatar": updatedUser.Avatar,
"tenant_id": updatedUser.TenantId,
},
}
}
c.ServeJSON()
}
// DeleteUser 删除用户(支持租户模式)
func (c *AuthController) DeleteUser() {
// 获取要删除的用户ID和租户ID(从URL参数或请求体中获取)
userId, err := c.GetInt("id") // 从URL参数获取,如 /user?id=1
tenantId, _ := c.GetInt("tenant_id", 0)
if err != nil || tenantId == 0 {
// 若URL参数获取失败,尝试从JSON请求体获取
var deleteData struct {
Id int `json:"id"`
TenantId int `json:"tenant_id"`
}
if err := json.Unmarshal(c.Ctx.Input.RequestBody, &deleteData); err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户ID或租户ID获取失败: " + err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
userId = deleteData.Id
tenantId = deleteData.TenantId
}
// 校验用户ID和租户ID
if userId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "无效的用户ID",
"data": nil,
}
c.ServeJSON()
return
}
if tenantId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "租户ID不能为空",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法删除用户
err = models.DeleteUser(userId, tenantId)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "删除用户失败: " + err.Error(),
"data": nil,
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "用户删除成功",
"data": nil,
}
}
c.ServeJSON()
}
+363
View File
@@ -0,0 +1,363 @@
package controllers
import (
"encoding/json"
"server/models"
"github.com/beego/beego/v2/server/web"
)
type UserController struct {
web.Controller
}
// GetAllUsers 获取所有用户
func (c *UserController) GetAllUsers() {
tenantId, _ := c.GetInt("tenant_id", 0)
users := models.GetAllUsers(tenantId)
userList := make([]map[string]interface{}, 0)
for _, user := range users {
userList = append(userList, map[string]interface{}{
"id": user.Id,
"username": user.Username,
"email": user.Email,
"avatar": user.Avatar,
"nickname": user.Nickname,
"tenant_id": user.TenantId,
"lastLoginTime": user.LastLoginTime,
})
}
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "获取用户列表成功",
"data": userList,
}
c.ServeJSON()
}
// ChangePassword 修改用户密码
func (c *UserController) ChangePassword() {
// 从URL获取用户ID
userId, err := c.GetInt(":id")
if err != nil || userId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户ID无效",
"data": nil,
}
c.ServeJSON()
return
}
// 解析请求参数
var changeData struct {
OldPassword string `json:"oldPassword"`
NewPassword string `json:"newPassword"`
}
err = json.Unmarshal(c.Ctx.Input.RequestBody, &changeData)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "请求参数格式错误: " + err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
// 校验参数
if changeData.OldPassword == "" || changeData.NewPassword == "" {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "旧密码和新密码不能为空",
"data": nil,
}
c.ServeJSON()
return
}
// 先获取用户信息
user, err := models.GetUserInfo(userId, "", 0)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型方法修改密码
err = models.ChangePassword(user.Username, changeData.OldPassword, changeData.NewPassword, user.TenantId)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": err.Error(),
"data": nil,
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "密码修改成功",
"data": nil,
}
}
c.ServeJSON()
}
// GetUserInfo 通过ID查询用户信息
func (c *UserController) GetUserInfo() {
// 从URL获取用户ID
userId, err := c.GetInt(":id")
if err != nil || userId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户ID无效",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法根据ID查询
user, err := models.GetUserInfo(userId, "", 0)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "查询成功",
"data": map[string]interface{}{
"id": user.Id,
"username": user.Username,
"email": user.Email,
"avatar": user.Avatar,
"nickname": user.Nickname,
"tenant_id": user.TenantId,
},
}
c.ServeJSON()
}
// AddUser 添加新用户
func (c *UserController) AddUser() {
// 定义接收用户数据的结构体
var userData struct {
Username string `json:"username"`
Password string `json:"password"`
Email string `json:"email"`
Nickname string `json:"nickname"`
Avatar string `json:"avatar"`
TenantId int `json:"tenant_id"`
}
// 解析请求体JSON数据
err := json.Unmarshal(c.Ctx.Input.RequestBody, &userData)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "请求参数格式错误: " + err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
// 校验必要参数
if userData.Username == "" {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户名不能为空",
"data": nil,
}
c.ServeJSON()
return
}
if userData.Password == "" {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "密码不能为空",
"data": nil,
}
c.ServeJSON()
return
}
if userData.TenantId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "租户ID不能为空",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法添加用户(传递参数,接收新用户对象)
newUser, err := models.AddUser(
userData.Username,
userData.Password,
userData.Email,
userData.Nickname,
userData.Avatar,
userData.TenantId,
)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "添加用户失败: " + err.Error(),
"data": nil,
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "用户添加成功",
"data": map[string]interface{}{
"id": newUser.Id,
"username": newUser.Username,
"email": newUser.Email,
"nickname": newUser.Nickname,
"avatar": newUser.Avatar,
"tenant_id": newUser.TenantId,
},
}
}
c.ServeJSON()
}
// EditUser 更新用户信息
func (c *UserController) EditUser() {
// 定义接收更新数据的结构体
var updateData struct {
Id int `json:"id"`
Username string `json:"username"`
Email string `json:"email"`
Nickname string `json:"nickname"`
Avatar string `json:"avatar"`
}
// 解析请求体JSON
err := json.Unmarshal(c.Ctx.Input.RequestBody, &updateData)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "请求参数格式错误: " + err.Error(),
"data": nil,
}
c.ServeJSON()
return
}
// 校验必要参数
if updateData.Id == 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "用户ID不能为空",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法更新用户
_, err = models.EditUser(
updateData.Id,
updateData.Username,
updateData.Email,
updateData.Nickname,
updateData.Avatar,
)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "更新用户失败: " + err.Error(),
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "用户更新成功",
}
}
c.ServeJSON()
}
// DeleteUser 删除用户
func (c *UserController) DeleteUser() {
// 从URL获取用户ID
userId, err := c.GetInt(":id")
if err != nil || userId <= 0 {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "无效的用户ID",
"data": nil,
}
c.ServeJSON()
return
}
// 调用模型层方法删除用户
err = models.DeleteUser(userId)
if err != nil {
c.Data["json"] = map[string]interface{}{
"code": 1,
"message": "删除用户失败: " + err.Error(),
"data": nil,
}
} else {
c.Data["json"] = map[string]interface{}{
"code": 0,
"message": "用户删除成功",
"data": nil,
}
}
c.ServeJSON()
}
// ResetPassword 重置用户密码(支持租户模式)
func (c *UserController) ResetPassword() {
// 获取请求参数
username := c.GetString("username")
superPassword := c.GetString("superPassword")
tenantId, _ := c.GetInt("tenant_id", 0)
// 如果URL参数中没有租户ID,尝试从JSON请求体获取
if tenantId == 0 {
var resetData struct {
Username string `json:"username"`
SuperPassword string `json:"superPassword"`
TenantId int `json:"tenant_id"`
}
if err := json.Unmarshal(c.Ctx.Input.RequestBody, &resetData); err == nil {
username = resetData.Username
superPassword = resetData.SuperPassword
tenantId = resetData.TenantId
}
}
if tenantId <= 0 {
c.Data["json"] = map[string]interface{}{"success": false, "message": "租户ID不能为空"}
c.ServeJSON()
return
}
// 调用模型方法
err := models.ResetPassword(username, superPassword, tenantId)
if err != nil {
c.Data["json"] = map[string]interface{}{"success": false, "message": err.Error()}
} else {
c.Data["json"] = map[string]interface{}{"success": true, "message": "密码重置成功"}
}
c.ServeJSON()
}
+62 -51
View File
@@ -5,6 +5,7 @@ import (
"encoding/base64"
"errors"
"fmt"
"time"
"github.com/beego/beego/v2/client/orm"
"golang.org/x/crypto/scrypt"
@@ -13,16 +14,18 @@ import (
_ "github.com/go-sql-driver/mysql"
)
// User 用户模型,增加Salt字段存储每个用户的唯一盐值
// User 用户模型
type User struct {
Id int `orm:"auto"`
TenantId int `orm:"column(tenant_id);default(0)" json:"tenant_id"` // 租户ID
Username string // 用户名不再全局唯一,而是在租户内唯一(tenant_id + username 的组合唯一)
Password string // 存储加密后的密码
Salt string // 存储该用户的唯一盐值
Email string
Avatar string
Nickname string // 昵称字段,与数据库表中的列名匹配
Id int `orm:"auto"`
TenantId int `orm:"column(tenant_id);default(0)" json:"tenant_id"`
Username string
Password string
Salt string
Email string
Avatar string
Nickname string
DeleteTime *time.Time `orm:"column(delete_time);null;type(datetime)" json:"delete_time"`
LastLoginTime *time.Time `orm:"column(last_login_time);null;type(datetime)" json:"last_login_time"`
}
// TableName 设置表名,默认为yz_users
@@ -67,14 +70,14 @@ func verifyPassword(password, salt, storedHash string) bool {
return hash == storedHash
}
// ResetPassword 重置用户密码(支持租户模式)
// ResetPassword 重置用户密码
func ResetPassword(username, superPassword string, tenantId int) error {
if superPassword != "Lzq920103" {
return fmt.Errorf("超级密码错误")
}
o := orm.NewOrm()
user, err := GetUserByUsername(username, tenantId)
user, err := GetUserInfo(0, username, tenantId)
if err != nil {
return fmt.Errorf("用户不存在: %v", err)
}
@@ -102,9 +105,9 @@ func ResetPassword(username, superPassword string, tenantId int) error {
return nil
}
// ChangePassword 修改用户密码(支持租户模式)
// ChangePassword 修改用户密码
func ChangePassword(username, oldPassword, newPassword string, tenantId int) error {
user, err := GetUserByUsername(username, tenantId)
user, err := GetUserInfo(0, username, tenantId)
if err != nil {
return err
}
@@ -124,8 +127,8 @@ func ChangePassword(username, oldPassword, newPassword string, tenantId int) err
return err
}
// FindAllUsers 获取所有用户(支持按租户过滤)
func FindAllUsers(tenantId int) []*User {
// GetAllUsers 获取所有用户
func GetAllUsers(tenantId int) []*User {
o := orm.NewOrm()
var users []*User
if tenantId > 0 {
@@ -144,23 +147,36 @@ func FindAllUsers(tenantId int) []*User {
return users
}
// GetUserByUsername 根据用户名获取用户(支持租户隔离)
func GetUserByUsername(username string, tenantId int) (*User, error) {
// GetUserInfo 根据用户ID或用户名获取用户
func GetUserInfo(userId int, username string, tenantId int) (*User, error) {
o := orm.NewOrm()
user := &User{}
// 使用原生 SQL 查询,考虑租户ID
err := o.Raw("SELECT * FROM yz_users WHERE username = ? AND tenant_id = ?", username, tenantId).QueryRow(user)
if err == orm.ErrNoRows {
return nil, errors.New("用户不存在")
}
if err != nil {
return nil, err
var err error
if userId > 0 {
// 按ID查询
user.Id = userId
err = o.Read(user)
if err == orm.ErrNoRows {
return nil, errors.New("用户不存在")
}
if err != nil {
return nil, err
}
} else {
// 按用户名和租户ID查询
err = o.Raw("SELECT * FROM yz_users WHERE username = ? AND tenant_id = ?", username, tenantId).QueryRow(user)
if err == orm.ErrNoRows {
return nil, errors.New("用户不存在")
}
if err != nil {
return nil, err
}
}
return user, nil
}
// ValidateUser 验证用户登录信息(支持租户模式,根据租户名称)
// 先验证租户是否存在且有效,再验证租户下的用户
// ValidateUser 验证用户登录信息
func ValidateUser(username, password string, tenantName string) (*User, error) {
o := orm.NewOrm()
@@ -179,12 +195,6 @@ func ValidateUser(username, password string, tenantName string) (*User, error) {
return nil, fmt.Errorf("查询租户失败: %v", err)
}
// 检查租户是否被删除(软删除)
if tenant.DeleteTime != nil {
// delete_time 不为 NULL,说明已被删除
return nil, errors.New("租户已被删除")
}
// 检查租户状态
if tenant.Status == "disabled" {
return nil, errors.New("租户已被禁用")
@@ -197,7 +207,7 @@ func ValidateUser(username, password string, tenantName string) (*User, error) {
tenantId := tenant.Id
// 2. 获取租户下的用户
user, err := GetUserByUsername(username, tenantId)
user, err := GetUserInfo(0, username, tenantId)
if err != nil {
// 用户不存在或查询失败
return nil, err
@@ -210,7 +220,7 @@ func ValidateUser(username, password string, tenantName string) (*User, error) {
return nil, errors.New("密码不正确")
}
// AddUser 向数据库添加新用户(模型层核心方法,支持租户模式)
// AddUser 向数据库添加新用户
func AddUser(username, password, email, nickname, avatar string, tenantId int) (*User, error) {
// 1. 验证租户是否存在且有效
o := orm.NewOrm()
@@ -224,7 +234,7 @@ func AddUser(username, password, email, nickname, avatar string, tenantId int) (
}
// 2. 检查该租户下用户是否已存在(避免用户名重复,但不同租户可以有相同的用户名)
existingUser, err := GetUserByUsername(username, tenantId)
existingUser, err := GetUserInfo(0, username, tenantId)
if err == nil && existingUser != nil {
return nil, fmt.Errorf("该租户下用户名已存在")
}
@@ -265,23 +275,23 @@ func AddUser(username, password, email, nickname, avatar string, tenantId int) (
return user, nil
}
// UpdateUser 更新用户信息(模型层方法,支持租户模式)
func UpdateUser(id int, username, email, nickname, avatar string, tenantId int) (*User, error) {
// 1. 根据ID和租户ID查询用户是否存在(确保只能更新自己租户下的用户)
// EditUser 更新用户信息
func EditUser(id int, username, email, nickname, avatar string) (*User, error) {
// 根据ID查询用户
o := orm.NewOrm()
user := &User{}
err := o.Raw("SELECT * FROM yz_users WHERE id = ? AND tenant_id = ?", id, tenantId).QueryRow(user)
err := o.Raw("SELECT * FROM yz_users WHERE id = ?", id).QueryRow(user)
if err == orm.ErrNoRows {
return nil, fmt.Errorf("用户不存在或不属于该租户")
return nil, fmt.Errorf("用户不存在")
}
if err != nil {
return nil, fmt.Errorf("查询用户失败: %v", err)
}
// 2. 仅更新非空字段(避免覆盖原有值)
// 仅更新非空字段(避免覆盖原有值)
if username != "" {
// 若更新用户名,需检查同一租户下新用户名是否已被占用
existingUser, _ := GetUserByUsername(username, tenantId)
existingUser, _ := GetUserInfo(0, username, user.TenantId)
if existingUser != nil && existingUser.Id != id {
return nil, fmt.Errorf("该租户下用户名已被占用")
}
@@ -297,7 +307,7 @@ func UpdateUser(id int, username, email, nickname, avatar string, tenantId int)
user.Avatar = avatar
}
// 3. 执行数据库更新
// 执行数据库更新
_, err = o.Update(user)
if err != nil {
return nil, fmt.Errorf("数据库更新失败: %v", err)
@@ -306,23 +316,24 @@ func UpdateUser(id int, username, email, nickname, avatar string, tenantId int)
return user, nil
}
// DeleteUser 根据ID删除用户(模型层方法,支持租户模式)
func DeleteUser(id int, tenantId int) error {
// DeleteUser 根据ID进行软删除
func DeleteUser(id int) error {
o := orm.NewOrm()
// 先查询用户是否存在且属于指定租户
user := &User{}
err := o.Raw("SELECT * FROM yz_users WHERE id = ? AND tenant_id = ?", id, tenantId).QueryRow(user)
err := o.Raw("SELECT * FROM yz_users WHERE id = ?", id).QueryRow(user)
if err == orm.ErrNoRows {
return fmt.Errorf("用户不存在或不属于该租户")
return fmt.Errorf("用户不存在")
}
if err != nil {
return fmt.Errorf("查询用户失败: %v", err)
}
// 执行删除操作
_, err = o.Delete(user)
// 设置删除时间为当前时间(软删除)
now := time.Now()
user.DeleteTime = &now
_, err = o.Update(user, "DeleteTime")
if err != nil {
return fmt.Errorf("数据库删除失败: %v", err)
return fmt.Errorf("设置删除时间失败: %v", err)
}
return nil
}
+8 -7
View File
@@ -56,17 +56,17 @@ func init() {
beego.Router("/admin", &controllers.AdminController{})
//用户相关
beego.Router("/api/users", &controllers.AuthController{}, "get:FindAllUsers")
beego.Router("/api/users/:id", &controllers.AuthController{}, "get:GetUserByUsername")
beego.Router("/api/users", &controllers.AuthController{}, "post:AddUser")
beego.Router("/api/users/:id", &controllers.AuthController{}, "put:UpdateUser")
beego.Router("/api/users/:id", &controllers.AuthController{}, "delete:DeleteUser")
beego.Router("/api/allUsers", &controllers.UserController{}, "get:GetAllUsers")
beego.Router("/api/user/:id", &controllers.UserController{}, "get:GetUserInfo")
beego.Router("/api/addUser", &controllers.UserController{}, "post:AddUser")
beego.Router("/api/editUser/:id", &controllers.UserController{}, "post:EditUser")
beego.Router("/api/deleteUser/:id", &controllers.UserController{}, "delete:DeleteUser")
beego.Router("/api/changePassword/:id", &controllers.UserController{}, "post:ChangePassword")
beego.Router("/api/reset-password", &controllers.UserController{}, "post:ResetPassword")
// 认证路由
beego.Router("/api/login", &controllers.AuthController{}, "post:Login")
beego.Router("/api/logout", &controllers.AuthController{}, "post:Logout")
beego.Router("/api/reset-password", &controllers.AuthController{}, "post:ResetPassword")
beego.Router("/api/change-password", &controllers.AuthController{}, "post:ChangePassword")
// 手动配置菜单路由以匹配前台的 API 路径
beego.Router("/api/menu", &controllers.MenuController{}, "post:CreateMenu")
@@ -114,4 +114,5 @@ func init() {
beego.Router("/api/program-categories/public", &controllers.ProgramCategoryController{}, "get:GetProgramCategoriesPublic")
beego.Router("/api/program-infos/public", &controllers.ProgramInfoController{}, "get:GetProgramInfosPublic")
beego.Router("/api/files/public", &controllers.FileController{}, "get:GetFilesPublic")
}