@focus-reactive/payload-plugin-comments

中文文档
1.11.3发布于 2026/10/12MITTypeScriptES Module构建来源已验证近 30 天下载 4.8万

npm

中文使用文档
文档目录30 节
  1. 目录
  2. AI 整合提示
  3. UI 屏幕截图
  4. 全球评论小组
  5. 文件评论小组
  6. 字段注释弹出
  7. 外地标签按钮——两个国家
  8. 特征
  9. 先决条件
  10. 安装
  11. 设置
  12. 1. 将插件添加到您的有效载荷配置中
  13. 2. 导入样式
  14. 3. 重新生成导入地图
  15. 4. 创建和管理移徙
  16. 配置
  17. CommentsPluginConfig
  18. CollectionEntry
  19. usernameFieldPath
  20. TenantPluginConfig
  21. 收藏覆盖
  22. 翻译
  23. 环境变量
  24. 电子邮件通知要求
  25. 结构概览
  26. 如何运作
  27. 参考文献
  28. 可用的脚本
  29. 捐款
  30. 许可证

@ 焦点反应/ payload- plugin- comments

npm

协作评论插件 有效载荷CMS v3. 在有效载荷管理员面板上添加一个全功能的注释系统——支持文档级别和字段级别对收藏和全局的评论,@mentions同时带有电子邮件通知,注释解析,多版本,以及本地化意识过滤.

目录


AI 整合提示

复制并粘贴此提示到您的 AI 助手( Cursor, Claude等) 中, 将插件整合到已有的 Biveload v3 工程中 .

I want to add a collaborative commenting system to my Payload CMS v3 project using @focus-reactive/payload-plugin-comments.

## How it works

The plugin injects into every collection and global:
- A field-level comment badge on every field label — shows comment count, opens a popup to post
- A document-level comments drawer (sidebar) scoped to the current document
- A global comments panel (header button) listing all comments across every document and global

Comments are stored in an auto-generated `comments` collection (hidden from the sidebar). Each comment records:
- documentId / collectionSlug / globalSlug — what it belongs to
- fieldPath — dot-notation field path (null = document-level)
- locale — for field-level comments (null = shown in all locales)
- text — may contain @(userId) mention tokens
- author, mentions, isResolved, resolvedBy, resolvedAt
- tenant (optional, when multi-tenancy is enabled)

@mentions use autocomplete from the users collection. Mentioned users receive email notifications via Resend.
Comments are automatically deleted when their parent document is deleted.

## Installation

pnpm add @focus-reactive/payload-plugin-comments

## Step 1 — Register the plugin in payload.config.ts

import { buildConfig } from 'payload'
import { commentsPlugin } from '@focus-reactive/payload-plugin-comments'

export default buildConfig({
  plugins: [
    commentsPlugin({
      // Optional: specify which field to use as document title in the UI
      collections: [
        { slug: 'pages', titleField: 'title' },
        { slug: 'products', titleField: 'name' },
      ],
      // Optional: customize the display name field on users
      usernameFieldPath: 'name', // default
    }),
  ],
})

## Step 2 — Import the stylesheet

In your global CSS or admin layout:

@import "@focus-reactive/payload-plugin-comments/styles.css";

Or in a TypeScript/JS file:

import "@focus-reactive/payload-plugin-comments/styles.css";

## Step 3 — Regenerate the import map

Run this after adding the plugin so Payload registers the plugin's admin components:

npx payload generate:importmap

(Or the equivalent for your package manager: pnpm payload generate:importmap / bunx payload generate:importmap)
If you skip this step the comment badges, drawer, and header button will not appear in the admin UI.

## Step 4 — Create and run a migration (SQL adapters only)

The plugin adds a `comments` collection to your database. If you use PostgreSQL or SQLite, create and apply a migration:

npx payload migrate:create create_comments
npx payload migrate

Skip this step if you use the MongoDB adapter.

## Optional: Multi-tenancy

commentsPlugin({
  tenant: {
    enabled: true,
    collectionSlug: 'tenants',       // default
    documentTenantField: 'tenant',   // default
  },
})

## Optional: Collection overrides

