You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

244 lines
6.3 KiB

package biz
import (
"context"
"strings"
pb "moredoc/api/v1"
"moredoc/middleware/auth"
"moredoc/model"
"moredoc/util"
"go.uber.org/zap"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
"google.golang.org/protobuf/types/known/emptypb"
"gorm.io/gorm"
)
type PunishmentAPIService struct {
pb.UnimplementedPunishmentAPIServer
dbModel *model.DBModel
logger *zap.Logger
}
func NewPunishmentAPIService(dbModel *model.DBModel, logger *zap.Logger) (service *PunishmentAPIService) {
return &PunishmentAPIService{dbModel: dbModel, logger: logger.Named("PunishmentAPIService")}
}
func (s *PunishmentAPIService) checkPermission(ctx context.Context) (userClaims *auth.UserClaims, err error) {
return checkGRPCPermission(s.dbModel, ctx)
}
func (s *PunishmentAPIService) CreatePunishment(ctx context.Context, req *pb.CreatePunishmentRequest) (*emptypb.Empty, error) {
userClaims, err := s.checkPermission(ctx)
if err != nil {
return nil, err
}
if len(req.UserId) == 0 {
return nil, status.Errorf(codes.InvalidArgument, "请选择用户")
}
if len(req.Type) == 0 {
return nil, status.Errorf(codes.InvalidArgument, "请选择处罚类型")
}
for _, userId := range req.UserId {
if userId == 1 {
continue
}
for _, typ := range req.Type {
punishment := &model.Punishment{
UserId: userId,
Type: int(typ),
Enable: req.Enable,
Reason: req.Reason,
Remark: req.Remark,
EndTime: req.EndTime,
}
s.logger.Debug("CreatePunishment", zap.Any("punishment", punishment), zap.Any("req", req))
punishment.Operators = s.dbModel.MakePunishmentOperators(userClaims.UserId, typ)
err = s.dbModel.CreatePunishment(punishment)
if err != nil {
s.logger.Error("CreatePunishment", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
}
}
return &emptypb.Empty{}, nil
}
func (s *PunishmentAPIService) UpdatePunishment(ctx context.Context, req *pb.Punishment) (*emptypb.Empty, error) {
userClaims, err := s.checkPermission(ctx)
if err != nil {
return nil, err
}
punishment := &model.Punishment{}
err = util.CopyStruct(req, punishment)
if err != nil {
s.logger.Error("CopyStruct", zap.Error(err))
return nil, status.Errorf(codes.InvalidArgument, err.Error())
}
s.logger.Debug("UpdatePunishment", zap.Any("punishment", punishment), zap.Any("req", req))
if existPunishment, _ := s.dbModel.GetPunishment(punishment.Id, "id", "operators"); existPunishment.Id > 0 {
punishment.Operators = s.dbModel.MakePunishmentOperators(userClaims.UserId, req.Type, existPunishment.Operators)
}
err = s.dbModel.UpdatePunishment(punishment)
if err != nil {
s.logger.Error("UpdatePunishment", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
return &emptypb.Empty{}, nil
}
func (s *PunishmentAPIService) GetPunishment(ctx context.Context, req *pb.GetPunishmentRequest) (*pb.Punishment, error) {
_, err := s.checkPermission(ctx)
if err != nil {
return nil, err
}
punishment, err := s.dbModel.GetPunishment(req.Id)
if err != nil {
s.logger.Error("GetPunishment", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
res := &pb.Punishment{}
err = util.CopyStruct(punishment, res)
if err != nil {
s.logger.Error("CopyStruct", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
if punishment.UserId > 0 {
user, _ := s.dbModel.GetUser(punishment.UserId, "id", "username")
if user.Id > 0 {
res.Username = user.Username
}
}
return res, nil
}
func (s *PunishmentAPIService) ListPunishment(ctx context.Context, req *pb.ListPunishmentRequest) (*pb.ListPunishmentReply, error) {
_, err := s.checkPermission(ctx)
if err != nil {
return nil, err
}
opt := &model.OptionGetPunishmentList{
Page: int(req.Page),
Size: int(req.Size_),
WithCount: true,
SelectFields: req.Field,
QueryLike: make(map[string][]interface{}),
QueryIn: make(map[string][]interface{}),
}
if len(req.UserId) > 0 {
opt.QueryIn["user_id"] = util.Slice2Interface(req.UserId)
}
if len(req.Type) > 0 {
opt.QueryIn["type"] = util.Slice2Interface(req.Type)
}
if len(req.Enable) > 0 {
opt.QueryIn["enable"] = util.Slice2Interface(req.Enable)
}
if req.Order != "" {
opt.Sort = strings.Split(req.Order, ",")
}
if req.Wd != "" {
wd := strings.TrimSpace(req.Wd)
opt.QueryLike["reason"] = []interface{}{wd}
opt.QueryLike["remark"] = []interface{}{wd}
}
data, total, err := s.dbModel.GetPunishmentList(opt)
if err != nil && err != gorm.ErrRecordNotFound {
s.logger.Error("GetPunishmentList", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
res := &pb.ListPunishmentReply{
Total: total,
}
err = util.CopyStruct(data, &res.Punishment)
if err != nil {
s.logger.Error("CopyStruct", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
if len(res.Punishment) > 0 {
var (
userIds []int64
userIdMapIndexes = make(map[int64][]int)
)
for i, v := range res.Punishment {
userIds = append(userIds, v.UserId)
userIdMapIndexes[v.UserId] = append(userIdMapIndexes[v.UserId], i)
}
users, _, _ := s.dbModel.GetUserList(&model.OptionGetUserList{
Ids: userIds,
WithCount: false,
SelectFields: []string{
"id",
"username",
},
})
for _, v := range users {
if indexes, ok := userIdMapIndexes[v.Id]; ok {
for _, index := range indexes {
res.Punishment[index].Username = v.Username
}
}
}
}
return res, nil
}
// 取消惩罚
func (s *PunishmentAPIService) CancelPunishment(ctx context.Context, req *pb.CancelPunishmentRequest) (*emptypb.Empty, error) {
userCliams, err := s.checkPermission(ctx)
if err != nil {
return nil, err
}
s.logger.Debug("CancelPunishment", zap.Any("req", req))
data, _, err := s.dbModel.GetPunishmentList(&model.OptionGetPunishmentList{
Ids: req.Id,
})
if err != nil && err != gorm.ErrRecordNotFound {
s.logger.Error("GetPunishmentList", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
for _, item := range data {
item.Enable = false
item.Operators = s.dbModel.MakePunishmentOperators(userCliams.UserId, 0, item.Operators)
err = s.dbModel.UpdatePunishment(&item, "enable", "operators")
if err != nil {
s.logger.Error("UpdatePunishment", zap.Error(err))
return nil, status.Errorf(codes.Internal, err.Error())
}
}
return &emptypb.Empty{}, nil
}