feat(B2): 附件引用模型-cms_attachment 增 ref_type/ref_id,消灭孤儿误报

- 实体/双 SQL 加列+idx_att_ref;upload 增 scene 白名单(banner/link/site)
- AttachmentService 新增 markUsed/release/markSiteConfigUsed(webUrl 反查,幂等)
- 未使用=articleId 与 refType 均空;page 返回 unusedCount(前后端同步改名无兼容别名)
- Banner/Link 保存先解引用再回写(换图旧图回未使用);Site 配置 logo/favicon 引用回写(@Lazy 解循环依赖)
- 新增13例(Attachment6/Banner3/Link2/Site2)+既有语义断言更新;mvn -o test 全绿
This commit is contained in:
chenxing
2026-09-07 19:40:14 +08:00
parent 52676f592a
commit b4822a7f38
15 changed files with 466 additions and 42 deletions
@@ -9,6 +9,7 @@ import org.springframework.data.jpa.repository.Query;
import org.springframework.data.repository.query.Param;
import java.util.List;
import java.util.Optional;
public interface CmsAttachmentRepository extends JpaRepository<CmsAttachment, Integer> {
@@ -19,10 +20,15 @@ public interface CmsAttachmentRepository extends JpaRepository<CmsAttachment, In
/** 编辑器图片上传时先按路径去重绑定,避免重复行 */
long countBySiteIdAndFilePath(Integer siteId, String filePath);
/** 孤儿附件(文章已删除:article_id is null) */
Page<CmsAttachment> findBySiteIdAndArticleIdIsNull(Integer siteId, Pageable pageable);
/** 未使用附件(B2 语义:无文章引用且无场景引用) */
Page<CmsAttachment> findBySiteIdAndArticleIdIsNullAndRefTypeIsNull(Integer siteId, Pageable pageable);
long countBySiteIdAndArticleIdIsNull(Integer siteId);
long countBySiteIdAndArticleIdIsNullAndRefTypeIsNull(Integer siteId);
/** 按 webUrl 反查(B2 保存点引用回写;webUrl 全站唯一由 uuid32 文件名保证,查询仍带 siteId 防御) */
Optional<CmsAttachment> findBySiteIdAndWebUrl(Integer siteId, String webUrl);
List<CmsAttachment> findByRefTypeAndRefId(String refType, Integer refId);
@Modifying
@Query("update CmsAttachment a set a.articleId = :articleId where a.id in :ids")