From fce9fc0584343e8f2bc225e11481a3b1728e6ddb Mon Sep 17 00:00:00 2001 From: MangoGovo <1749100231@qq.com> Date: Fri, 6 Dec 2024 01:52:42 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E5=AE=9E=E7=8E=B0=E4=BA=86=E6=9D=83?= =?UTF-8?q?=E7=9B=8A=E7=A0=81=E5=88=97=E8=A1=A8=E7=9A=84=E5=88=86=E9=A1=B5?= =?UTF-8?q?=E8=8E=B7=E5=8F=96,=20=E6=90=9C=E7=B4=A2,=20=E7=AD=9B=E9=80=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/qrcodeController/create.go | 6 +-- app/controllers/qrcodeController/get.go | 49 +++++++++++++++-- app/controllers/qrcodeController/getList.go | 60 +++++++++++++++++++++ app/controllers/qrcodeController/update.go | 12 ++--- app/models/qrcode.go | 26 +++++---- app/services/qrcodeService/getList.go | 42 +++++++++++++++ app/utils/database/filter.go | 14 +++++ app/utils/database/paginate.go | 18 +++++++ config/router/router.go | 4 +- 9 files changed, 206 insertions(+), 25 deletions(-) create mode 100644 app/controllers/qrcodeController/getList.go create mode 100644 app/services/qrcodeService/getList.go create mode 100644 app/utils/database/filter.go create mode 100644 app/utils/database/paginate.go diff --git a/app/controllers/qrcodeController/create.go b/app/controllers/qrcodeController/create.go index 9f3fa7f..bdf138a 100644 --- a/app/controllers/qrcodeController/create.go +++ b/app/controllers/qrcodeController/create.go @@ -9,10 +9,10 @@ import ( ) type createQrcodeData struct { - College uint `json:"college" binding:"required"` + College uint `json:"college"` Department string `json:"department" binding:"required"` - Description string `json:"description" binding:"required"` - FeedbackType uint `json:"feedback_type" binding:"required"` + Description string `json:"description"` + FeedbackType uint `json:"feedback_type"` Location string `json:"location" binding:"required"` } diff --git a/app/controllers/qrcodeController/get.go b/app/controllers/qrcodeController/get.go index 7aeb92f..b1e381f 100644 --- a/app/controllers/qrcodeController/get.go +++ b/app/controllers/qrcodeController/get.go @@ -2,8 +2,11 @@ package qrcodeController import ( "errors" + "time" "4u-go/app/apiException" + "4u-go/app/models" + "4u-go/app/services/collegeService" "4u-go/app/services/qrcodeService" "4u-go/app/utils" "github.com/gin-gonic/gin" @@ -14,6 +17,20 @@ type getQrcodeData struct { ID uint `form:"id" binding:"required"` } +type qrcodeResp struct { + ID uint `json:"id"` + CreatedAt time.Time `json:"created_at"` + FeedbackType uint `json:"feedback_type"` // 反馈类型 + College models.College `json:"college"` // 责任部门 + Department string `json:"department"` // 负责单位 + Location string `json:"location"` // 投放位置 + Status bool `json:"status"` // 状态(是否启用) + Description string `json:"description"` // 备注 + + ScanCount uint `json:"scan_count"` // 扫描次数 + FeedbackCount uint `json:"feedback_count"` // 反馈次数 +} + // GetQrcode 获取权益码信息 func GetQrcode(c *gin.Context) { var data getQrcodeData @@ -25,15 +42,41 @@ func GetQrcode(c *gin.Context) { qrcode, err := qrcodeService.GetQrcodeById(data.ID) - if errors.Is(err, gorm.ErrRecordNotFound) { - apiException.AbortWithException(c, apiException.ResourceNotFound, err) + if err != nil { + if errors.Is(err, gorm.ErrRecordNotFound) { + apiException.AbortWithException(c, apiException.ResourceNotFound, err) + } else { + apiException.AbortWithException(c, apiException.ServerError, err) + } return } + resp, err := generateResp(qrcode) if err != nil { apiException.AbortWithException(c, apiException.ServerError, err) return } - utils.JsonSuccessResponse(c, qrcode) + utils.JsonSuccessResponse(c, resp) +} + +func generateResp(qrcode models.Qrcode) (*qrcodeResp, error) { + college, err := collegeService.GetCollegeById(qrcode.College) + if err != nil { + return nil, err + } + + return &qrcodeResp{ + ID: qrcode.ID, + CreatedAt: qrcode.CreatedAt, + FeedbackType: qrcode.FeedbackType, + College: college, + Department: qrcode.Department, + Location: qrcode.Location, + ScanCount: qrcode.ScanCount, + Status: qrcode.Status, + + FeedbackCount: qrcode.FeedbackCount, + Description: qrcode.Description, + }, nil } diff --git a/app/controllers/qrcodeController/getList.go b/app/controllers/qrcodeController/getList.go new file mode 100644 index 0000000..fb4c1e0 --- /dev/null +++ b/app/controllers/qrcodeController/getList.go @@ -0,0 +1,60 @@ +package qrcodeController + +import ( + "4u-go/app/apiException" + "4u-go/app/services/qrcodeService" + "4u-go/app/utils" + "github.com/gin-gonic/gin" +) + +type filter struct { + College []uint `json:"college"` + FeedbackType []uint `json:"feedback_type"` +} + +type getListData struct { + Keyword string `json:"keyword"` + Filter filter `json:"filter"` + Page int `json:"page"` + PageSize int `json:"page_size"` +} + +type getListResponse struct { + QrcodeList []qrcodeResp `json:"qrcode_list"` + Total int64 `json:"total"` +} + +// GetList 实现了权益码列表的分页获取, 搜索, 筛选 +func GetList(c *gin.Context) { + var data getListData + err := c.ShouldBindJSON(&data) + if err != nil { + apiException.AbortWithException(c, apiException.ParamError, err) + return + } + filter := data.Filter + + qrcodeListResp := make([]qrcodeResp, 0) + + qrcodeList, total, err := qrcodeService.GetList( + filter.College, filter.FeedbackType, + data.Keyword, data.Page, data.PageSize) + if err != nil { + apiException.AbortWithException(c, apiException.ParamError, err) + return + } + + for _, qrcode := range qrcodeList { + resp, err := generateResp(qrcode) + if err != nil { + apiException.AbortWithException(c, apiException.ParamError, err) + return + } + qrcodeListResp = append(qrcodeListResp, *resp) + } + + utils.JsonSuccessResponse(c, getListResponse{ + QrcodeList: qrcodeListResp, + Total: total, + }) +} diff --git a/app/controllers/qrcodeController/update.go b/app/controllers/qrcodeController/update.go index 7a60ed7..5e164c3 100644 --- a/app/controllers/qrcodeController/update.go +++ b/app/controllers/qrcodeController/update.go @@ -29,14 +29,12 @@ func UpdateQrcode(c *gin.Context) { } qrcode, err := qrcodeService.GetQrcodeById(data.ID) - - if errors.Is(err, gorm.ErrRecordNotFound) { - apiException.AbortWithException(c, apiException.ResourceNotFound, err) - return - } - if err != nil { - apiException.AbortWithException(c, apiException.ServerError, err) + if errors.Is(err, gorm.ErrRecordNotFound) { + apiException.AbortWithException(c, apiException.ResourceNotFound, err) + } else { + apiException.AbortWithException(c, apiException.ServerError, err) + } return } diff --git a/app/models/qrcode.go b/app/models/qrcode.go index 8525b29..0b6e96f 100644 --- a/app/models/qrcode.go +++ b/app/models/qrcode.go @@ -1,6 +1,9 @@ package models -import "gorm.io/gorm" +import ( + "database/sql" + "time" +) // FeedbackType const ( @@ -20,14 +23,17 @@ const ( // Qrcode 权益码的结构体 type Qrcode struct { - gorm.Model - FeedbackType uint // 反馈类型 - College uint // 责任部门 - Department string // 负责单位 - Location string // 投放位置 - Status bool // 状态(是否启用) - Description string // 备注 + ID uint `json:"id"` + CreatedAt time.Time `json:"created_at"` + UpdatedAt time.Time `json:"-"` + DeletedAt sql.NullTime `json:"-" gorm:"index"` + FeedbackType uint `json:"feedback_type"` // 反馈类型 + College uint `json:"college"` // 责任部门 + Department string `json:"department"` // 负责单位 + Location string `json:"location"` // 投放位置 + Status bool `json:"status"` // 状态(是否启用) + Description string `json:"description"` // 备注 - ScanCount uint // 扫描次数 - FeedbackCount uint // 反馈次数 + ScanCount uint `json:"scan_count"` // 扫描次数 + FeedbackCount uint `json:"feedback_count"` // 反馈次数 } diff --git a/app/services/qrcodeService/getList.go b/app/services/qrcodeService/getList.go new file mode 100644 index 0000000..73813e3 --- /dev/null +++ b/app/services/qrcodeService/getList.go @@ -0,0 +1,42 @@ +package qrcodeService + +import ( + "4u-go/app/models" + dbUtils "4u-go/app/utils/database" + "4u-go/config/database" +) + +// GetList 获取权益码信息列表的筛选,搜索,分页 +func GetList( + collegeFilter []uint, + feedbackFilter []uint, + keyword string, + page int, pageSize int, +) (qrcodeList []models.Qrcode, total int64, err error) { + query := database.DB.Model(models.Qrcode{}) + + // 关键词搜索 + if len(keyword) > 0 { + query = query.Where("ID = ? "+ + "OR department LIKE ? "+ + "OR location LIKE ? "+ + "OR description LIKE ?", keyword, "%"+keyword+"%", "%"+keyword+"%", "%"+keyword+"%") + } + + // 筛选`责任部门` + if len(collegeFilter) > 0 { + query = query.Scopes(dbUtils.Filter("college", collegeFilter)) + } + + // 筛选`反馈类型` + if len(feedbackFilter) > 0 { + query = query.Scopes(dbUtils.Filter("feedback_type", feedbackFilter)) + } + + // 分页查找 + err = query.Count(&total). + Scopes(dbUtils.Paginate(page, pageSize)). + Find(&qrcodeList).Error + + return qrcodeList, total, err +} diff --git a/app/utils/database/filter.go b/app/utils/database/filter.go new file mode 100644 index 0000000..93d142d --- /dev/null +++ b/app/utils/database/filter.go @@ -0,0 +1,14 @@ +package database + +import "gorm.io/gorm" + +// Filter 自定义筛选插件 +// Usage: db.Scopes(dbUtils.Filter("college", [1,2,3])) +// Desc: 筛选出"college"字段为1,2,3其中之一的字段 +// +// Spec: 使用泛型以接收所有类型的切片 +func Filter[T any](name string, choices []T) func(db *gorm.DB) *gorm.DB { + return func(db *gorm.DB) *gorm.DB { + return db.Where(name+" IN (?)", choices) + } +} diff --git a/app/utils/database/paginate.go b/app/utils/database/paginate.go new file mode 100644 index 0000000..3d71a59 --- /dev/null +++ b/app/utils/database/paginate.go @@ -0,0 +1,18 @@ +package database + +import "gorm.io/gorm" + +// Paginate 自定义分页插件 +// Usage: db.Scopes(dbUtils.Paginate(page, pageSize)) +func Paginate(page int, size int) func(db *gorm.DB) *gorm.DB { + return func(db *gorm.DB) *gorm.DB { + pageSize := size + if pageSize > 20 { + pageSize = 20 + } else if pageSize <= 0 { + pageSize = 10 + } + offset := (page - 1) * pageSize + return db.Offset(offset).Limit(pageSize) + } +} diff --git a/config/router/router.go b/config/router/router.go index 1c29646..e2f5be7 100644 --- a/config/router/router.go +++ b/config/router/router.go @@ -71,9 +71,9 @@ func Init(r *gin.Engine) { { adminQrcode.PUT("/status", qrcodeController.ToggleStatus) adminQrcode.POST("", qrcodeController.CreateQrcode) - adminQrcode.DELETE("", qrcodeController.DeleteQrcode) + adminQrcode.DELETE("", midwares.CheckSuperAdmin, qrcodeController.DeleteQrcode) adminQrcode.GET("", qrcodeController.GetQrcode) - adminQrcode.GET("/list", qrcodeController.GetList) + adminQrcode.POST("/list", qrcodeController.GetList) adminQrcode.PUT("", qrcodeController.UpdateQrcode) } }