commentsPlugin({
  overrides: {
    access: { /* custom access control */ },
    fields: (defaultFields) => [...defaultFields],
    hooks: {
      afterChange: [async ({ doc }) => { /* ... */ }],
    },
  },
})

## Environment variables (for email notifications)

RESEND_API_KEY=re_xxxxxxxxxxxxxxxx
[email protected]

## Important notes

- All collections and globals automatically get field-level comments — `collections` config only sets UI metadata (titleField).
- Comments on globals use globalSlug instead of collectionSlug/documentId.
- Field-level comments are locale-scoped; document-level comments show in all locales.
- The `comments` collection is hidden from the admin sidebar by default.
- Auto-cleanup: when a document is deleted, all its comments are deleted too.
- usernameFieldPath supports dot-notation (e.g. "profile.displayName").
- If RESEND_FROM_EMAIL is not set, mention emails are silently skipped.

UI 屏幕截图

全球评论小组

在“有效载荷”管理员中,一个标题按钮打开一个抽屉,列出每个文件和收藏中的所有注释.

Global comments panel

文件评论小组

在查看一个文件时,一个侧面面板会用过滤标签显示该文件的所有评论(打开/解决/提及我).

Document comments panel

字段注释弹出

点击字段标签上的注释徽章打开弹出符,您可以写出并发布该特定字段的新注释.

Field comment popup

外地标签按钮——两个国家

嵌入于字段标签中的评论按钮有两个可视状态:没有评论(不活动,出现在悬浮上)和一个或多个可公开的评论(活性,显示计数徽章).

不活动( 无评论)活动( 有评论)
Field label button — inactiveField label button — active

特征

  • 文件级评论 - 将任何文件的评论留在任何汇编或全局
  • 外地一级的评论 ——直接对单个字段进行注释;字段标签显示带有注释计数的徽章
  • 全球支助 ——外地一级和文件一级对有效载荷全球的评论工作,而不仅仅是收集
  • @mention 用户 - 在注释中提及其他用户时使用 @name 自动补全
  • 电子邮件通知 - 被提及用户通过电子邮件收到通知 重新发送
  • 解析注释 - 将评论意见标为已解决/未解决;通过打开、解决或提及过滤
  • 全球评论小组 – 一个页眉按钮打开一个抽屉,显示所有文档和全局的所有注释
  • 乐观 UI ——在服务器确认前立即出现评论
  • 多重租赁 - 通过下列方式对租户提出范围意见: @payloadcms/plugin-multi-tenant
  • 地方意识 – 外地一级的注释被绑入一个地块;在所有地块中都显示文档级别的评论
  • 自动清理 ——当其母文档被删除时,注释会被自动删除
  • i18n/ 翻译 ——所有UI字符串都是可转换的;在内置的英语默认值的同时,将您自己的语言域覆盖

先决条件


安装

pnpm add @focus-reactive/payload-plugin-comments
npm install @focus-reactive/payload-plugin-comments
# or
yarn add @focus-reactive/payload-plugin-comments

同伴依赖性 : payload ^3.0.0, (中文(简体) ), @payloadcms/ui ^3.0.0。 。 。 . next ^14 || ^15, (中文(简体) ), react ^18 || ^19, (中文(简体) ), react-dom,以及 @payloadcms/plugin-multi-tenant 是可选的.


设置

1. 将插件添加到您的有效载荷配置中

// payload.config.ts
import { buildConfig } from "payload";
import { commentsPlugin } from "@focus-reactive/payload-plugin-comments";

export default buildConfig({
  plugins: [
    commentsPlugin({
      // Optional: customize which field is used as the document title in the UI
      collections: [
        { slug: "pages", titleField: "title" },
        { slug: "products", titleField: "name" },
      ],
    }),
  ],
  // ... rest of your config
});

2. 导入样式

将插件的样式表添加到您的全局 CSS 或管理版式 :

/* global CSS */
@import "@focus-reactive/payload-plugin-comments/styles.css";

或导入到布局/ 页面文件中 :

import "@focus-reactive/payload-plugin-comments/styles.css";

3. 重新生成导入地图

