fix: 修复构建配置和运行时错误处理
This commit is contained in:
@@ -6,9 +6,10 @@ import (
|
||||
"errors"
|
||||
"feedsystem_video_go/internal/middleware/rabbitmq"
|
||||
"feedsystem_video_go/internal/video"
|
||||
amqp "github.com/rabbitmq/amqp091-go"
|
||||
"log"
|
||||
"time"
|
||||
|
||||
amqp "github.com/rabbitmq/amqp091-go"
|
||||
)
|
||||
|
||||
type LikeWorker struct {
|
||||
|
||||
@@ -42,6 +42,9 @@ func (w *NotificationWorker) Run(ctx context.Context) error {
|
||||
if w == nil || w.ch == nil || w.db == nil {
|
||||
return errors.New("notification worker is not initialized")
|
||||
}
|
||||
if w.queue == "" {
|
||||
return errors.New("queue is required")
|
||||
}
|
||||
if err := w.db.WithContext(ctx).AutoMigrate(&Notification{}); err != nil {
|
||||
return err
|
||||
}
|
||||
@@ -96,10 +99,12 @@ func (w *NotificationWorker) process(ctx context.Context, d amqp.Delivery) error
|
||||
return nil
|
||||
}
|
||||
var authorID uint
|
||||
w.db.WithContext(ctx).Model(&struct {
|
||||
if err := w.db.WithContext(ctx).Model(&struct {
|
||||
ID uint
|
||||
AuthorID uint
|
||||
}{}).Table("videos").Where("id = ?", evt.VideoID).Select("author_id").Scan(&authorID)
|
||||
}{}).Table("videos").Where("id = ?", evt.VideoID).Select("author_id").Scan(&authorID).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
if authorID == 0 || authorID == evt.UserID {
|
||||
return nil
|
||||
}
|
||||
@@ -114,10 +119,12 @@ func (w *NotificationWorker) process(ctx context.Context, d amqp.Delivery) error
|
||||
return nil
|
||||
}
|
||||
var authorID uint
|
||||
w.db.WithContext(ctx).Model(&struct {
|
||||
if err := w.db.WithContext(ctx).Model(&struct {
|
||||
ID uint
|
||||
AuthorID uint
|
||||
}{}).Table("videos").Where("id = ?", evt.VideoID).Select("author_id").Scan(&authorID)
|
||||
}{}).Table("videos").Where("id = ?", evt.VideoID).Select("author_id").Scan(&authorID).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
if authorID == 0 || authorID == evt.AuthorID {
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -35,7 +35,9 @@ func StartOutboxPoller(db *gorm.DB, tmq *rabbitmq.TimelineMQ) {
|
||||
err := tmq.PublishVideo(context.Background(), msg.VideoID, msg.CreateTime)
|
||||
|
||||
if err == nil {
|
||||
db.Delete(&msg)
|
||||
if err := db.Delete(&msg).Error; err != nil {
|
||||
log.Printf("删除 outbox 消息失败: id=%d, err=%v", msg.ID, err)
|
||||
}
|
||||
} else {
|
||||
log.Printf("投递MQ失败: VideoID: %d, err: %v", msg.VideoID, err)
|
||||
}
|
||||
|
||||
@@ -2,7 +2,9 @@ package worker
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"io"
|
||||
"net/http"
|
||||
"sync"
|
||||
"time"
|
||||
@@ -25,8 +27,8 @@ func NewSSEHub(db *gorm.DB) *SSEHub {
|
||||
|
||||
func (h *SSEHub) Push(userID uint, n *Notification) {
|
||||
h.mu.RLock()
|
||||
defer h.mu.RUnlock()
|
||||
chs, ok := h.clients[userID]
|
||||
h.mu.RUnlock()
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
@@ -52,13 +54,27 @@ func (h *SSEHub) Unsubscribe(userID uint, ch chan *Notification) {
|
||||
chs := h.clients[userID]
|
||||
for i, c := range chs {
|
||||
if c == ch {
|
||||
h.clients[userID] = append(chs[:i], chs[i+1:]...)
|
||||
chs = append(chs[:i], chs[i+1:]...)
|
||||
if len(chs) == 0 {
|
||||
delete(h.clients, userID)
|
||||
} else {
|
||||
h.clients[userID] = chs
|
||||
}
|
||||
close(c)
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func sseAccountID(c *gin.Context) (uint, bool) {
|
||||
accountID, ok := c.Get("accountID")
|
||||
if !ok {
|
||||
return 0, false
|
||||
}
|
||||
userID, ok := accountID.(uint)
|
||||
return userID, ok && userID != 0
|
||||
}
|
||||
|
||||
func (h *SSEHub) SSERequireAuth() gin.HandlerFunc {
|
||||
return func(c *gin.Context) {
|
||||
token := c.Query("token")
|
||||
@@ -83,8 +99,11 @@ func (h *SSEHub) SSERequireAuth() gin.HandlerFunc {
|
||||
}
|
||||
|
||||
func (h *SSEHub) SSEHandler(c *gin.Context) {
|
||||
accountID, _ := c.Get("accountID")
|
||||
userID := accountID.(uint)
|
||||
userID, ok := sseAccountID(c)
|
||||
if !ok {
|
||||
c.JSON(http.StatusUnauthorized, gin.H{"error": "invalid account"})
|
||||
return
|
||||
}
|
||||
|
||||
c.Writer.Header().Set("Content-Type", "text/event-stream")
|
||||
c.Writer.Header().Set("Cache-Control", "no-cache")
|
||||
@@ -120,8 +139,11 @@ func (h *SSEHub) SSEHandler(c *gin.Context) {
|
||||
}
|
||||
|
||||
func (h *SSEHub) ListHandler(c *gin.Context) {
|
||||
accountID, _ := c.Get("accountID")
|
||||
userID := accountID.(uint)
|
||||
userID, ok := sseAccountID(c)
|
||||
if !ok {
|
||||
c.JSON(http.StatusUnauthorized, gin.H{"error": "invalid account"})
|
||||
return
|
||||
}
|
||||
|
||||
var notifications []Notification
|
||||
if err := h.db.WithContext(c.Request.Context()).
|
||||
@@ -139,28 +161,45 @@ func (h *SSEHub) ListHandler(c *gin.Context) {
|
||||
}
|
||||
|
||||
func (h *SSEHub) MarkReadHandler(c *gin.Context) {
|
||||
accountID, _ := c.Get("accountID")
|
||||
userID := accountID.(uint)
|
||||
userID, ok := sseAccountID(c)
|
||||
if !ok {
|
||||
c.JSON(http.StatusUnauthorized, gin.H{"error": "invalid account"})
|
||||
return
|
||||
}
|
||||
|
||||
var req struct {
|
||||
ID *uint `json:"id"`
|
||||
}
|
||||
c.ShouldBindJSON(&req)
|
||||
if err := c.ShouldBindJSON(&req); err != nil && !errors.Is(err, io.EOF) {
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": err.Error()})
|
||||
return
|
||||
}
|
||||
|
||||
var err error
|
||||
if req.ID != nil {
|
||||
h.db.WithContext(c.Request.Context()).Model(&Notification{}).Where("id = ? AND recipient_id = ?", *req.ID, userID).Update("is_read", true)
|
||||
err = h.db.WithContext(c.Request.Context()).Model(&Notification{}).Where("id = ? AND recipient_id = ?", *req.ID, userID).Update("is_read", true).Error
|
||||
} else {
|
||||
h.db.WithContext(c.Request.Context()).Model(&Notification{}).Where("recipient_id = ?", userID).Update("is_read", true)
|
||||
err = h.db.WithContext(c.Request.Context()).Model(&Notification{}).Where("recipient_id = ?", userID).Update("is_read", true).Error
|
||||
}
|
||||
if err != nil {
|
||||
c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
|
||||
return
|
||||
}
|
||||
c.JSON(200, gin.H{"message": "ok"})
|
||||
}
|
||||
|
||||
func (h *SSEHub) UnreadCountHandler(c *gin.Context) {
|
||||
accountID, _ := c.Get("accountID")
|
||||
userID := accountID.(uint)
|
||||
userID, ok := sseAccountID(c)
|
||||
if !ok {
|
||||
c.JSON(http.StatusUnauthorized, gin.H{"error": "invalid account"})
|
||||
return
|
||||
}
|
||||
|
||||
var count int64
|
||||
h.db.WithContext(c.Request.Context()).Model(&Notification{}).Where("recipient_id = ? AND is_read = ?", userID, false).Count(&count)
|
||||
if err := h.db.WithContext(c.Request.Context()).Model(&Notification{}).Where("recipient_id = ? AND is_read = ?", userID, false).Count(&count).Error; err != nil {
|
||||
c.JSON(http.StatusInternalServerError, gin.H{"error": err.Error()})
|
||||
return
|
||||
}
|
||||
c.JSON(200, gin.H{"count": count})
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user