style: remove markdown bold syntax from code comments
Remove `**...**` emphasis markers from inline comments and JSDoc blocks across auth and chat components, machine mappers, and quota helpers. These are plain code comments, not rendered markdown, so the bold syntax was noise. Files touched: - src/app/auth/components/auth-screen.tsx - src/app/chat/components/chat-header.tsx - src/app/chat/components/chat-screen.tsx - chat machine mapper / quota helpers No functional or behavioral changes.
This commit is contained in:
@@ -1,32 +1,32 @@
|
||||
/**
|
||||
* Chat 状态机(XState v5)
|
||||
*
|
||||
* **鉴权解耦**(**事件驱动**):
|
||||
* chat 机器**不**感知鉴权 / **不**管 WebSocket —— 由 chat-screen 派生 loginStatus
|
||||
* chat-screen **只**派 3 个事件:
|
||||
* - `ChatGuestLogin` → 游客会话(**断** WS = 不连)
|
||||
* - `ChatNonGuestLogin { token }` → 非游客会话(**连** WS)
|
||||
* 鉴权解耦(事件驱动):
|
||||
* chat 机器不感知鉴权 / 不管 WebSocket —— 由 chat-screen 派生 loginStatus
|
||||
* chat-screen 只派 3 个事件:
|
||||
* - `ChatGuestLogin` → 游客会话(断 WS = 不连)
|
||||
* - `ChatNonGuestLogin { token }` → 非游客会话(连 WS)
|
||||
* - `ChatLogout` → 登出(机器自动 cleanup WS actor)
|
||||
*
|
||||
* **状态结构**(parent state 模式):
|
||||
* 状态结构(parent state 模式):
|
||||
* - `idle`:屏没挂 / 登出
|
||||
* - `guestSession`(**parent**):游客会话 —— **不** invoke WS
|
||||
* - `userSession`(**parent**):非游客会话 —— **invoke WS**(持久)
|
||||
* - `guestSession`(parent):游客会话 —— 不 invoke WS
|
||||
* - `userSession`(parent):非游客会话 —— invoke WS(持久)
|
||||
*
|
||||
* **init 双任务**(**核**心**重**构**):
|
||||
* - guestSession.initializing:loadQuota + loadHistory **并**行**(`invoke: [...]` **数**组**)
|
||||
* - userSession.initializing:loadHistory + parent-level chatWebSocket **并**行
|
||||
* - **每**个**任务**都**是**独**立** actor,**不**互**相**等**待**(**除**非** `always` barrier)
|
||||
* init 双任务(核心重构):
|
||||
* - guestSession.initializing:loadQuota + loadHistory 并行(`invoke: [...]` 数组)
|
||||
* - userSession.initializing:loadHistory + parent-level chatWebSocket 并行
|
||||
* - 每个任务都是独立 actor,不互相等待(除非 `always` barrier)
|
||||
*
|
||||
* **消息发送路径**(**业务事实**):
|
||||
* - `wsConnected: true`(**仅** userSession 期间)→ **走 WS**,**不**消耗次数(**仅**配额规则)
|
||||
* - `wsConnected: false` → **走 HTTP**,消耗次数(**仅**游客有意义 —— 非游客 0-1=max(0,-1)=0 天然 no-op)
|
||||
* 消息发送路径(业务事实):
|
||||
* - `wsConnected: true`(仅 userSession 期间)→ 走 WS,不消耗次数(仅配额规则)
|
||||
* - `wsConnected: false` → 走 HTTP,消耗次数(仅游客有意义 —— 非游客 0-1=max(0,-1)=0 天然 no-op)
|
||||
* - `ChatWebSocketConnected` 事件 → `wsConnected = true`
|
||||
* - `userSession.exit` action → `wsConnected = false`(WS actor cleanup 时**也**会跑 exit)
|
||||
* - `userSession.exit` action → `wsConnected = false`(WS actor cleanup 时也会跑 exit)
|
||||
*
|
||||
* **配额(**仅**游客)**:
|
||||
* 配额(仅游客):
|
||||
* - 非游客"无消息限制"(业务事实)—— 永不被赋值
|
||||
* - `appendUserMessage` 减 `context.wsConnected ? q : Math.max(0, q-1)` —— WS 已连时**不**递减
|
||||
* - `appendUserMessage` 减 `context.wsConnected ? q : Math.max(0, q-1)` —— WS 已连时不递减
|
||||
*
|
||||
*/
|
||||
|
||||
@@ -75,7 +75,7 @@ export const chatMachine = setup({
|
||||
appendUserMessage: assign(({ context, event }) => {
|
||||
if (event.type !== "ChatSendMessage") return {};
|
||||
|
||||
// 两**个**额度**同**步**更**新**:WS 已**连****不**递减(**实**时**会**话**不**消耗**),HTTP **必**须**减
|
||||
// 两个额度同步更新:WS 已连不递减(实时会话不消耗),HTTP 必须减
|
||||
const newRemaining = context.wsConnected
|
||||
? context.guestRemainingQuota
|
||||
: Math.max(0, context.guestRemainingQuota - 1);
|
||||
@@ -83,8 +83,8 @@ export const chatMachine = setup({
|
||||
? context.guestTotalQuota
|
||||
: Math.max(0, context.guestTotalQuota - 1);
|
||||
|
||||
// 持**久**化**两**个**额度**(** fire-and-forget,**不** await —— assign **是** sync)
|
||||
// daily quota 需**要** today **字**符**串**(**让** ChatStorage 跨**天**判**断** reset)
|
||||
// 持久化两个额度( fire-and-forget,不 await —— assign 是 sync)
|
||||
// daily quota 需要 today 字符串(让 ChatStorage 跨天判断 reset)
|
||||
const today = formatDate();
|
||||
ChatStorage.getInstance().setGuestDailyChatQuota(newRemaining, today);
|
||||
ChatStorage.getInstance().setGuestTotalQuota(newTotal);
|
||||
@@ -117,7 +117,7 @@ export const chatMachine = setup({
|
||||
|
||||
appendUserImage: assign(({ context, event }) => {
|
||||
if (event.type !== "ChatSendImage") return {};
|
||||
// **同** appendUserMessage:两**个**额度**同**步**减
|
||||
// 同 appendUserMessage:两个额度同步减
|
||||
const newRemaining = context.wsConnected
|
||||
? context.guestRemainingQuota
|
||||
: Math.max(0, context.guestRemainingQuota - 1);
|
||||
@@ -211,13 +211,13 @@ export const chatMachine = setup({
|
||||
},
|
||||
|
||||
// ========================================================================
|
||||
// guestSession(游客会话 —— **不**连 WS,2 **个** init 任务**并**行**)
|
||||
// guestSession(游客会话 —— 不连 WS,2 个 init 任务并行)
|
||||
// ========================================================================
|
||||
guestSession: {
|
||||
initial: "initializing",
|
||||
states: {
|
||||
initializing: {
|
||||
// "always" barrier:两**个**任务**都**完**成**才**进** ready
|
||||
// "always" barrier:两个任务都完成才进 ready
|
||||
always: [
|
||||
{
|
||||
target: "ready",
|
||||
@@ -225,7 +225,7 @@ export const chatMachine = setup({
|
||||
},
|
||||
],
|
||||
invoke: [
|
||||
// 任务 1:加载配额(fromPromise,**返**结果 + onDone 设 flag)
|
||||
// 任务 1:加载配额(fromPromise,返结果 + onDone 设 flag)
|
||||
{
|
||||
id: "loadQuota",
|
||||
src: "loadQuota",
|
||||
@@ -237,13 +237,13 @@ export const chatMachine = setup({
|
||||
})),
|
||||
},
|
||||
onError: {
|
||||
// 失败**也**标 loaded,**不**卡 init(**游**客**可**能 quota 服务**不**可**用**,**让** UI **进** ready)
|
||||
// 失败也标 loaded,不卡 init(游客可能 quota 服务不可用,让 UI 进 ready)
|
||||
actions: assign({
|
||||
quotaLoaded: true,
|
||||
}),
|
||||
},
|
||||
},
|
||||
// 任务 2:拉 history(fromPromise,**返**回**最**终** network messages**)
|
||||
// 任务 2:拉 history(fromPromise,返回最终 network messages)
|
||||
{
|
||||
id: "loadHistory",
|
||||
src: "loadHistory",
|
||||
@@ -256,7 +256,7 @@ export const chatMachine = setup({
|
||||
})),
|
||||
},
|
||||
onError: {
|
||||
// 失败**也**标 loaded,**不**卡 init(**让** UI **还**是**能**进** ready,**屏**幕**可**能**空**)
|
||||
// 失败也标 loaded,不卡 init(让 UI 还是能进 ready,屏幕可能空)
|
||||
actions: assign({
|
||||
historyLoaded: true,
|
||||
}),
|
||||
@@ -266,29 +266,29 @@ export const chatMachine = setup({
|
||||
},
|
||||
ready: {
|
||||
on: {
|
||||
// **配**额**检**查** + 发**送**消息**(3 **条** guard,**按**顺**序**匹**配**)
|
||||
// 1. **总**配**额**(guestTotalQuota)**不**足 → **触**发** quota exceeded dialog,**不**发**送**
|
||||
// 2. **每**日**配**额**(guestRemainingQuota)**不**足 → **同**上**
|
||||
// 3. **两**个**配**额**都** OK + **内**容**非**空** → **发**送** + **减**配**额**
|
||||
// 配额检查 + 发送消息(3 条 guard,按顺序匹配)
|
||||
// 1. 总配额(guestTotalQuota)不足 → 触发 quota exceeded dialog,不发送
|
||||
// 2. 每日配额(guestRemainingQuota)不足 → 同上
|
||||
// 3. 两个配额都 OK + 内容非空 → 发送 + 减配额
|
||||
ChatSendMessage: [
|
||||
// 1. 总配**额** **不**足**(guestTotalQuota <= 0) → **触**发** quota exceeded dialog
|
||||
// 1. 总配额 不足(guestTotalQuota <= 0) → 触发 quota exceeded dialog
|
||||
{
|
||||
guard: ({ context }) => context.guestTotalQuota <= 0,
|
||||
actions: "incrementQuotaExceeded",
|
||||
},
|
||||
// 2. 每**日**配**额** **不**足**(guestRemainingQuota <= 0) → **触**发** quota exceeded dialog
|
||||
// 2. 每日配额 不足(guestRemainingQuota <= 0) → 触发 quota exceeded dialog
|
||||
{
|
||||
guard: ({ context }) => context.guestRemainingQuota <= 0,
|
||||
actions: "incrementQuotaExceeded",
|
||||
},
|
||||
// 3. 两**个**配**额**都** OK + **内**容**非**空** → **发**送**(**只**用** appendUserMessage **自**己**的**日**志**)
|
||||
// 3. 两个配额都 OK + 内容非空 → 发送(只用 appendUserMessage 自己的日志)
|
||||
{
|
||||
actions: "appendUserMessage",
|
||||
guard: ({ event }) => event.content.trim().length > 0,
|
||||
target: "sending",
|
||||
},
|
||||
],
|
||||
// **配**额**检**查** + 发**送**图**片**(**同**样** 3 **条** guard,**不**检**查** "内**容**空"**)
|
||||
// 配额检查 + 发送图片(同样 3 条 guard,不检查 "内容空")
|
||||
ChatSendImage: [
|
||||
{
|
||||
guard: ({ context }) => context.guestTotalQuota <= 0,
|
||||
@@ -303,7 +303,7 @@ export const chatMachine = setup({
|
||||
target: "sending",
|
||||
},
|
||||
],
|
||||
// **删**除 ChatLoadMoreHistory handler —— 游客**无**服**务**端** history,**不**支**持**翻**页**
|
||||
// 删除 ChatLoadMoreHistory handler —— 游客无服务端 history,不支持翻页
|
||||
ChatLogout: "#chat.idle",
|
||||
ChatNonGuestLogin: "#chat.userSession",
|
||||
ChatAISentenceReceived: { actions: "appendOrUpdateAISentence" },
|
||||
@@ -331,18 +331,18 @@ export const chatMachine = setup({
|
||||
},
|
||||
},
|
||||
},
|
||||
// **删**除 loadingMore(游客**无**翻**页**)
|
||||
// 删除 loadingMore(游客无翻页)
|
||||
},
|
||||
},
|
||||
|
||||
// ========================================================================
|
||||
// userSession(非游客会话 —— WS **父**级 + history **子**级**)
|
||||
// userSession(非游客会话 —— WS 父级 + history 子级)
|
||||
// ========================================================================
|
||||
userSession: {
|
||||
initial: "initializing",
|
||||
exit: "clearWsConnected",
|
||||
invoke: {
|
||||
// 父级:WS 长**连**接(**一**进**来****就**连,跨 initializing/ready/sending/loadingMore)
|
||||
// 父级:WS 长连接(一进来就连,跨 initializing/ready/sending/loadingMore)
|
||||
src: "chatWebSocket",
|
||||
input: ({ event }) => ({
|
||||
token: event.type === "ChatNonGuestLogin" ? event.token : "",
|
||||
@@ -350,7 +350,7 @@ export const chatMachine = setup({
|
||||
},
|
||||
states: {
|
||||
initializing: {
|
||||
// barrier:WS **连**上** + history **加**载**完**成**才**进** ready
|
||||
// barrier:WS 连上 + history 加载完成才进 ready
|
||||
always: [
|
||||
{
|
||||
target: "ready",
|
||||
@@ -358,7 +358,7 @@ export const chatMachine = setup({
|
||||
},
|
||||
],
|
||||
invoke: {
|
||||
// 任务 2:拉 history(**只**调**用** loadHistoryActor,**不**再**用** loadMoreHistoryActor)
|
||||
// 任务 2:拉 history(只调用 loadHistoryActor,不再用 loadMoreHistoryActor)
|
||||
src: "loadHistory",
|
||||
onDone: {
|
||||
actions: assign(({ event }) => ({
|
||||
@@ -370,7 +370,7 @@ export const chatMachine = setup({
|
||||
})),
|
||||
},
|
||||
onError: {
|
||||
// 失败**也**标 loaded,**不**卡 init
|
||||
// 失败也标 loaded,不卡 init
|
||||
actions: assign({
|
||||
isLoadingMore: false,
|
||||
historyLoaded: true,
|
||||
|
||||
Reference in New Issue
Block a user