fix: 修复客服权限与收件箱配置问题

This commit is contained in:
Rogee
2026-08-08 19:52:18 +08:00
parent dc2a6577bf
commit 518f9c5d6b
20 changed files with 385 additions and 70 deletions
@@ -2291,6 +2291,7 @@ func TestInboxHandler_List_WithDB_Cov26(t *testing.T) {
svc := service.NewInboxService(repo, agentBotInboxRepo, agentBotRepo, campaignRepo, webhookSubRepo, nil, nil)
h := NewInboxHandler(svc)
c, w := ctxCov26("GET", "/api/v1/accounts/"+uitoaCov26(acc.ID)+"/inboxes", map[string]string{"account_id": uitoaCov26(acc.ID)})
c.Set("role", "administrator")
safeCallCov26(t, "InboxList_WithDB", func() { h.List(c) })
assert.Equal(t, http.StatusOK, w.Code)
}
@@ -63,7 +63,20 @@ func (h *InboxHandler) List(c *gin.Context) {
perPage := getPageSize(c)
offset := (page - 1) * perPage
inboxes, _, svcErr := h.svc.ListByAccount(c.Request.Context(), accountID, offset, perPage)
var (
inboxes []model.Inbox
svcErr error
)
if getRole(c) == "administrator" {
inboxes, _, svcErr = h.svc.ListByAccount(c.Request.Context(), accountID, offset, perPage)
} else {
userID := getUserID(c)
if userID == 0 {
response.AbortWithStatusError(c, http.StatusUnauthorized, response.ErrUnauthorized, "current user is required")
return
}
inboxes, _, svcErr = h.svc.ListByAccountAndUser(c.Request.Context(), accountID, userID, offset, perPage)
}
if svcErr != nil {
c.JSON(http.StatusUnprocessableEntity, gin.H{"error": "failed to list inboxes"})
return
@@ -42,6 +42,48 @@ func newNilInboxHandler() *InboxHandler {
return NewInboxHandler(&service.InboxService{})
}
func setupInboxListAccessRouter(t *testing.T) (*gin.Engine, *gorm.DB, *model.Account, *model.User) {
t.Helper()
db, err := gorm.Open(sqlite.Open("file:inbox_list_access?mode=memory&cache=shared"), &gorm.Config{Logger: logger.Default.LogMode(logger.Silent)})
require.NoError(t, err)
require.NoError(t, db.AutoMigrate(&model.Account{}, &model.User{}, &model.Inbox{}, &model.InboxMember{}, &model.WorkingHour{}))
account := &model.Account{Name: "Inbox List Access", Locale: "en", Active: true}
require.NoError(t, db.Create(account).Error)
user := &model.User{Name: "Scoped Agent", Email: "handler-scoped-agent@example.com"}
require.NoError(t, db.Create(user).Error)
handler := NewInboxHandler(service.NewInboxService(repository.NewInboxRepo(db), nil, nil, nil, nil, nil, nil))
router := gin.New()
router.Use(func(c *gin.Context) {
c.Set("user_id", user.ID)
c.Set("role", "agent")
c.Next()
})
router.GET("/api/v1/accounts/:account_id/inboxes", handler.List)
return router, db, account, user
}
func TestInboxHandler_ListScopesAgentToAssignedInboxes(t *testing.T) {
router, db, account, user := setupInboxListAccessRouter(t)
assigned := &model.Inbox{AccountID: account.ID, Name: "Assigned", ChannelType: "web_widget", ChannelID: 1}
hidden := &model.Inbox{AccountID: account.ID, Name: "Hidden", ChannelType: "api", ChannelID: 2}
require.NoError(t, db.Create(assigned).Error)
require.NoError(t, db.Create(hidden).Error)
require.NoError(t, db.Create(&model.InboxMember{InboxID: assigned.ID, UserID: user.ID}).Error)
w := httptest.NewRecorder()
req := httptest.NewRequest(http.MethodGet, "/api/v1/accounts/1/inboxes", nil)
router.ServeHTTP(w, req)
require.Equal(t, http.StatusOK, w.Code, w.Body.String())
var body struct {
Payload []map[string]any `json:"payload"`
}
require.NoError(t, json.Unmarshal(w.Body.Bytes(), &body))
require.Len(t, body.Payload, 1)
assert.Equal(t, "Assigned", body.Payload[0]["name"])
}
type fakeInboxHandlerWhatsAppService struct{}
func (f *fakeInboxHandlerWhatsAppService) FetchMessageTemplates(context.Context, *channelmodel.ChannelWhatsApp) ([]interface{}, error) {