feat: heal dead sync channels and block deleting system default (Z12h)
Ensure default channel and rebind Agent/Binding on list, ticket, agents/me, and ensure-binding so SyncPage does not stay on deleted-channel errors. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -9,6 +9,7 @@ import (
|
||||
"aijianzhan/platform/internal/audit"
|
||||
"aijianzhan/platform/internal/authx"
|
||||
"aijianzhan/platform/internal/dbsync"
|
||||
"aijianzhan/platform/internal/logic/applogic"
|
||||
"aijianzhan/platform/internal/svc"
|
||||
|
||||
"github.com/zeromicro/go-zero/rest/httpx"
|
||||
@@ -41,7 +42,12 @@ func syncListHandler(svcCtx *svc.ServiceContext) http.HandlerFunc {
|
||||
if !requireDBSync(svcCtx, w) {
|
||||
return
|
||||
}
|
||||
list, err := svcCtx.DBSync.Store().ListChannelsByTenant(syncTenantID(r))
|
||||
tid := syncTenantID(r)
|
||||
if _, err := applogic.HealTenantSyncBind(r.Context(), svcCtx, tid); err != nil {
|
||||
// 列表仍继续,避免自愈失败挡运维
|
||||
_ = err
|
||||
}
|
||||
list, err := svcCtx.DBSync.Store().ListChannelsByTenant(tid)
|
||||
if err != nil {
|
||||
authx.WriteError(w, http.StatusBadRequest, err.Error())
|
||||
return
|
||||
@@ -109,15 +115,26 @@ func syncDeleteHandler(svcCtx *svc.ServiceContext) http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
id := pathvar.Vars(r)["id"]
|
||||
if _, err := svcCtx.DBSync.Store().GetChannelForTenant(id, syncTenantID(r)); err != nil {
|
||||
tid := syncTenantID(r)
|
||||
ch, err := svcCtx.DBSync.Store().GetChannelForTenant(id, tid)
|
||||
if err != nil {
|
||||
authx.WriteError(w, http.StatusNotFound, err.Error())
|
||||
return
|
||||
}
|
||||
// Z12h-1:公司默认同步通道禁止删除(账号落点依赖它)
|
||||
if ch.IsSystemDefault {
|
||||
authx.WriteError(w, http.StatusBadRequest, "公司默认同步通道不可删除;账号绑定落点依赖此通道。若异常请刷新页面自动修复")
|
||||
return
|
||||
}
|
||||
svcCtx.DBSync.StopChannel(id)
|
||||
if err := svcCtx.DBSync.Store().DeleteChannel(id); err != nil {
|
||||
authx.WriteError(w, http.StatusBadRequest, err.Error())
|
||||
return
|
||||
}
|
||||
// 若误删后仍有 Binding 挂死,heal 会挂回默认通道
|
||||
if _, hErr := applogic.HealTenantSyncBind(r.Context(), svcCtx, tid); hErr != nil {
|
||||
_ = hErr
|
||||
}
|
||||
httpx.OkJson(w, map[string]any{"ok": true})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@ import (
|
||||
|
||||
"aijianzhan/platform/internal/authx"
|
||||
"aijianzhan/platform/internal/dbsync"
|
||||
"aijianzhan/platform/internal/logic/applogic"
|
||||
"aijianzhan/platform/internal/svc"
|
||||
|
||||
"github.com/zeromicro/go-zero/rest/httpx"
|
||||
@@ -16,8 +17,11 @@ func syncBindingsListHandler(svcCtx *svc.ServiceContext) http.HandlerFunc {
|
||||
if !requireDBSync(svcCtx, w) {
|
||||
return
|
||||
}
|
||||
localID := r.URL.Query().Get("local_database_id")
|
||||
tid := syncTenantID(r)
|
||||
if _, err := applogic.HealTenantSyncBind(r.Context(), svcCtx, tid); err != nil {
|
||||
_ = err
|
||||
}
|
||||
localID := r.URL.Query().Get("local_database_id")
|
||||
var (
|
||||
list []dbsync.Binding
|
||||
err error
|
||||
@@ -74,6 +78,18 @@ func syncBindingsEnsureHandler(svcCtx *svc.ServiceContext) http.HandlerFunc {
|
||||
return
|
||||
}
|
||||
}
|
||||
// Z12h-2:通道空/已删 → 静默挂回公司默认同步
|
||||
needHeal := body.ChannelID == ""
|
||||
if !needHeal {
|
||||
if _, e := svcCtx.DBSync.Store().GetChannelForTenant(body.ChannelID, body.TenantID); e != nil {
|
||||
needHeal = true
|
||||
}
|
||||
}
|
||||
if needHeal {
|
||||
if healed, hErr := applogic.HealTenantSyncBind(r.Context(), svcCtx, body.TenantID); hErr == nil && healed != nil && healed.ChannelID != "" {
|
||||
body.ChannelID = healed.ChannelID
|
||||
}
|
||||
}
|
||||
saved, err := svcCtx.DBSync.Store().EnsureBinding(body)
|
||||
if err != nil {
|
||||
authx.WriteError(w, http.StatusBadRequest, err.Error())
|
||||
|
||||
Reference in New Issue
Block a user