diff --git a/internal/common/errors.go b/internal/common/errors.go index c9793e0..61c0d7d 100644 --- a/internal/common/errors.go +++ b/internal/common/errors.go @@ -37,10 +37,11 @@ var ( ErrRegistrationDisabled = errors.New("注册功能已关闭") // 帖子相关 - ErrPostNotFound = errors.New("帖子不存在") - ErrPostCannotEdit = errors.New("当前状态不允许编辑") - ErrPostCannotSubmit = errors.New("仅草稿和已退回帖子可提交审核") - ErrPostCannotApprove = errors.New("仅待审核帖子可通过") - ErrPostCannotReject = errors.New("仅待审核和已发布帖子可退回") - ErrPostCannotUnlock = errors.New("仅锁定状态可解锁") + ErrPostNotFound = errors.New("帖子不存在") + ErrPostCannotEdit = errors.New("当前状态不允许编辑") + ErrPostCannotSubmit = errors.New("仅草稿和已退回帖子可提交审核") + ErrPostCannotApprove = errors.New("仅待审核帖子可通过") + ErrPostCannotReject = errors.New("仅待审核和已发布帖子可退回") + ErrPostCannotLock = errors.New("待审核帖子不允许锁定") + ErrPostCannotUnlock = errors.New("仅锁定状态可解锁") ) diff --git a/internal/controller/admin/admin_post_controller.go b/internal/controller/admin/admin_post_controller.go index e048305..8e488cd 100644 --- a/internal/controller/admin/admin_post_controller.go +++ b/internal/controller/admin/admin_post_controller.go @@ -117,7 +117,7 @@ func (ctrl *AdminPostController) Lock(c *gin.Context) { } if err := ctrl.postService.Lock(uint(id)); err != nil { - if errors.Is(err, common.ErrPostNotFound) { + if errors.Is(err, common.ErrPostNotFound) || errors.Is(err, common.ErrPostCannotLock) { common.Error(c, http.StatusBadRequest, err.Error()) } else { common.Error(c, http.StatusInternalServerError, "锁定失败") diff --git a/internal/controller/post_controller.go b/internal/controller/post_controller.go index 03a3fa2..2cd9f2f 100644 --- a/internal/controller/post_controller.go +++ b/internal/controller/post_controller.go @@ -139,7 +139,7 @@ func (ctrl *PostController) EditPage(c *gin.Context) { } post, err := ctrl.postService.GetByID(uint(id)) - if err != nil || post.Status == model.PostStatusPending || post.Status == model.PostStatusLocked { + if err != nil || post.Status == model.PostStatusPending || post.IsLocked { c.HTML(http.StatusNotFound, "posts/404.html", common.BuildPageData(c, gin.H{ "Title": "未找到或无法编辑", })) diff --git a/internal/model/post.go b/internal/model/post.go index 51e9285..0d51946 100644 --- a/internal/model/post.go +++ b/internal/model/post.go @@ -14,6 +14,7 @@ type Post struct { Excerpt string `gorm:"type:varchar(500)" json:"excerpt"` // plain text summary for list UserID uint `gorm:"index;not null" json:"user_id"` Status string `gorm:"type:varchar(20);index;default:draft;not null" json:"status"` + IsLocked bool `gorm:"default:false" json:"is_locked"` RejectReason string `gorm:"type:varchar(500);default:''" json:"reject_reason,omitempty"` AllowComment bool `gorm:"default:true" json:"allow_comment"` DeletedAt gorm.DeletedAt `gorm:"index" json:"-"` diff --git a/internal/service/post_service.go b/internal/service/post_service.go index 6638003..218b43a 100644 --- a/internal/service/post_service.go +++ b/internal/service/post_service.go @@ -213,7 +213,7 @@ func (s *PostService) Update(postID uint, title, body string) error { return err } - if post.Status == model.PostStatusPending || post.Status == model.PostStatusLocked { + if post.Status == model.PostStatusPending || post.IsLocked { return common.ErrPostCannotEdit } @@ -263,6 +263,7 @@ func (s *PostService) Approve(postID uint) error { } // Reject 退回:pending/approved → rejected +// 独立于锁定:可单独退回(允许作者修改后重审),也可锁定+退回(禁止再投稿) func (s *PostService) Reject(postID uint, reason string) error { post, err := s.findPost(postID) if err != nil { @@ -276,26 +277,30 @@ func (s *PostService) Reject(postID uint, reason string) error { return s.repo.Update(post) } -// Lock 锁定:任意状态 → locked(管理员可随时锁定) +// Lock 锁定:设置 IsLocked 标志,禁止编辑,不改变帖子发布状态 func (s *PostService) Lock(postID uint) error { post, err := s.findPost(postID) if err != nil { return err } - post.Status = model.PostStatusLocked + // 待审核帖子不允许锁定(审核流程中) + if post.Status == model.PostStatusPending { + return common.ErrPostCannotLock + } + post.IsLocked = true return s.repo.Update(post) } -// Unlock 解锁:locked → 草稿 +// Unlock 解锁:清除 IsLocked 标志,恢复可编辑 func (s *PostService) Unlock(postID uint) error { post, err := s.findPost(postID) if err != nil { return err } - if post.Status != model.PostStatusLocked { + if !post.IsLocked { return common.ErrPostCannotUnlock } - post.Status = model.PostStatusDraft + post.IsLocked = false return s.repo.Update(post) } diff --git a/templates/MetaLab-2026/html/posts/show.html b/templates/MetaLab-2026/html/posts/show.html index 71da54e..15a134c 100644 --- a/templates/MetaLab-2026/html/posts/show.html +++ b/templates/MetaLab-2026/html/posts/show.html @@ -13,6 +13,9 @@ {{if ne .Post.Status "approved"}} {{index $.StatusNames .Post.Status}} {{end}} + {{if .Post.IsLocked}} + 已锁定 + {{end}} @@ -27,7 +30,7 @@ {{if .IsLoggedIn}}
- {{if and $.Post (or (eq $.Post.UserID $.UID) $.CanAccessAdmin) (ne $.Post.Status "pending") (ne $.Post.Status "locked")}} + {{if and $.Post (or (eq $.Post.UserID $.UID) $.CanAccessAdmin) (ne $.Post.Status "pending") (not $.Post.IsLocked)}} 编辑 {{end}} {{if and $.Post (eq $.Post.UserID $.UID) (or (eq $.Post.Status "draft") (eq $.Post.Status "rejected"))}} diff --git a/templates/admin/html/posts/index.html b/templates/admin/html/posts/index.html index c8b30af..2b18f99 100644 --- a/templates/admin/html/posts/index.html +++ b/templates/admin/html/posts/index.html @@ -13,7 +13,6 @@ - @@ -43,7 +42,7 @@ {{.ID}} {{.Title}} {{if .AuthorName}}{{.AuthorName}}({{.UserID}}){{else}}UID{{.UserID}}{{end}} - {{index $.StatusNames .Status}} + {{index $.StatusNames .Status}}{{if .IsLocked}} 已锁定{{end}} {{.CreatedAt.Format "2006-01-02 15:04"}}
@@ -54,10 +53,10 @@ {{if eq .Status "approved"}} {{end}} - {{if and (ne .Status "locked") (ne .Status "pending")}} + {{if and (not .IsLocked) (ne .Status "pending")}} {{end}} - {{if eq .Status "locked"}} + {{if .IsLocked}} {{end}}