当您添加或删除注册管理员组件的插件时, 有效载荷需要重新生成其导入地图 。 运行 :

npx payload generate:importmap

此命令不管您的软件包管理器如何有效( Namenpm, (中文(简体) ), pnpm, (中文(简体) ), yarn, (中文(简体) ), bun) (中文(简体) ). 或者对您的软件包管理器使用等效:

pnpm payload generate:importmap
# yarn payload generate:importmap
# bunx payload generate:importmap

如果您跳过此步骤, 插件的管理员组件( 注释徽章、 抽屉、 标题按钮) 将不会出现在 有效载荷管理员 UI 中 .

4. 创建和管理移徙

插件添加一个 comments 收藏到数据库。 如果您使用 SQL 适配器( PostgreSQL, SQLite), 请创建并应用迁移 :

npx payload migrate:create create_comments
npx payload migrate

如果您使用 MongoDB 适配器, 请跳过此步骤 .


配置

这个 commentsPlugin 工厂接受可选 CommentsPluginConfig 对象 :

commentsPlugin(config?: CommentsPluginConfig)

CommentsPluginConfig

选项类型默认说明
collectionsCollectionEntry[]—— 说用于收藏的UI元数据(标题字段). 所有集合都会收到评论.
enabledbooleantrue设定为 false 完全禁用插件
tenantTenantPluginConfig—— 说多租赁设置(见下文)
overridesCollectionOverrides—— 说自定义生成 comments 收藏
translationsTranslations—— 说覆盖每个地方的 UI 字符串(见下文)
usernameFieldPathstring"name"用户收藏中显示名称字段的点注释路径

CollectionEntry

每个条目 collections 是一个为特定集合提供UI元数据的对象 :

interface CollectionEntry {
  slug: string;
  titleField?: string; // Field used as document title in the UI. Default: "id"
}

说明: 您不需要列出每个收藏 。 所有集合(和所有全局)自动支持注释. 这个 collections 数组只设置显示像标题字段这样的元数据.

实例:

commentsPlugin({
  collections: [
    { slug: "pages", titleField: "title" },
    { slug: "products", titleField: "name" },
  ],
});

usernameFieldPath

指定在 users 库被用作注释 UI 和 @mention 自动完成中的显示名 。 支持嵌入地的点注释.

commentsPlugin({
  usernameFieldPath: "name", // default
  // usernameFieldPath: "firstName",
  // usernameFieldPath: "profile.displayName",
});

TenantPluginConfig

使用时配置多租赁 @payloadcms/plugin-multi-tenant数字 :

选项类型默认说明
enabledbooleanfalse启用租户范围界定
collectionSlugstring"tenants"租户的积蓄
documentTenantFieldstring"tenant"存有租户参考文献的栏目

示例

commentsPlugin({
  tenant: {
    enabled: true,
    collectionSlug: "tenants",
    documentTenantField: "tenant",
  },
});

收藏覆盖

使用 overrides 以自定义生成 comments 收藏——例如,用于扩展访问控制或添加自定义字段:

commentsPlugin({
  overrides: {
    access: {
      // Override the default "authenticated only" access
    },
    fields: (defaultFields) => [...defaultFields],
    hooks: {
      afterChange: [
        async ({ doc }) => {
          console.log("Comment changed:", doc.id);
        },
      ],
    },
  },
});

翻译

使用 translations 以覆盖一个或多个地方的任意 UI 字符串。 每个密钥都是一个地块代码;该值是一个部分对象 CommentsTranslations 形状 —— 您省略的密钥会回到内置的英语默认值.

commentsPlugin({
  translations: {
    fr: {
      label: "Commentaires",
      add: "Ajouter un commentaire",
      writeComment: "Écrire un commentaire",
      comment: "Commenter",
      cancel: "Annuler",
      resolve: "Résoudre",
      reopen: "Rouvrir",
      delete: "Supprimer",
      filterOpen: "Ouverts",
      filterResolved: "Résolus",
      filterMentioned: "Me mentionnent",
    },
  },
});

所有可变键( 带有英语默认值):

