refactor: scope providers by route and use XState selectors

This commit is contained in:
2026-07-13 19:07:53 +08:00
parent f9b5f22ee9
commit 37ae152abb
24 changed files with 512 additions and 336 deletions
@@ -1,6 +1,11 @@
"use client";
import { useChatDispatch, useChatState } from "@/stores/chat/chat-context";
import { shallowEqual } from "@xstate/react";
import {
useChatDispatch,
useChatSelector,
} from "@/stores/chat/chat-context";
import type { ChatUnlockPaywallRequest } from "@/stores/chat/chat-state";
import { HistoryUnlockDialog } from "./history-unlock-dialog";
@@ -19,7 +24,15 @@ export function ChatUnlockDialogs({
onConfirmInsufficientCreditsDialog,
includeHistoryUnlock = true,
}: ChatUnlockDialogsProps) {
const chatState = useChatState();
const chatState = useChatSelector(
(state) => ({
isUnlockingHistory: state.context.isUnlockingHistory,
lockedHistoryCount: state.context.lockedHistoryCount,
unlockHistoryError: state.context.unlockHistoryError,
unlockHistoryPromptVisible: state.context.unlockHistoryPromptVisible,
}),
shallowEqual,
);
const chatDispatch = useChatDispatch();
return (
+2 -2
View File
@@ -8,7 +8,7 @@
* - AI[Avatar] [Content] [占位 spacer]
* - 用户:[占位 spacer] [Content] [Avatar]
*/
import { useUserState } from "@/stores/user/user-context";
import { useUserSelector } from "@/stores/user/user-context";
import { MessageAvatar } from "./message-avatar";
import { MessageContent } from "./message-content";
@@ -49,7 +49,7 @@ export function MessageBubble({
onUnlockImageMessage,
onOpenImage,
}: MessageBubbleProps) {
const { avatarUrl } = useUserState();
const avatarUrl = useUserSelector((state) => state.context.avatarUrl);
if (isFromAI) {
return (