
语言 🇨🇳 简体中文
文档
入门指南
使用说明
API 参考
为您的 Django 应用添加评论
这是 FastComments 的官方 Django 包。
通过模板标签实现安全单点登录的实时评论和聊天组件。
仓库
要求 
- Python 3.10+
- Django 4.2, 5.0, 5.1, or 5.2
- FastComments 租户 ID(使用
demo可以在没有账户的情况下尝试) - API 密钥仅在安全单点登录时需要
安装 
从发布标签安装(此项目通过 git 标签分发,而不是 PyPI):
pip install "git+https://github.com/fastcomments/fastcomments-django.git@v0.1.0"
对于服务器端 REST 访问(admin() / public_api() 辅助函数),添加 api 额外项,它会引入 SDK 生成的客户端:
pip install "fastcomments-django[api] @ git+https://github.com/fastcomments/fastcomments-django.git@v0.1.0"
将该应用添加到 INSTALLED_APPS:
INSTALLED_APPS = [
# ...
"fastcomments_django",
]
快速入门 
在 settings.py 中配置您的租户:
import os
FASTCOMMENTS = {
"TENANT_ID": os.environ.get("FASTCOMMENTS_TENANT_ID", "demo"),
}
将小部件放入任意模板:
{% load fastcomments %}
{% fastcomments url_id="my-page" %}
自动单点登录的前提条件 
要自动将已登录用户传递给小部件,标签会从请求中读取当前用户。确保你的项目具备以下两项(在标准 Django 项目中默认启用):
django.template.context_processors.request在TEMPLATES["OPTIONS"]["context_processors"]django.contrib.auth.middleware.AuthenticationMiddleware在MIDDLEWARE
如果模板上下文中没有请求,组件将为匿名访客渲染。你也可以显式传递用户:{% fastcomments user=some_user %}。
小部件标签 
每个小部件都有其专属标签。所有标签都接受 **extra 关键字参数,这些参数会原样合并到小部件的配置中(使用 camelCase 键),用于处理下面未列出的命名参数。
| 标签 | 小部件 |
|---|---|
{% fastcomments %} | 评论 |
{% fastcomments_live_chat %} | 实时聊天 |
{% fastcomments_comment_count %} | 评论计数徽章 |
{% fastcomments_comment_count_bulk %} + {% fastcomments_count_marker %} | 批量评论计数 |
{% fastcomments_collab_chat target="#el" %} | 协作(内联)聊天 |
{% fastcomments_image_chat target="#el" %} | 图片标注聊天 |
{% fastcomments_recent_comments %} | 最近评论 |
{% fastcomments_recent_discussions %} | 最近讨论 |
{% fastcomments_reviews_summary %} | 评论摘要 |
{% fastcomments_top_pages %} | 讨论最多的页面 |
{% fastcomments_user_activity user_id="..." %} | 用户活动流 |
命名参数对应小部件的 camelCase 配置键:
| 参数 | 配置键 | 标签 |
|---|---|---|
url_id | urlId | 评论、实时聊天、评论计数、协作/图片聊天、最近评论、评论摘要 |
url | url | 评论、实时聊天、协作/图片聊天 |
readonly | readonly | 评论、实时聊天、协作/图片聊天 |
locale | locale | 评论、实时聊天、协作/图片聊天、用户活动 |
has_dark_background | hasDarkBackground | 所有 |
default_sort_direction | defaultSortDirection | 评论、实时聊天、协作/图片聊天 |
number_only | numberOnly | 评论计数 |
is_live | isLive | 评论计数 |
count | count | 最近评论、最近讨论 |
target | (querySelector, not sent) | 协作聊天、图片聊天 |
chat_square_percentage | chatSquarePercentage | 图片聊天 |
user_id | userId | 用户活动 |
示例:
{% load fastcomments %}
{% fastcomments url_id="my-page" locale="en_us" default_sort_direction="MR" %}
{% fastcomments_live_chat url_id="room-1" %}
Comments: {% fastcomments_comment_count url_id="my-page" number_only=True %}
{# 协作聊天附加到页面上已有的元素 #}
<article id="post-body">...</article>
{% fastcomments_collab_chat target="#post-body" %}
{# 批量计数:放置标记,然后一个批量加载器一次性填充所有计数 #}
{% for post in posts %}
<a href="\{{ post.url }}">\{{ post.title }}</a>
{% fastcomments_count_marker url_id=post.url_id %}
{% endfor %}
{% fastcomments_comment_count_bulk %}
单点登录 (SSO) 
Enable SSO and choose a mode in settings.py. Secure SSO signs the user
server-side with HMAC-SHA256 using your API secret and is recommended.
FASTCOMMENTS = {
"TENANT_ID": os.environ["FASTCOMMENTS_TENANT_ID"],
"API_KEY": os.environ["FASTCOMMENTS_API_KEY"], # 您的 API 密钥;用于签署 Secure SSO
"SSO": {
"ENABLED": True,
"MODE": "secure", # "secure" | "simple"
# 将 FastComments 字段映射到您的用户模型。值可以是属性
# 名称、点路径 ("profile.avatar_url")、callable(user) 或 None.
"USER_MAP": {
"id": "id",
"email": "email",
"username": "username",
"avatar": None,
"display_name": None,
"website_url": None,
},
"IS_ADMIN": lambda user: user.is_staff, # callable(user) -> bool,或点路径
"IS_MODERATOR": None,
"GROUP_IDS": None, # callable(user) -> list,或点路径
},
}
谨慎选择 SSO
id。 FastComments 的id是用户评论历史的永久标识。默认的USER_MAP将其映射到您的 Django 主键,以实现零配置的便利,但顺序整数主键是可枚举的,且以后难以更改(更改用户的id会把他们的历史拆分到新账号)。对于任何超出演示的情况,请将id映射到预先选择的稳定、不可公开的值(如 UUID 或专用公共 id),且永远不要在其中放置私有数据。示例应用程序因此使用基于用户名的 id。
SSO 会自动注入到当前用户的 {% fastcomments %}, {% fastcomments_live_chat %}, {% fastcomments_collab_chat %}, {% fastcomments_image_chat %} 和 {% fastcomments_user_activity %} 中。
Login/logout URLs shown to signed-out visitors default to reverse("login") /
reverse("logout"); override them with SSO["LOGIN_URL"] / SSO["LOGOUT_URL"].
自定义映射
Two higher-precedence options beat USER_MAP:
-
对用户模型的一个方法 (the Pythonic analog of an interface):
class User(AbstractUser): def to_fastcomments_user_data(self): return {"id": self.pk, "email": self.email, "username": self.get_username()} -
全局映射器, a dotted path to
callable(user) -> dict:FASTCOMMENTS = {"SSO": {"USER_MAPPER": "myapp.sso.map_user"}}
Precedence is USER_MAPPER > to_fastcomments_user_data() > USER_MAP.
服务器端 API 访问 
With the [api] extra installed, call the FastComments REST API through the SDK,
pre-configured with your API key and region:
from fastcomments_django import admin, public_api, get_manager
admin().get_comments("YOUR_TENANT_ID", ...) # 已认证 (DefaultApi)
public_api().get_comments_public(...) # 公共 (PublicApi)
# 为 API 调用或客户端交接生成 SSO 令牌:
token = get_manager().sso().token_for(request.user)
自定义嵌入标记 
通过在模板搜索路径的更前面放置您自己的副本来覆盖 fastcomments/widget.html
(项目的 templates/fastcomments/widget.html)。这相当于 Laravel 的 vendor:publish --tag=fastcomments-views
在 Django 中的对应做法。
设置参考 
| Key | Default | Description |
|---|---|---|
TENANT_ID | "" | 您的 FastComments 租户 ID(测试用为 demo)。 |
API_KEY | "" | 您的 API 密钥。用于签署安全 SSO 并验证 admin()。 |
REGION | None | 美国使用 None,欧盟地区使用 "eu"。 |
SSO.ENABLED | False | 启用 SSO。 |
SSO.MODE | "secure" | "secure"(HMAC)或 "simple"(未签名)。 |
SSO.LOGIN_URL / SSO.LOGOUT_URL | None | 显示给未登录的访客;默认使用 reverse("login"/"logout")。 |
SSO.USER_MAP | id/email/username | FastComments 字段映射到用户属性/路径/可调用对象。 |
SSO.IS_ADMIN / IS_MODERATOR / GROUP_IDS | None | callable(user) 或点分路径。 |
SSO.USER_MAPPER | None | 点分路径指向 callable(user) -> dict;优先级最高。 |
WIDGET_DEFAULTS | {} | 配置将合并到每个小部件中(camelCase 键)。 |
示例项目 
可运行的演示位于 example/:一个 left-rail + main-stage
应用,每个部件都有一个页面,并且包含一个列出预先种子演示用户的登录页面。
使用其中任意用户登录,评论和实时聊天部件将通过Secure SSO 验证该身份。
在该目录下运行:
python manage.py migrate
# 使用您自己的租户以查看 Secure SSO 的实际效果(需要 API secret):
FASTCOMMENTS_TENANT_ID=... FASTCOMMENTS_API_KEY=... python manage.py runserver
如果没有 API secret,则会回退到公共 demo 租户(匿名)。
example/browser_smoke.py 是一个 Playwright e2e
它在真实浏览器中加载页面并以 Secure-SSO 用户身份发布评论。
需要帮助?
如果您遇到任何问题或对 Django 包有疑问,请:
贡献
欢迎贡献!请访问GitHub 仓库查看贡献指南。