密钥默认(英文)
label"Comments"
openComments_one"{{count}} open comment"
openComments_other"{{count}} open comments"
add"Add comment"
writeComment"Write a comment"
comment"Comment"
cancel"Cancel"
posting"Posting…"
resolve"Resolve"
reopen"Reopen"
delete"Delete"
general"General"
close"Close"
syncingComments"Syncing comments"
openCommentsAria"Open comments"
failedToPost"Failed to post comment"
failedToUpdate"Failed to update comment"
failedToDelete"Failed to delete comment"
failedToAdd"Failed to add comment"
unknownAuthor"Unknown"
deletedUser"Deleted user"
noOpenComments"No open comments"
noResolvedComments"No resolved comments"
noMentionedComments"No comments mentioning you"
filterOpen"Open"
filterResolved"Resolved"
filterMentioned"Mentioned me"
noMentionMatches"No matches"

这个 CommentsTranslations 类型是从软件包中导出,以便输入翻译对象:

import type { CommentsTranslations } from "@focus-reactive/payload-plugin-comments";

const myTranslations: Record<string, Partial<CommentsTranslations>> = {
  fr: { label: "Commentaires" },
  de: { label: "Kommentare" },
};

commentsPlugin({ translations: myTranslations });

环境变量

电子邮件通知要求

变量说明示例
RESEND_API_KEY您重新发送 API 密钥re_xxxxxxxxxxxxxxxx
RESEND_FROM_EMAIL发送者电子邮件地址以获取引用通知[email protected]

若为 RESEND_FROM_EMAIL 未设置, 请提及电子邮件通知被悄悄跳过, 错误会被登录到控制台上 .

.env. 本地实例:

RESEND_API_KEY=re_xxxxxxxxxxxxxxxx
[email protected]

结构概览

如何运作

