178 lines
5.0 KiB
Go
178 lines
5.0 KiB
Go
package admin
|
|
|
|
import (
|
|
"github.com/goravel/framework/contracts/http"
|
|
"github.com/spf13/cast"
|
|
|
|
apperrors "goravel/app/errors"
|
|
"goravel/app/http/helpers"
|
|
"goravel/app/http/response"
|
|
"goravel/app/models"
|
|
"goravel/app/services"
|
|
"goravel/app/utils/logger"
|
|
)
|
|
|
|
type NotificationController struct {
|
|
service services.NotificationService
|
|
}
|
|
|
|
func NewNotificationController() *NotificationController {
|
|
return &NotificationController{
|
|
service: services.NewNotificationServiceImpl(),
|
|
}
|
|
}
|
|
|
|
func (r *NotificationController) Index(ctx http.Context) http.Response {
|
|
admin := r.currentAdmin(ctx)
|
|
if admin == nil {
|
|
return response.Error(ctx, http.StatusUnauthorized, apperrors.ErrNotLoggedIn.Code)
|
|
}
|
|
|
|
page := helpers.GetIntQuery(ctx, "page", 1)
|
|
pageSize := helpers.GetIntQuery(ctx, "page_size", 10)
|
|
notifType := ctx.Request().Query("type", "")
|
|
isRead := ctx.Request().Query("is_read", "")
|
|
notifications, total, err := r.service.List(admin.ID, page, pageSize, notifType, isRead)
|
|
if err != nil {
|
|
logger.ErrorfHTTP(ctx, "list notifications error: %v", err)
|
|
return response.Error(ctx, http.StatusInternalServerError, apperrors.ErrQueryFailed.Code)
|
|
}
|
|
count, err := r.service.UnreadCount(admin.ID)
|
|
if err != nil {
|
|
logger.ErrorfHTTP(ctx, "unread count error: %v", err)
|
|
}
|
|
|
|
return response.Success(ctx, http.Json{
|
|
"notifications": notifications,
|
|
"unread_count": count,
|
|
"pagination": http.Json{
|
|
"page": page,
|
|
"page_size": pageSize,
|
|
"total": total,
|
|
"total_page": (total + int64(pageSize) - 1) / int64(pageSize),
|
|
},
|
|
})
|
|
}
|
|
|
|
func (r *NotificationController) UnreadCount(ctx http.Context) http.Response {
|
|
admin := r.currentAdmin(ctx)
|
|
if admin == nil {
|
|
return response.Error(ctx, http.StatusUnauthorized, apperrors.ErrNotLoggedIn.Code)
|
|
}
|
|
|
|
count, err := r.service.UnreadCount(admin.ID)
|
|
if err != nil {
|
|
return response.Error(ctx, http.StatusInternalServerError, apperrors.ErrQueryFailed.Code)
|
|
}
|
|
|
|
return response.Success(ctx, http.Json{
|
|
"count": count,
|
|
})
|
|
}
|
|
|
|
func (r *NotificationController) Recent(ctx http.Context) http.Response {
|
|
admin := r.currentAdmin(ctx)
|
|
if admin == nil {
|
|
return response.Error(ctx, http.StatusUnauthorized, apperrors.ErrNotLoggedIn.Code)
|
|
}
|
|
|
|
limit := helpers.GetIntQuery(ctx, "limit", 5)
|
|
notifications, err := r.service.ListRecent(admin.ID, limit)
|
|
if err != nil {
|
|
return response.Error(ctx, http.StatusInternalServerError, apperrors.ErrQueryFailed.Code)
|
|
}
|
|
|
|
count, _ := r.service.UnreadCount(admin.ID)
|
|
|
|
return response.Success(ctx, http.Json{
|
|
"notifications": notifications,
|
|
"unread_count": count,
|
|
})
|
|
}
|
|
|
|
func (r *NotificationController) MarkRead(ctx http.Context) http.Response {
|
|
admin := r.currentAdmin(ctx)
|
|
if admin == nil {
|
|
return response.Error(ctx, http.StatusUnauthorized, apperrors.ErrNotLoggedIn.Code)
|
|
}
|
|
|
|
id := helpers.GetUintRoute(ctx, "id")
|
|
if id == 0 {
|
|
return response.Error(ctx, http.StatusBadRequest, apperrors.ErrParamsRequired.Code)
|
|
}
|
|
|
|
if err := r.service.MarkRead(admin.ID, id); err != nil {
|
|
// 使用业务错误类型,直接提取错误码
|
|
if businessErr, ok := apperrors.GetBusinessError(err); ok {
|
|
return response.Error(ctx, http.StatusNotFound, businessErr.Code)
|
|
}
|
|
return response.Error(ctx, http.StatusInternalServerError, apperrors.ErrUpdateFailed.Code)
|
|
}
|
|
|
|
return response.Success(ctx, http.Json{
|
|
"id": id,
|
|
})
|
|
}
|
|
|
|
func (r *NotificationController) MarkAllRead(ctx http.Context) http.Response {
|
|
admin := r.currentAdmin(ctx)
|
|
if admin == nil {
|
|
return response.Error(ctx, http.StatusUnauthorized, apperrors.ErrNotLoggedIn.Code)
|
|
}
|
|
|
|
if err := r.service.MarkAllRead(admin.ID); err != nil {
|
|
return response.Error(ctx, http.StatusInternalServerError, apperrors.ErrUpdateFailed.Code)
|
|
}
|
|
|
|
return response.Success(ctx)
|
|
}
|
|
|
|
func (r *NotificationController) Store(ctx http.Context) http.Response {
|
|
admin := r.currentAdmin(ctx)
|
|
if admin == nil {
|
|
return response.Error(ctx, http.StatusUnauthorized, apperrors.ErrNotLoggedIn.Code)
|
|
}
|
|
|
|
title := ctx.Request().Input("title")
|
|
content := ctx.Request().Input("content")
|
|
notificationType := ctx.Request().Input("type", "announcement")
|
|
if title == "" || content == "" {
|
|
return response.Error(ctx, http.StatusBadRequest, apperrors.ErrParamsRequired.Code)
|
|
}
|
|
|
|
var receiverID *uint
|
|
receiverVal := ctx.Request().Input("receiver_id")
|
|
if receiverVal != "" {
|
|
id := cast.ToUint(receiverVal)
|
|
if id > 0 {
|
|
receiverID = &id
|
|
}
|
|
}
|
|
|
|
senderID := admin.ID
|
|
notification, err := r.service.Create(title, content, notificationType, &senderID, receiverID)
|
|
if err != nil {
|
|
return response.Error(ctx, http.StatusInternalServerError, apperrors.ErrCreateFailed.Code)
|
|
}
|
|
|
|
if notification == nil {
|
|
return response.Success(ctx)
|
|
}
|
|
|
|
return response.Success(ctx, http.Json{
|
|
"notification": notification,
|
|
})
|
|
}
|
|
|
|
func (r *NotificationController) currentAdmin(ctx http.Context) *models.Admin {
|
|
if adminValue := ctx.Value("admin"); adminValue != nil {
|
|
if admin, ok := adminValue.(models.Admin); ok {
|
|
return &admin
|
|
}
|
|
if adminPtr, ok := adminValue.(*models.Admin); ok {
|
|
return adminPtr
|
|
}
|
|
}
|
|
return nil
|
|
}
|