From 0a39e5c092cd581669d9ed507653d9d7afdca130 Mon Sep 17 00:00:00 2001 From: lyzno1 Date: Tue, 11 Nov 2025 19:32:48 +0800 Subject: [PATCH] Fix modal query sync for settings & pricing --- .../header/account-setting/index.tsx | 10 ++- web/app/education-apply/constants.ts | 1 - web/context/modal-context.tsx | 67 ++++++++++++++++--- 3 files changed, 68 insertions(+), 10 deletions(-) diff --git a/web/app/components/header/account-setting/index.tsx b/web/app/components/header/account-setting/index.tsx index efec47ad50..49f6f62a08 100644 --- a/web/app/components/header/account-setting/index.tsx +++ b/web/app/components/header/account-setting/index.tsx @@ -43,6 +43,7 @@ const iconClassName = ` type IAccountSettingProps = { onCancel: () => void activeTab?: AccountSettingTab + onTabChange?: (tab: AccountSettingTab) => void } type GroupItem = { @@ -56,8 +57,12 @@ type GroupItem = { export default function AccountSetting({ onCancel, activeTab = ACCOUNT_SETTING_TAB.MEMBERS, + onTabChange, }: IAccountSettingProps) { const [activeMenu, setActiveMenu] = useState(activeTab) + useEffect(() => { + setActiveMenu(activeTab) + }, [activeTab]) const { t } = useTranslation() const { enableBilling, enableReplaceWebAppLogo } = useProviderContext() const { isCurrentWorkspaceDatasetOperator } = useAppContext() @@ -182,7 +187,10 @@ export default function AccountSetting({ 'mb-0.5 flex h-[37px] cursor-pointer items-center rounded-lg p-1 pl-3 text-sm', activeMenu === item.key ? 'system-sm-semibold bg-state-base-active text-components-menu-item-text-active' : 'system-sm-medium text-components-menu-item-text')} title={item.name} - onClick={() => setActiveMenu(item.key)} + onClick={() => { + setActiveMenu(item.key) + onTabChange?.(item.key) + }} > {activeMenu === item.key ? item.activeIcon : item.icon} {!isMobile &&
{item.name}
} diff --git a/web/app/education-apply/constants.ts b/web/app/education-apply/constants.ts index 75b6da67e5..2c42d2b263 100644 --- a/web/app/education-apply/constants.ts +++ b/web/app/education-apply/constants.ts @@ -2,4 +2,3 @@ export const EDUCATION_VERIFY_URL_SEARCHPARAMS_ACTION = 'getEducationVerify' export const EDUCATION_VERIFYING_LOCALSTORAGE_ITEM = 'educationVerifying' export const EDUCATION_PRICING_SHOW_ACTION = 'educationPricing' export const EDUCATION_RE_VERIFY_ACTION = 'educationReVerify' -export const SHOW_PRICING_MODAL_ACTION = 'showPricing' diff --git a/web/context/modal-context.tsx b/web/context/modal-context.tsx index 9853508603..e0228b8ca8 100644 --- a/web/context/modal-context.tsx +++ b/web/context/modal-context.tsx @@ -1,7 +1,7 @@ 'use client' import type { Dispatch, SetStateAction } from 'react' -import { useCallback, useState } from 'react' +import { useCallback, useEffect, useState } from 'react' import { createContext, useContext, useContextSelector } from 'use-context-selector' import { useSearchParams } from 'next/navigation' import type { @@ -12,8 +12,8 @@ import type { ModelProvider, } from '@/app/components/header/account-setting/model-provider-page/declarations' import { + EDUCATION_PRICING_SHOW_ACTION, EDUCATION_VERIFYING_LOCALSTORAGE_ITEM, - SHOW_PRICING_MODAL_ACTION, } from '@/app/education-apply/constants' import type { AccountSettingTab } from '@/app/components/header/account-setting/constants' import { @@ -114,6 +114,9 @@ export type ModalContextState = { setShowUpdatePluginModal: Dispatch | null>> setShowEducationExpireNoticeModal: Dispatch | null>> } +const PRICING_MODAL_QUERY_PARAM = 'pricing' +const PRICING_MODAL_QUERY_VALUE = 'open' + const ModalContext = createContext({ setShowAccountSettingModal: noop, setShowApiBasedExtensionModal: noop, @@ -167,7 +170,7 @@ export const ModalContextProvider = ({ const [showEducationExpireNoticeModal, setShowEducationExpireNoticeModal] = useState | null>(null) const [showPricingModal, setShowPricingModal] = useState( - searchParams.get('action') === SHOW_PRICING_MODAL_ACTION, + searchParams.get(PRICING_MODAL_QUERY_PARAM) === PRICING_MODAL_QUERY_VALUE, ) const [showAnnotationFullModal, setShowAnnotationFullModal] = useState(false) const handleCancelAccountSettingModal = () => { @@ -183,6 +186,48 @@ export const ModalContextProvider = ({ showAccountSettingModal?.onCancelCallback() } + const handleAccountSettingTabChange = useCallback((tab: AccountSettingTab) => { + setShowAccountSettingModal((prev) => { + if (!prev) + return { payload: tab } + if (prev.payload === tab) + return prev + return { ...prev, payload: tab } + }) + }, [setShowAccountSettingModal]) + + useEffect(() => { + if (typeof window === 'undefined') + return + const url = new URL(window.location.href) + if (!showAccountSettingModal?.payload) { + if (url.searchParams.get('action') !== ACCOUNT_SETTING_MODAL_ACTION) + return + url.searchParams.delete('action') + url.searchParams.delete('tab') + window.history.replaceState(null, '', url.toString()) + return + } + url.searchParams.set('action', ACCOUNT_SETTING_MODAL_ACTION) + url.searchParams.set('tab', showAccountSettingModal.payload) + window.history.replaceState(null, '', url.toString()) + }, [showAccountSettingModal]) + + useEffect(() => { + if (typeof window === 'undefined') + return + const url = new URL(window.location.href) + if (showPricingModal) { + url.searchParams.set(PRICING_MODAL_QUERY_PARAM, PRICING_MODAL_QUERY_VALUE) + } + else { + url.searchParams.delete(PRICING_MODAL_QUERY_PARAM) + if (url.searchParams.get('action') === EDUCATION_PRICING_SHOW_ACTION) + url.searchParams.delete('action') + } + window.history.replaceState(null, '', url.toString()) + }, [showPricingModal]) + const handleCancelModerationSettingModal = () => { setShowModerationSettingModal(null) if (showModerationSettingModal?.onCancelCallback) @@ -267,13 +312,21 @@ export const ModalContextProvider = ({ setShowOpeningModal(null) } + const handleShowPricingModal = useCallback(() => { + setShowPricingModal(true) + }, []) + + const handleCancelPricingModal = useCallback(() => { + setShowPricingModal(false) + }, []) + return ( setShowPricingModal(true), + setShowPricingModal: handleShowPricingModal, setShowAnnotationFullModal: () => setShowAnnotationFullModal(true), setShowModelModal, setShowExternalKnowledgeAPIModal, @@ -289,6 +342,7 @@ export const ModalContextProvider = ({ ) } @@ -324,10 +378,7 @@ export const ModalContextProvider = ({ { !!showPricingModal && ( - { - removeSpecificQueryParam('action') - setShowPricingModal(false) - }} /> + ) }