插件初始化 (单位:千美元)plugin.ts:

  1. 插件收到一个 CommentsPluginConfig 返回标准有效载荷 Plugin 函数.
  2. 它创造了一个 comments 收藏(默认从管理员边栏中隐藏).
  3. 补丁 每个收藏 输入 FieldCommentLabel 输入每个字段的管理标签并登记一个 afterDelete 键入删除文档时的级联删除注释.
  4. 补丁 每个全球 输入 FieldCommentLabel 输入每个字段的管理员标签.
  5. 它登记行政提供者(CommentsProviderWrapper)和一个管理行动(CommentsHeaderButton) (中文(简体) ).
  6. 它将REST的终点登记在以下 /api/comments-plugin/* (列表,创建,删除,解析,标记读取,不读取-计数,可引用用户,文档标题,字段标签). 每个都需要一个经过认证的用户,并使用请求中的“有效载荷”实例,因此它工作在一个刚开始的无服务器实例上.

数据加载 (单位:千美元)src/api:

  • 管理员UI从插件的端点获取注释、文档标题、可引用用户、字段标签和未读引用数.
  • 突变(添加,删除,解析,标记为已读)调用相同的端点并乐观地更新查询缓存.

国家管理 (单位:千美元)CommentsProvider:

  • 持有 allComments 在反应状态下,有乐观的更新通过 useOptimistic。 。 。 .
  • visibleComments 来源:根据下个.js过滤到当前文档/收集/全球/本地 pathname。 。 。 .
  • 展览 addComment, (中文(简体) ), removeComment, (中文(简体) ), resolveComment,以及 syncComments 变相.

外地一级的评论 (单位:千美元)FieldCommentLabel:

  • 插件覆盖 Label 用于每个已配置的集合和全局中每个指定字段的组件.
  • 标签从上下文读取注释并用字段路径过滤出,显示带有计数的徽章.
  • 点击徽章打开预滚动到该字段评论组的评论抽屉.

注释集计划 :

外地类型说明
documentId编号正在被评论的文件的编号( 以全局为单位)
collectionSlug文本收藏的块块( 不包括全局评论)
globalSlug文本有效载荷全球屏障( 用于收集文件注释的空白)
fieldPath文本字段的点注释路径( null = 文档级别)
locale文本注释的语系( null = 在所有语系中显示)
text文本区域注释正文( 可包含 @(userId) 提及符号)
mentions数组 − 关系本评论中提到的用户
author− 用户注释作者( 自动设置)
isResolved复选框评论是否解决
resolvedBy− 用户谁解决的
resolvedAt日期当它解决
tenant关系(可选)租户范围(在允许多租房时)

参考文献

导入路径出口
@focus-reactive/payload-plugin-commentscommentsPlugin, (中文(简体) ), CommentsPluginConfig (类型), CommentsTranslations (类型)
@focus-reactive/payload-plugin-comments/styles.css插件样式表( 已编译的 CSS)

可用的脚本

从工程根中运行这些 pnpm数字 :

命令说明
pnpm build构建插件到 dist/ (Tsup + Tailwind CSS 微调)
pnpm dev在监视模式下构建——在文件更改中重建
pnpm lintLint + 检查格式 (Ultracite: oxlint + oxfmt)
pnpm lint:fixLint + 固定,包括格式化(Ultracite)
pnpm format格式文件( Ultracite: oxfmt)
pnpm format:check检查格式而不写入

捐款

  1. 叉出寄存器并创建一个特性分支.
  2. 安装依赖性 : pnpm install
  3. 启动建筑监视器 : pnpm dev
  4. 更改您在 src/。 。 。 .
  5. 运行 pnpm lint 财务报告和审定财务报表 pnpm format:check 在提交之前.
  6. 打开拉动请求 main。 。 。 .

许可证

麻省理工学院 焦点反应

版本与发布记录

@focus-reactive/payload-plugin-comments 共发布 22 个版本,首次发布于 2026/03/18;过去 12 个月发布了 22 个版本。最新版本附带 npm provenance 构建来源证明,可追溯到公开的 CI 构建记录。

版本发布日期距今
1.11.3latest2026/10/121 个月前
1.11.22026/10/061 个月前
1.11.12026/07/054 个月前
1.11.02026/06/294 个月前
1.10.02026/06/194 个月前
1.9.02026/06/184 个月前

关于 @focus-reactive/payload-plugin-comments 的常见问题

如何安装 @focus-reactive/payload-plugin-comments?

在项目目录运行 npm install @focus-reactive/payload-plugin-comments,或使用 pnpm add / yarn add / bun add。它还需要宿主项目提供 peer 依赖:payload(^3.0.0)、@payloadcms/ui(^3.0.0)。npm 7 及以上与 pnpm 8 及以上默认会自动安装必需的 peer 依赖,Yarn 需要手动安装。

@focus-reactive/payload-plugin-comments 支持 TypeScript 吗?

支持。包内自带 TypeScript 类型声明(package.json 声明了 types 入口),安装后即可获得类型提示,无需再安装 @types 包。

@focus-reactive/payload-plugin-comments 支持 ESM 还是 CommonJS?

以 ES Module 形式发布,推荐使用 import 引入。在 CommonJS 项目中,Node.js 20.19+ / 22.12+ 可以直接 require() 不含顶层 await 的 ES Module,更早的版本需要改用动态 import()。

@focus-reactive/payload-plugin-comments 可以商用吗?

@focus-reactive/payload-plugin-comments 使用 MIT 许可。宽松许可:允许商业使用、修改和再分发,通常只需在分发时保留原版权与许可声明。以上为概括,不构成法律意见,请以许可原文为准。

@focus-reactive/payload-plugin-comments 的下载量有多少?

根据 npm 官方下载统计,@focus-reactive/payload-plugin-comments 在 2026/10/15 – 2026/11/13 这 30 天内被下载 47,701 次,日均约 1,590 次。下载量会把 CI 构建、镜像同步和作为其他包依赖的安装一并计入,适合横向比较热度,不能直接等同于使用人数。

@focus-reactive/payload-plugin-comments 还在维护吗?

最新版本 1.11.3 发布于 2026/10/12(1 个月前);至今共发布 22 个版本,其中过去 12 个月发布了 22 个;首次发布于 2026/03/18。发布频率只是参考信号:功能稳定的工具可能很少需要更新,建议结合源码仓库的 issue 和提交记录判断。