From 337169e0a456ac3943a9ded079fda14786008f83 Mon Sep 17 00:00:00 2001 From: CaIon Date: Sat, 11 Jul 2026 14:51:54 +0800 Subject: [PATCH 1/2] revert: undo t0ng7u UI design-system refactor Revert the following commits: - 308e3e347 feat(web): polish themed data views and add task log details - b2a890e75 fix: Fontsource asset resolution across workspace layouts - 9d1ca545e refactor(web): refine data-table cards and pricing page layout - 0918bdb49 refactor(web): consolidate design-system primitives and responsive data views - 262ab9312 style(web): unify design system across default frontend --- common/constants.go | 2 +- controller/channel.go | 2 +- web/bun.lock | 28 +- .../settings/ChannelSelectorModal.jsx | 2 +- .../channels/modals/MultiKeyManageModal.jsx | 4 +- .../users/modals/UserSubscriptionsModal.jsx | 2 +- .../topup/modals/TopupHistoryModal.jsx | 2 +- .../src/constants/channel.constants.js | 2 +- web/classic/src/constants/common.constant.js | 2 +- .../src/constants/dashboard.constants.js | 2 +- .../subscriptions/useSubscriptionsData.jsx | 2 +- web/classic/src/index.css | 16 - .../src/pages/Setting/Chat/SettingsChats.jsx | 2 +- .../Setting/Dashboard/SettingsAPIInfo.jsx | 2 +- .../Dashboard/SettingsAnnouncements.jsx | 2 +- .../pages/Setting/Dashboard/SettingsFAQ.jsx | 2 +- .../Setting/Dashboard/SettingsUptimeKuma.jsx | 2 +- .../pages/Setting/Ratio/UpstreamRatioSync.jsx | 2 +- .../Ratio/hooks/useModelPricingEditorState.js | 2 +- web/default/.oxlintrc.json | 40 - web/default/AGENTS.md | 54 +- web/default/components.json | 2 +- web/default/package.json | 6 +- .../src/components/ai-elements/actions.tsx | 6 +- .../src/components/ai-elements/artifact.tsx | 16 +- .../src/components/ai-elements/branch.tsx | 10 +- .../src/components/ai-elements/code-block.tsx | 14 +- .../components/ai-elements/confirmation.tsx | 4 +- .../src/components/ai-elements/context.tsx | 2 +- .../components/ai-elements/conversation.tsx | 2 +- .../ai-elements/inline-citation.tsx | 2 +- .../components/ai-elements/open-in-chat.tsx | 2 +- .../src/components/ai-elements/plan.tsx | 4 +- .../components/ai-elements/prompt-input.tsx | 31 +- .../src/components/ai-elements/queue.tsx | 4 +- .../ai-elements/response-renderer-alert.tsx | 24 +- .../src/components/ai-elements/suggestion.tsx | 2 +- .../components/ai-elements/web-preview.tsx | 10 +- web/default/src/components/command-menu.tsx | 2 +- web/default/src/components/config-drawer.tsx | 8 +- web/default/src/components/confirm-dialog.tsx | 4 +- web/default/src/components/copy-button.tsx | 4 +- .../components/data-table/core/badge-cell.tsx | 2 +- .../core/badge-list-cell-context.ts | 24 - .../data-table/core/badge-list-cell.tsx | 19 +- .../data-table/core/column-header.tsx | 5 +- .../data-table/core/column-pinning.ts | 4 +- .../data-table/core/content-sized-columns.ts | 7 +- .../data-table/core/data-table-colgroup.tsx | 11 +- .../data-table/core/data-table-header.tsx | 19 +- .../data-table/core/data-table-row.tsx | 74 +- .../data-table/core/data-table-view.tsx | 32 +- .../components/data-table/core/pagination.tsx | 20 +- .../data-table/core/row-action-menu.tsx | 4 +- .../data-table/core/table-empty.tsx | 2 +- .../data-table/core/table-sizing.ts | 5 +- .../data-table/core/table-skeleton.tsx | 2 +- .../data-table/core/truncated-cell.tsx | 9 +- .../src/components/data-table/core/types.ts | 1 - .../src/components/data-table/index.ts | 20 +- .../data-table/layout/card-cell-utils.ts | 8 +- .../data-table/layout/card-field.tsx | 119 --- .../data-table/layout/card-grid.tsx | 6 +- .../data-table/layout/card-row-content.tsx | 245 +++--- .../data-table/layout/data-table-page.tsx | 38 +- .../data-table/layout/mobile-card-list.tsx | 20 +- .../static/static-data-table-classnames.ts | 5 +- .../data-table/static/static-data-table.tsx | 2 +- .../data-table/static/static-row-actions.tsx | 2 +- .../data-table/toolbar/bulk-actions.tsx | 5 +- .../data-table/toolbar/faceted-filter.tsx | 146 ++-- .../data-table/toolbar/filter-panel.tsx | 314 -------- .../components/data-table/toolbar/toolbar.tsx | 202 +++-- .../data-table/toolbar/view-mode-toggle.tsx | 92 ++- .../data-table/toolbar/view-options.tsx | 2 +- web/default/src/components/date-picker.tsx | 2 +- .../src/components/datetime-picker.tsx | 4 +- .../src/components/design-system/README.md | 42 -- .../components/design-system/alert-dialog.tsx | 80 -- .../src/components/design-system/button.tsx | 65 -- .../design-system/combobox-input.tsx | 37 - .../src/components/design-system/combobox.tsx | 139 ---- .../src/components/design-system/command.tsx | 77 -- .../src/components/design-system/dialog.tsx | 74 -- .../components/design-system/input-group.tsx | 79 -- .../src/components/design-system/input.tsx | 37 - .../components/design-system/pagination.tsx | 55 -- .../src/components/design-system/select.tsx | 64 -- .../src/components/design-system/sidebar.tsx | 95 --- .../src/components/design-system/table.tsx | 49 -- .../src/components/design-system/tabs.tsx | 61 -- .../components/design-system/toggle-group.tsx | 46 -- .../src/components/design-system/toggle.tsx | 59 -- web/default/src/components/dialog.tsx | 4 +- web/default/src/components/drawer-layout.ts | 8 +- web/default/src/components/error-state.tsx | 4 +- web/default/src/components/group-badge.tsx | 66 +- web/default/src/components/html-content.tsx | 10 +- .../src/components/json-code-editor.tsx | 7 +- web/default/src/components/json-editor.tsx | 10 +- .../src/components/language-switcher.tsx | 6 +- .../layout/components/app-sidebar.tsx | 14 +- .../components/authenticated-layout.tsx | 7 +- .../layout/components/chat-presets-item.tsx | 16 +- .../src/components/layout/components/glow.tsx | 4 +- .../components/layout/components/header.tsx | 4 +- .../layout/components/mobile-drawer.tsx | 7 +- .../layout/components/nav-group.tsx | 24 +- .../layout/components/public-header.tsx | 6 +- .../layout/components/public-page-header.tsx | 67 -- .../layout/components/section-page-layout.tsx | 2 +- .../layout/components/sidebar-view-header.tsx | 4 +- .../layout/components/system-brand.tsx | 2 +- .../components/layout/components/top-nav.tsx | 4 +- web/default/src/components/layout/index.ts | 5 - web/default/src/components/learn-more.tsx | 2 +- .../src/components/masked-value-display.tsx | 6 +- .../src/components/model-group-selector.tsx | 78 +- web/default/src/components/multi-select.tsx | 2 +- .../src/components/navigation-progress.tsx | 9 +- .../src/components/notification-popover.tsx | 17 +- .../src/components/page-transition.tsx | 88 ++- web/default/src/components/password-input.tsx | 9 +- .../src/components/profile-dropdown.tsx | 6 +- web/default/src/components/provider-badge.tsx | 37 +- web/default/src/components/rich-content.tsx | 5 +- .../risk-acknowledgement-dialog.tsx | 6 +- web/default/src/components/search.tsx | 7 +- web/default/src/components/status-badge.tsx | 374 +++++----- web/default/src/components/table-id.tsx | 2 +- web/default/src/components/tag-input.tsx | 2 +- .../src/components/theme-quick-switcher.tsx | 14 +- web/default/src/components/theme-switch.tsx | 12 +- web/default/src/components/ui/accordion.tsx | 4 +- .../src/components/ui/alert-dialog.tsx | 16 +- web/default/src/components/ui/alert.tsx | 4 +- web/default/src/components/ui/avatar.tsx | 10 +- web/default/src/components/ui/breadcrumb.tsx | 4 +- .../src/components/ui/button-group.tsx | 2 +- web/default/src/components/ui/button.tsx | 26 +- web/default/src/components/ui/calendar.tsx | 4 +- web/default/src/components/ui/card.tsx | 10 +- web/default/src/components/ui/carousel.tsx | 8 +- web/default/src/components/ui/chart.tsx | 12 +- web/default/src/components/ui/checkbox.tsx | 2 +- web/default/src/components/ui/combobox.tsx | 59 +- web/default/src/components/ui/command.tsx | 10 +- .../src/components/ui/context-menu.tsx | 18 +- web/default/src/components/ui/dialog.tsx | 8 +- web/default/src/components/ui/drawer.tsx | 166 +---- .../src/components/ui/dropdown-menu-events.ts | 25 + .../src/components/ui/dropdown-menu.test.tsx | 51 ++ .../src/components/ui/dropdown-menu.tsx | 36 +- web/default/src/components/ui/empty.tsx | 2 +- web/default/src/components/ui/field.tsx | 8 +- web/default/src/components/ui/hover-card.tsx | 2 +- web/default/src/components/ui/input-group.tsx | 11 +- web/default/src/components/ui/input-otp.tsx | 4 +- web/default/src/components/ui/input.tsx | 2 +- web/default/src/components/ui/item.tsx | 2 +- web/default/src/components/ui/kbd.tsx | 2 +- web/default/src/components/ui/menubar.tsx | 18 +- .../src/components/ui/native-select.tsx | 2 +- .../src/components/ui/navigation-menu.tsx | 6 +- web/default/src/components/ui/popover.tsx | 16 +- web/default/src/components/ui/progress.tsx | 6 +- web/default/src/components/ui/radio-group.tsx | 2 +- web/default/src/components/ui/resizable.tsx | 2 +- web/default/src/components/ui/select.tsx | 72 +- web/default/src/components/ui/separator.tsx | 2 +- web/default/src/components/ui/sheet.tsx | 27 +- web/default/src/components/ui/sidebar.tsx | 51 +- web/default/src/components/ui/skeleton.tsx | 2 +- web/default/src/components/ui/sonner.tsx | 35 +- web/default/src/components/ui/spinner.tsx | 8 +- web/default/src/components/ui/switch.tsx | 2 +- web/default/src/components/ui/table.tsx | 28 +- web/default/src/components/ui/tabs.tsx | 4 +- web/default/src/components/ui/textarea.tsx | 2 +- web/default/src/components/ui/titled-card.tsx | 8 +- .../src/components/ui/toggle-group.tsx | 6 +- web/default/src/components/ui/toggle.tsx | 2 +- web/default/src/components/ui/tooltip.tsx | 10 +- web/default/src/config/fonts.ts | 37 + web/default/src/context/font-provider.tsx | 77 ++ .../context/theme-customization-provider.tsx | 18 +- web/default/src/context/theme-provider.tsx | 5 +- .../auth/components/oauth-providers.tsx | 5 +- .../components/forgot-password-form.tsx | 5 +- .../features/auth/otp/components/otp-form.tsx | 11 +- .../auth/reset-password-confirm/index.tsx | 5 +- .../components/secure-verification-dialog.tsx | 11 +- .../sign-in/components/user-auth-form.tsx | 12 +- .../auth/sign-up/components/sign-up-form.tsx | 9 +- web/default/src/features/channels/api.ts | 2 +- .../channels/components/channel-card.tsx | 164 ++-- .../channels/components/channels-columns.tsx | 253 +++---- .../components/channels-primary-buttons.tsx | 65 +- .../channels/components/channels-table.tsx | 18 +- .../components/data-table-bulk-actions.tsx | 8 +- .../components/data-table-row-actions.tsx | 10 +- .../components/data-table-tag-row-actions.tsx | 2 +- .../dialogs/advanced-custom-editor-dialog.tsx | 30 +- .../dialogs/balance-query-dialog.tsx | 2 +- .../dialogs/channel-test-dialog.tsx | 56 +- .../components/dialogs/codex-usage-dialog.tsx | 122 ++- .../dialogs/copy-channel-dialog.tsx | 4 +- .../components/dialogs/edit-tag-dialog.tsx | 46 +- .../dialogs/fetch-models-dialog.tsx | 15 +- .../missing-models-confirmation-dialog.tsx | 6 +- .../dialogs/multi-key-manage-dialog.tsx | 67 +- .../dialogs/multi-key-table-row-actions.tsx | 2 +- .../dialogs/ollama-models-dialog.tsx | 17 +- .../dialogs/param-override-editor-dialog.tsx | 189 +++-- .../dialogs/status-code-risk-dialog.tsx | 6 +- .../dialogs/tag-batch-edit-dialog.tsx | 6 +- .../dialogs/upstream-update-dialog.tsx | 23 +- .../drawers/channel-mutate-drawer.tsx | 66 +- .../components/model-mapping-editor.tsx | 16 +- .../components/numeric-spinner-input.tsx | 4 +- .../src/features/channels/constants.ts | 6 +- .../features/channels/lib/channel-utils.ts | 4 +- .../dashboard/components/flow/flow-charts.tsx | 4 +- .../components/flow/flow-node-filter.tsx | 15 +- .../components/models/log-stat-cards.tsx | 4 +- .../models/models-chart-preferences.tsx | 10 +- .../models/models-filter-dialog.tsx | 15 +- .../models/performance-overview.tsx | 49 +- .../components/overview/api-info-item.tsx | 51 +- .../overview/overview-dashboard.tsx | 699 +++++++++++++++++- .../overview/performance-health-panel.tsx | 10 +- .../components/overview/summary-cards.tsx | 8 +- .../components/overview/uptime-panel.tsx | 17 +- .../dashboard/components/ui/panel-wrapper.tsx | 6 +- .../dashboard/components/ui/stat-card.tsx | 20 +- .../components/users/user-charts.tsx | 2 +- web/default/src/features/dashboard/index.tsx | 8 +- .../src/features/dashboard/lib/api-info.ts | 8 +- .../dashboard/lib/flow-selection.test.ts | 43 ++ .../features/dashboard/lib/flow-selection.ts | 14 +- .../src/features/dashboard/lib/flow.test.ts | 10 +- .../src/features/dashboard/lib/flow.ts | 22 + web/default/src/features/errors/forbidden.tsx | 2 +- .../src/features/errors/general-error.tsx | 2 +- .../src/features/errors/maintenance-error.tsx | 2 +- .../src/features/errors/not-found-error.tsx | 2 +- .../features/errors/unauthorized-error.tsx | 2 +- .../features/home/components/hero-buttons.tsx | 2 +- .../features/home/components/sections/cta.tsx | 2 +- .../home/components/sections/hero.tsx | 17 +- web/default/src/features/keys/api.ts | 2 +- .../features/keys/components/api-key-card.tsx | 177 ----- .../components/api-key-group-combobox.tsx | 22 +- .../keys/components/api-keys-cells.tsx | 38 +- .../keys/components/api-keys-columns.tsx | 139 ++-- .../components/api-keys-delete-dialog.tsx | 2 +- .../components/api-keys-mutate-drawer.tsx | 16 +- .../components/api-keys-primary-buttons.tsx | 4 +- .../keys/components/api-keys-table.tsx | 162 +++- .../components/data-table-bulk-actions.tsx | 4 +- .../components/data-table-row-actions.tsx | 4 +- .../components/dialogs/cc-switch-dialog.tsx | 4 +- web/default/src/features/keys/constants.ts | 4 +- .../src/features/legal/legal-document.tsx | 8 +- .../components/data-table-bulk-actions.tsx | 6 +- .../components/data-table-row-actions.tsx | 2 +- .../components/deployment-access-guard.tsx | 14 +- .../models/components/deployments-columns.tsx | 92 +-- .../models/components/deployments-table.tsx | 8 +- .../models/components/description-cell.tsx | 6 +- .../dialogs/create-deployment-drawer.tsx | 20 +- .../components/dialogs/description-dialog.tsx | 2 +- .../dialogs/extend-deployment-dialog.tsx | 4 +- .../dialogs/missing-models-dialog.tsx | 27 +- .../prefill-group-management-dialog.tsx | 70 +- .../dialogs/rename-deployment-dialog.tsx | 4 +- .../components/dialogs/sync-wizard-dialog.tsx | 8 +- .../dialogs/update-config-dialog.tsx | 4 +- .../dialogs/upstream-conflict-dialog.tsx | 77 +- .../dialogs/vendor-mutate-dialog.tsx | 4 +- .../dialogs/view-details-dialog.tsx | 6 +- .../components/dialogs/view-logs-dialog.tsx | 22 +- .../drawers/model-mutate-drawer.tsx | 22 +- .../drawers/prefill-group-form-drawer.tsx | 100 +-- .../models/components/models-columns.tsx | 165 ++--- .../components/models-primary-buttons.tsx | 6 +- .../models/components/models-table.tsx | 6 +- .../models/components/prefill-group-shared.ts | 20 +- web/default/src/features/models/constants.ts | 42 +- web/default/src/features/models/index.tsx | 10 +- .../performance-metrics/lib/format.ts | 16 +- .../chat/playground-empty-state.tsx | 4 +- .../input/playground-parameter-panel.tsx | 12 +- .../message/message-action-button.tsx | 2 +- .../components/message/message-actions.tsx | 6 +- .../components/message/message-error.tsx | 5 +- .../components/message/message-metadata.tsx | 2 +- .../message/playground-message-editor.tsx | 2 +- .../components/dynamic-pricing-breakdown.tsx | 80 +- .../pricing/components/empty-state.tsx | 4 +- .../src/features/pricing/components/index.ts | 6 +- .../pricing/components/loading-skeleton.tsx | 124 ++-- .../pricing/components/model-card-grid.tsx | 25 +- .../pricing/components/model-card.tsx | 387 +++++----- .../pricing/components/model-details-api.tsx | 22 +- .../pricing/components/model-details-apps.tsx | 36 +- .../components/model-details-performance.tsx | 10 +- .../model-details-uptime-sparkline.tsx | 14 +- .../pricing/components/model-details.tsx | 570 +++++++------- .../pricing/components/model-perf-badge.tsx | 6 +- .../pricing/components/pricing-columns.tsx | 591 ++++++++------- .../pricing/components/pricing-sidebar.tsx | 76 +- .../pricing/components/pricing-table.tsx | 41 +- .../pricing/components/pricing-toolbar.tsx | 265 ++++--- .../pricing/components/search-bar.tsx | 31 +- web/default/src/features/pricing/constants.ts | 8 +- .../src/features/pricing/hooks/use-filters.ts | 41 +- web/default/src/features/pricing/index.tsx | 261 ++++--- .../components/checkin-calendar-card.tsx | 152 ++-- .../dialogs/access-token-dialog.tsx | 5 +- .../dialogs/change-password-dialog.tsx | 4 +- .../dialogs/delete-account-dialog.tsx | 6 +- .../components/dialogs/email-bind-dialog.tsx | 19 +- .../dialogs/telegram-bind-dialog.tsx | 4 +- .../dialogs/two-fa-backup-dialog.tsx | 48 +- .../dialogs/two-fa-disable-dialog.tsx | 6 +- .../dialogs/two-fa-setup-dialog.tsx | 20 +- .../components/language-preferences-card.tsx | 39 +- .../{passkey-row.tsx => passkey-card.tsx} | 231 +++--- .../profile/components/profile-header.tsx | 89 ++- .../components/profile-security-card.tsx | 129 ++-- .../components/profile-settings-card.tsx | 106 +++ .../components/sidebar-modules-card.tsx | 144 ++-- .../account-bindings-tab.tsx} | 246 +++--- .../notification-tab.tsx} | 186 ++--- .../profile/components/two-fa-card.tsx | 186 +++++ .../profile/components/two-fa-row.tsx | 122 --- web/default/src/features/profile/index.tsx | 86 +-- .../rankings/components/growth-text.tsx | 11 +- .../components/market-share-section.tsx | 6 +- .../rankings/components/model-leaderboard.tsx | 10 +- .../rankings/components/models-section.tsx | 6 +- .../rankings/components/pulse-section.tsx | 12 +- .../rankings/components/rankings-hero.tsx | 86 ++- web/default/src/features/rankings/index.tsx | 99 +-- .../src/features/redemption-codes/api.ts | 4 +- .../components/data-table-bulk-actions.tsx | 1 + .../components/data-table-row-actions.tsx | 2 +- .../components/redemptions-columns.tsx | 90 +-- .../components/redemptions-delete-dialog.tsx | 2 +- .../components/redemptions-mutate-drawer.tsx | 8 +- .../redemptions-primary-buttons.tsx | 5 +- .../components/redemptions-table.tsx | 9 +- .../features/redemption-codes/constants.ts | 5 +- .../features/setup/components/admin-step.tsx | 6 +- .../setup/components/complete-step.tsx | 8 +- .../setup/components/database-step.tsx | 22 +- .../setup/components/step-navigation.tsx | 2 +- .../components/data-table-row-actions.tsx | 2 +- .../dialogs/subscription-purchase-dialog.tsx | 10 +- .../dialogs/user-subscriptions-dialog.tsx | 47 +- .../components/subscriptions-columns.tsx | 89 +-- .../subscriptions-mutate-drawer.tsx | 20 +- .../subscriptions-primary-buttons.tsx | 8 +- .../components/subscriptions-table.tsx | 1 - .../components/system-instances-panel.tsx | 98 +-- .../components/system-tasks-panel.tsx | 227 +++--- .../src/features/system-info/index.tsx | 6 +- .../auth/bot-protection-section.tsx | 2 +- .../components/discovery-button.tsx | 3 +- .../components/preset-selector.tsx | 6 +- .../components/provider-form-dialog.tsx | 23 +- .../components/provider-table.tsx | 18 +- .../custom-oauth/custom-oauth-section.tsx | 3 +- .../system-settings/auth/oauth-section.tsx | 12 +- .../system-settings/auth/passkey-section.tsx | 18 +- .../components/form-dirty-indicator.tsx | 7 +- .../components/settings-page-context.tsx | 4 +- .../content/announcements-section.tsx | 67 +- .../content/api-info-section.tsx | 42 +- .../system-settings/content/chat-dialog.tsx | 4 +- .../content/chat-settings-section.tsx | 7 +- .../content/chat-settings-visual-editor.tsx | 4 +- .../content/dashboard-section.tsx | 18 +- .../system-settings/content/faq-section.tsx | 14 +- .../content/uptime-kuma-section.tsx | 12 +- .../general/channel-affinity/index.tsx | 44 +- .../channel-affinity/rule-editor-dialog.tsx | 23 +- .../general/checkin-settings-section.tsx | 2 +- .../general/pricing-section.tsx | 18 +- .../general/quota-settings-section.tsx | 2 +- .../general/system-info-section.tsx | 18 +- .../integrations/amount-discount-dialog.tsx | 10 +- .../amount-discount-visual-editor.tsx | 9 +- .../amount-options-visual-editor.tsx | 34 +- .../integrations/creem-product-dialog.tsx | 20 +- .../creem-products-visual-editor.tsx | 6 +- .../integrations/email-settings-section.tsx | 2 +- .../ionet-deployment-settings-section.tsx | 6 +- .../monitoring-settings-section.tsx | 18 +- .../integrations/payment-method-dialog.tsx | 6 +- .../payment-methods-visual-editor.tsx | 6 +- .../integrations/payment-settings-section.tsx | 28 +- .../waffo-pancake-settings-section.tsx | 20 +- .../integrations/waffo-settings-section.tsx | 6 +- .../integrations/worker-settings-section.tsx | 2 +- .../maintenance/log-settings-section.tsx | 25 +- .../maintenance/performance-section.tsx | 22 +- .../maintenance/update-checker-section.tsx | 2 +- .../models/channel-selector-dialog.tsx | 45 +- .../models/claude-settings-card.tsx | 2 +- .../models/conflict-confirm-dialog.tsx | 4 +- .../system-settings/models/constants.ts | 2 +- .../models/gemini-settings-card.tsx | 2 +- .../models/global-settings-card.tsx | 14 +- .../models/grok-settings-card.tsx | 2 +- .../models/group-ratio-form.tsx | 35 +- .../models/group-ratio-visual-editor.tsx | 54 +- .../models/group-special-usable-editor.tsx | 68 +- .../models/model-pricing-inputs.tsx | 2 +- .../models/model-pricing-sheet.tsx | 21 +- .../models/model-ratio-form.tsx | 12 +- .../models/model-ratio-table-columns.tsx | 27 +- .../models/model-ratio-visual-editor.tsx | 4 +- .../models/ratio-settings-card.tsx | 7 +- .../models/routing-reliability-section.tsx | 18 +- .../models/tiered-pricing-editor.tsx | 186 +++-- .../models/tool-price-settings.tsx | 14 +- .../models/upstream-ratio-sync-columns.tsx | 60 +- .../models/upstream-ratio-sync-table.tsx | 6 +- .../models/upstream-ratio-sync.tsx | 2 +- .../request-limits/rate-limit-dialog.tsx | 4 +- .../request-limits/rate-limit-section.tsx | 5 +- .../rate-limit-visual-editor.tsx | 4 +- .../request-limits/ssrf-section.tsx | 18 +- .../request-limits/token-limit-section.tsx | 2 +- .../components/columns/column-helpers.tsx | 92 +-- .../columns/common-logs-columns.tsx | 305 ++++---- .../columns/drawing-logs-columns.tsx | 81 +- .../components/columns/task-logs-columns.tsx | 236 +++--- .../components/common-logs-filter-bar.tsx | 8 +- .../components/common-logs-header-actions.tsx | 6 +- .../components/common-logs-stats.tsx | 34 +- .../compact-date-time-range-picker.tsx | 27 +- .../dialogs/audio-preview-dialog.tsx | 63 +- .../components/dialogs/details-dialog.tsx | 169 +++-- .../components/dialogs/fail-reason-dialog.tsx | 12 +- .../components/dialogs/prompt-dialog.tsx | 14 +- .../dialogs/task-details-dialog.tsx | 633 ---------------- .../components/logs-filter-toolbar.tsx | 233 +++++- .../usage-logs/components/model-badge.tsx | 89 +-- .../components/usage-logs-mobile-card.tsx | 446 +++++++---- .../components/usage-logs-table.tsx | 40 +- .../src/features/usage-logs/constants.ts | 110 ++- web/default/src/features/usage-logs/index.tsx | 4 +- .../src/features/usage-logs/lib/format.ts | 25 +- .../src/features/usage-logs/lib/mappers.ts | 19 - .../src/features/usage-logs/lib/status.ts | 8 +- web/default/src/features/usage-logs/types.ts | 7 - web/default/src/features/users/api.ts | 4 +- .../components/data-table-row-actions.tsx | 2 +- .../dialogs/user-binding-dialog.tsx | 16 +- .../users/components/user-quota-dialog.tsx | 5 +- .../users/components/users-columns.tsx | 132 ++-- .../users/components/users-mutate-drawer.tsx | 20 +- .../components/users-primary-buttons.tsx | 4 +- .../features/users/components/users-table.tsx | 20 +- web/default/src/features/users/constants.ts | 2 +- .../components/affiliate-rewards-card.tsx | 97 +-- .../components/creem-products-section.tsx | 38 +- .../dialogs/billing-history-dialog.tsx | 65 +- .../dialogs/creem-confirm-dialog.tsx | 2 +- .../dialogs/payment-confirm-dialog.tsx | 4 +- .../components/dialogs/transfer-dialog.tsx | 8 +- .../wallet/components/recharge-form-card.tsx | 543 ++++++++------ .../components/subscription-plans-card.tsx | 484 ++++++------ .../wallet/components/wallet-stats-card.tsx | 39 +- .../features/wallet/hooks/use-affiliate.ts | 2 +- .../wallet/hooks/use-billing-history.ts | 2 +- .../wallet/hooks/use-creem-payment.ts | 2 +- .../src/features/wallet/hooks/use-payment.ts | 21 +- .../features/wallet/hooks/use-redemption.ts | 2 +- .../wallet/hooks/use-waffo-pancake-payment.ts | 2 +- .../wallet/hooks/use-waffo-payment.ts | 2 +- web/default/src/features/wallet/index.tsx | 89 ++- .../src/features/wallet/lib/billing.ts | 6 +- .../src/features/wallet/lib/payment.ts | 4 +- web/default/src/features/wallet/lib/ui.tsx | 2 +- web/default/src/hooks/use-group-ratios.ts | 44 -- web/default/src/hooks/use-table-url-state.ts | 35 +- web/default/src/i18n/config.ts | 19 +- web/default/src/i18n/languages.ts | 11 +- web/default/src/i18n/locales/en.json | 51 +- web/default/src/i18n/locales/fr.json | 51 +- web/default/src/i18n/locales/ja.json | 51 +- web/default/src/i18n/locales/ru.json | 51 +- web/default/src/i18n/locales/vi.json | 51 +- web/default/src/i18n/locales/zh-TW.json | 51 +- web/default/src/i18n/locales/zh.json | 51 +- web/default/src/lib/avatar.ts | 27 +- web/default/src/lib/colors.ts | 61 +- web/default/src/lib/format.ts | 28 + web/default/src/lib/motion.ts | 78 +- web/default/src/main.tsx | 16 +- .../routes/_authenticated/chat/$chatId.tsx | 2 +- .../routes/_authenticated/models/$section.tsx | 4 +- .../_authenticated/redemption-codes/index.tsx | 2 +- web/default/src/styles/fonts.css | 134 ---- web/default/src/styles/index.css | 97 ++- web/default/src/styles/theme-presets.css | 24 +- web/default/src/styles/theme.css | 205 +---- web/default/src/tanstack-table.d.ts | 19 +- 512 files changed, 10188 insertions(+), 10268 deletions(-) delete mode 100644 web/default/src/components/data-table/core/badge-list-cell-context.ts delete mode 100644 web/default/src/components/data-table/layout/card-field.tsx delete mode 100644 web/default/src/components/data-table/toolbar/filter-panel.tsx delete mode 100644 web/default/src/components/design-system/README.md delete mode 100644 web/default/src/components/design-system/alert-dialog.tsx delete mode 100644 web/default/src/components/design-system/button.tsx delete mode 100644 web/default/src/components/design-system/combobox-input.tsx delete mode 100644 web/default/src/components/design-system/combobox.tsx delete mode 100644 web/default/src/components/design-system/command.tsx delete mode 100644 web/default/src/components/design-system/dialog.tsx delete mode 100644 web/default/src/components/design-system/input-group.tsx delete mode 100644 web/default/src/components/design-system/input.tsx delete mode 100644 web/default/src/components/design-system/pagination.tsx delete mode 100644 web/default/src/components/design-system/select.tsx delete mode 100644 web/default/src/components/design-system/sidebar.tsx delete mode 100644 web/default/src/components/design-system/table.tsx delete mode 100644 web/default/src/components/design-system/tabs.tsx delete mode 100644 web/default/src/components/design-system/toggle-group.tsx delete mode 100644 web/default/src/components/design-system/toggle.tsx delete mode 100644 web/default/src/components/layout/components/public-page-header.tsx create mode 100644 web/default/src/components/ui/dropdown-menu-events.ts create mode 100644 web/default/src/components/ui/dropdown-menu.test.tsx create mode 100644 web/default/src/config/fonts.ts create mode 100644 web/default/src/context/font-provider.tsx delete mode 100644 web/default/src/features/keys/components/api-key-card.tsx rename web/default/src/features/profile/components/{passkey-row.tsx => passkey-card.tsx} (52%) create mode 100644 web/default/src/features/profile/components/profile-settings-card.tsx rename web/default/src/features/profile/components/{connected-accounts-card.tsx => tabs/account-bindings-tab.tsx} (65%) rename web/default/src/features/profile/components/{notification-settings-card.tsx => tabs/notification-tab.tsx} (71%) create mode 100644 web/default/src/features/profile/components/two-fa-card.tsx delete mode 100644 web/default/src/features/profile/components/two-fa-row.tsx delete mode 100644 web/default/src/features/usage-logs/components/dialogs/task-details-dialog.tsx delete mode 100644 web/default/src/hooks/use-group-ratios.ts delete mode 100644 web/default/src/styles/fonts.css diff --git a/common/constants.go b/common/constants.go index ebca3b108b..87d212f997 100644 --- a/common/constants.go +++ b/common/constants.go @@ -80,7 +80,7 @@ var SessionCookieTrustedURLs []string var OptionMap map[string]string var OptionMapRWMutex sync.RWMutex -var ItemsPerPage = 20 +var ItemsPerPage = 10 var MaxRecentItems = 1000 var PasswordLoginEnabled = true diff --git a/controller/channel.go b/controller/channel.go index 21e5f0f5d7..a2b5687ab3 100644 --- a/controller/channel.go +++ b/controller/channel.go @@ -1488,7 +1488,7 @@ func ManageMultiKeys(c *gin.Context) { page = 1 } if pageSize <= 0 { - pageSize = common.ItemsPerPage + pageSize = 50 // Default page size } // Statistics for all keys (unchanged by filtering) diff --git a/web/bun.lock b/web/bun.lock index 1cd7f42e0d..d86f3a8b3f 100644 --- a/web/bun.lock +++ b/web/bun.lock @@ -83,6 +83,7 @@ "@tanstack/react-query": "^5.101.2", "@tanstack/react-router": "^1.170.17", "@tanstack/react-table": "^8.21.3", + "@tanstack/react-virtual": "^3.14.5", "@visactor/react-vchart": "^2.1.2", "@visactor/vchart": "^2.1.2", "ai": "^7.0.14", @@ -91,7 +92,6 @@ "class-variance-authority": "^0.7.1", "clsx": "catalog:", "cmdk": "^1.1.1", - "date-fns": "^4.4.0", "dayjs": "catalog:", "dompurify": "3.4.11", "i18next": "^26.3.4", @@ -102,6 +102,7 @@ "marked": "^18.0.5", "motion": "^12.42.2", "nanoid": "^5.1.16", + "next-themes": "^0.4.6", "qrcode.react": "catalog:", "react": "catalog:", "react-day-picker": "^10.0.1", @@ -111,7 +112,7 @@ "react-icons": "catalog:", "react-resizable-panels": "^4.12.0", "react-top-loading-bar": "^3.0.2", - "recharts": "3.8.0", + "recharts": "3.9.1", "shiki": "^4.3.0", "sonner": "^2.0.7", "sse.js": "catalog:", @@ -121,6 +122,7 @@ "tokenlens": "^1.3.1", "tw-animate-css": "^1.4.0", "use-stick-to-bottom": "^1.1.6", + "vaul": "^1.1.2", "zod": "^4.4.3", "zustand": "^5.0.14", }, @@ -956,6 +958,8 @@ "@tanstack/react-table": ["@tanstack/react-table@8.21.3", "", { "dependencies": { "@tanstack/table-core": "8.21.3" }, "peerDependencies": { "react": ">=16.8", "react-dom": ">=16.8" } }, "sha512-5nNMTSETP4ykGegmVkhjcS8tTLW6Vl4axfEGQN3v0zdHYbK4UfoqfPChclTrJ4EoK9QynqAu9oUf8VEmrpZ5Ww=="], + "@tanstack/react-virtual": ["@tanstack/react-virtual@3.14.5", "", { "dependencies": { "@tanstack/virtual-core": "3.17.3" }, "peerDependencies": { "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0", "react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" } }, "sha512-4EKRXh7zBLkbKbFmG3AUVkircuHd+7OdT1pocJSepxtfBd3qnrJgJ5rtPkRYyo9fmyVb2+pI2xPy5oYvMLQy6A=="], + "@tanstack/router-core": ["@tanstack/router-core@1.171.8", "", { "dependencies": { "@tanstack/history": "1.162.0", "cookie-es": "^3.0.0", "seroval": "^1.5.4", "seroval-plugins": "^1.5.4" } }, "sha512-PbrTBbofFcacrH3RLgHYILRqTFnAGq+gXrXoA/vo7qUSkJpSO4GWfLtrtCahD4VayzRm19IPwcjPPLEugag6pw=="], "@tanstack/router-devtools-core": ["@tanstack/router-devtools-core@1.168.0", "", { "dependencies": { "clsx": "^2.1.1", "goober": "^2.1.16" }, "peerDependencies": { "@tanstack/router-core": "^1.170.0", "csstype": "^3.0.10" }, "optionalPeers": ["csstype"] }, "sha512-wQoQhlBK7nlZgqzaqdYXKWNTpdHdsaREdaPhFZVH0/Ador+F+eM3/NF2i3f2LPeS0GgKraZUQXe1Q/1+KHyEYg=="], @@ -970,6 +974,8 @@ "@tanstack/table-core": ["@tanstack/table-core@8.21.3", "", {}, "sha512-ldZXEhOBb8Is7xLs01fR3YEc3DERiz5silj8tnGkFZytt1abEvl/GhUmCE0PMLaMPTa3Jk4HbKmRlHmu+gCftg=="], + "@tanstack/virtual-core": ["@tanstack/virtual-core@3.17.3", "", {}, "sha512-8Np/TFELpI0ySuJoVmjvOrQYXH/8sTX0Biv9szhFhY39xOdAAY+smrMxjxOum/ux3eM8MUJQsEJ0/R0UpvC8dw=="], + "@tanstack/virtual-file-routes": ["@tanstack/virtual-file-routes@1.162.0", "", {}, "sha512-uhOeFyxLcU41HzvrxsGpiWdcMbScY1EDgbZ5K7DVRMYInbLYWAC0EA/kx9wXAoSM8q82bUG2hRl8+EAjE6XAbA=="], "@tiptap/core": ["@tiptap/core@3.24.0", "", { "peerDependencies": { "@tiptap/pm": "3.24.0" } }, "sha512-GTAsXAI32p4hEZgPzvUv2RPrObxamy9AFhmhG10fXSvN/cDUs8naEYVIqDV3Sh99jMwQEbTFKW1E1mcspsY6ow=="], @@ -1854,7 +1860,7 @@ "ignore": ["ignore@5.3.2", "", {}, "sha512-hsBTNUqQTDwkWtcdYI2i06Y/nUBEsNEDJKjWdigLvegy8kDuJAS8uRlpkkcQpyEXL0Z/pjDy5HBmMjRCJ2gq+g=="], - "immer": ["immer@10.2.0", "", {}, "sha512-d/+XTN3zfODyjr89gM3mPq1WNX2B8pYsu7eORitdwyA2sBubnTl3laYlBk4sXY5FUa5qTZGBDPJICVbvqzjlbw=="], + "immer": ["immer@11.1.8", "", {}, "sha512-/tbkHMW7y10Lx6i1crLjD4/OhNkRG+Fo7byZHtah0547nIeXYcpIXaUh0IAQY6gO5459qpGGYapcEOHtFXkIuA=="], "import-fresh": ["import-fresh@3.3.1", "", { "dependencies": { "parent-module": "^1.0.0", "resolve-from": "^4.0.0" } }, "sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ=="], @@ -2242,6 +2248,8 @@ "newapi-web": ["newapi-web@workspace:default"], + "next-themes": ["next-themes@0.4.6", "", { "peerDependencies": { "react": "^16.8 || ^17 || ^18 || ^19 || ^19.0.0-rc", "react-dom": "^16.8 || ^17 || ^18 || ^19 || ^19.0.0-rc" } }, "sha512-pZvgD5L0IEvX5/9GWyHMf3m8BKiVQwsCMHfoFosXtXBMnaS0ZnIJ9ST4b4NqLVKDEm8QBxoNNGNaBv2JNF6XNA=="], + "node-releases": ["node-releases@2.0.46", "", {}, "sha512-GYVXHE2KnrzAfsAjl4uP++evGFCrAU1jta4ubEjIG7YWt/64Gqv66a30yKwWczVjA6j3bM4nBwH7Pk1JmDHaxQ=="], "normalize-path": ["normalize-path@3.0.0", "", {}, "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA=="], @@ -2530,7 +2538,7 @@ "recast": ["recast@0.23.11", "", { "dependencies": { "ast-types": "^0.16.1", "esprima": "~4.0.0", "source-map": "~0.6.1", "tiny-invariant": "^1.3.3", "tslib": "^2.0.1" } }, "sha512-YTUo+Flmw4ZXiWfQKGcwwc11KnoRAYgzAE2E7mXKCjSviTKShtxBsN6YUUBB2gtaBzKzeKunxhUwNHQuRryhWA=="], - "recharts": ["recharts@3.8.0", "", { "dependencies": { "@reduxjs/toolkit": "^1.9.0 || 2.x.x", "clsx": "^2.1.1", "decimal.js-light": "^2.5.1", "es-toolkit": "^1.39.3", "eventemitter3": "^5.0.1", "immer": "^10.1.1", "react-redux": "8.x.x || 9.x.x", "reselect": "5.1.1", "tiny-invariant": "^1.3.3", "use-sync-external-store": "^1.2.2", "victory-vendor": "^37.0.2" }, "peerDependencies": { "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0", "react-dom": "^16.0.0 || ^17.0.0 || ^18.0.0 || ^19.0.0", "react-is": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" } }, "sha512-Z/m38DX3L73ExO4Tpc9/iZWHmHnlzWG4njQbxsF5aSjwqmHNDDIm0rdEBArkwsBvR8U6EirlEHiQNYWCVh9sGQ=="], + "recharts": ["recharts@3.9.1", "", { "dependencies": { "@reduxjs/toolkit": "^1.9.0 || 2.x.x", "clsx": "^2.1.1", "decimal.js-light": "^2.5.1", "es-toolkit": "^1.39.3", "eventemitter3": "^5.0.1", "immer": "^11.1.8", "react-redux": "8.x.x || 9.x.x", "reselect": "5.2.0", "tiny-invariant": "^1.3.3", "use-sync-external-store": "^1.2.2", "victory-vendor": "^37.0.2" }, "peerDependencies": { "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0", "react-dom": "^16.0.0 || ^17.0.0 || ^18.0.0 || ^19.0.0", "react-is": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" } }, "sha512-WMcwlXcB7l+BbxiEdyClkG+1sxrMHNZpzT577LEvU4+rXPd8oTAy1wXk72hnk2KOOmxuLvw3z5DtXT7HEAydtg=="], "recma-build-jsx": ["recma-build-jsx@1.0.0", "", { "dependencies": { "@types/estree": "^1.0.0", "estree-util-build-jsx": "^3.0.0", "vfile": "^6.0.0" } }, "sha512-8GtdyqaBcDfva+GUKDr3nev3VpKAhup1+RvkMvUxURHpW7QyIvk9F5wz7Vzo06CEMSilw6uArgRqhpiUcWp8ew=="], @@ -2582,7 +2590,7 @@ "require-from-string": ["require-from-string@2.0.2", "", {}, "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw=="], - "reselect": ["reselect@5.1.1", "", {}, "sha512-K/BG6eIky/SBpzfHZv/dd+9JBFiS4SWV7FIujVyJRux6e45+73RaUHXLmIR1f7WOMaQ0U1km6qwklRQxpJJY0w=="], + "reselect": ["reselect@5.2.0", "", {}, "sha512-AgZ3UOZm3YndfrJ4OYjgrT7bmCm/1iqkjvEfH/oYjzh6PD2qw4QuT3jjnXIrpdt4MTpMXclMT3lXbmRY+XRakw=="], "resize-observer-polyfill": ["resize-observer-polyfill@1.5.1", "", {}, "sha512-LwZrotdHOo12nQuZlHEmtuXdqGoOD0OhaxopaNFxWzInpEgaLWoVuAMbTzixuosCx2nEG58ngzW3vxdWoxIgdg=="], @@ -2870,6 +2878,8 @@ "vary": ["vary@1.1.2", "", {}, "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg=="], + "vaul": ["vaul@1.1.2", "", { "dependencies": { "@radix-ui/react-dialog": "^1.1.1" }, "peerDependencies": { "react": "^16.8 || ^17.0 || ^18.0 || ^19.0.0 || ^19.0.0-rc", "react-dom": "^16.8 || ^17.0 || ^18.0 || ^19.0.0 || ^19.0.0-rc" } }, "sha512-ZFkClGpWyI2WUQjdLJ/BaGuV6AVQiJ3uELGk3OYtP+B6yCO7Cmn9vPFXVJkRaGkOJu3m8bQMgtyzNHixULceQA=="], + "vfile": ["vfile@6.0.3", "", { "dependencies": { "@types/unist": "^3.0.0", "vfile-message": "^4.0.0" } }, "sha512-KzIbH/9tXat2u30jf+smMwFCsno4wHVdNmzFyL+T/L3UGqqk6JKfVqOFOZEpZSHADH1k40ab6NUIXZq422ov3Q=="], "vfile-location": ["vfile-location@5.0.3", "", { "dependencies": { "@types/unist": "^3.0.0", "vfile": "^6.0.0" } }, "sha512-5yXvWDEgqeiYiBe1lbxYF7UMAIm/IcopxMHrMQDq3nvKcjPKIhZklUKL+AE7J7uApI4kwe2snsK+eI6UTj9EHg=="], @@ -2916,8 +2926,6 @@ "zwitch": ["zwitch@2.0.4", "", {}, "sha512-bXE4cR/kVZhKZX/RjPEflHaKVhUVl85noU3v6b8apfQEc1x4A+zBxjZ4lN8LqGd6WZ3dl98pY4o717VFmoPp+A=="], - "@base-ui/utils/reselect": ["reselect@5.2.0", "", {}, "sha512-AgZ3UOZm3YndfrJ4OYjgrT7bmCm/1iqkjvEfH/oYjzh6PD2qw4QuT3jjnXIrpdt4MTpMXclMT3lXbmRY+XRakw=="], - "@codemirror/autocomplete/@codemirror/view": ["@codemirror/view@6.43.3", "", { "dependencies": { "@codemirror/state": "^6.7.0", "crelt": "^1.0.6", "style-mod": "^4.1.0", "w3c-keyname": "^2.2.4" } }, "sha512-MwEwCAr/o0agJefhC2+reBv5kfOQpMcDRUNQrRYZgWlhH8IwQcerMZrpqWyUFSyO0ebgN2cnh/w87F7G4BGSng=="], "@codemirror/lang-html/@codemirror/view": ["@codemirror/view@6.43.3", "", { "dependencies": { "@codemirror/state": "^6.7.0", "crelt": "^1.0.6", "style-mod": "^4.1.0", "w3c-keyname": "^2.2.4" } }, "sha512-MwEwCAr/o0agJefhC2+reBv5kfOQpMcDRUNQrRYZgWlhH8IwQcerMZrpqWyUFSyO0ebgN2cnh/w87F7G4BGSng=="], @@ -2966,8 +2974,6 @@ "@lobehub/ui/@shikijs/core": ["@shikijs/core@4.1.0", "", { "dependencies": { "@shikijs/primitive": "4.1.0", "@shikijs/types": "4.1.0", "@shikijs/vscode-textmate": "^10.0.2", "@types/hast": "^3.0.4", "hast-util-to-html": "^9.0.5" } }, "sha512-jLJtSJeuFffqX6/inRE1zqU5aFv2hrszvYgq3OjbAgFRZiWv7abKMDdQzYxuSDfmUPQozZvI/kuy6VMTvnvqTQ=="], - "@lobehub/ui/immer": ["immer@11.1.8", "", {}, "sha512-/tbkHMW7y10Lx6i1crLjD4/OhNkRG+Fo7byZHtah0547nIeXYcpIXaUh0IAQY6gO5459qpGGYapcEOHtFXkIuA=="], - "@lobehub/ui/katex": ["katex@0.16.47", "", { "dependencies": { "commander": "^8.3.0" }, "bin": { "katex": "cli.js" } }, "sha512-Eeo8Ys1doU1z+x8AZsPpQu+p/QcZBI5PeOo7QGQdy2x2m0MU/hYagBbGOmXwr5KVbEfVuWv9LpnQWeehogurjg=="], "@lobehub/ui/lucide-react": ["lucide-react@1.17.0", "", { "peerDependencies": { "react": "^16.5.1 || ^17.0.0 || ^18.0.0 || ^19.0.0" } }, "sha512-9FA9evdox/JQL5PT57fdA1x/yg8T7knJ98+zjTL3UfKza6pflQUUh3XtaQIHKvnsJw1lmsEyHVlt5jchYxOQ5w=="], @@ -3010,7 +3016,7 @@ "@rc-component/trigger/@rc-component/portal": ["@rc-component/portal@2.2.0", "", { "dependencies": { "@rc-component/util": "^1.2.1", "clsx": "^2.1.1" }, "peerDependencies": { "react": ">=18.0.0", "react-dom": ">=18.0.0" } }, "sha512-oc6FlA+uXCMiwArHsJyHcIkX4q6uKyndrPol2eWX8YPkAnztHOPsFIRtmWG4BMlGE5h7YIRE3NiaJ5VS8Lb1QQ=="], - "@reduxjs/toolkit/immer": ["immer@11.1.8", "", {}, "sha512-/tbkHMW7y10Lx6i1crLjD4/OhNkRG+Fo7byZHtah0547nIeXYcpIXaUh0IAQY6gO5459qpGGYapcEOHtFXkIuA=="], + "@reduxjs/toolkit/reselect": ["reselect@5.1.1", "", {}, "sha512-K/BG6eIky/SBpzfHZv/dd+9JBFiS4SWV7FIujVyJRux6e45+73RaUHXLmIR1f7WOMaQ0U1km6qwklRQxpJJY0w=="], "@rspack/binding-wasm32-wasi/@napi-rs/wasm-runtime": ["@napi-rs/wasm-runtime@1.1.6", "", { "dependencies": { "@tybys/wasm-util": "^0.10.3" }, "peerDependencies": { "@emnapi/core": "^1.7.1", "@emnapi/runtime": "^1.7.1" } }, "sha512-ZLv/JdUfkvOy9eCnnBaGfiO+XimbjebAeO+MRQqD/B+FR1tnRN0tpKSJHRbE8sFfS6aqsXZ67TQjfwfsxULVbg=="], @@ -3456,6 +3462,8 @@ "type-is/mime-types/mime-db": ["mime-db@1.54.0", "", {}, "sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ=="], + "@lobehub/ui/@base-ui/react/@base-ui/utils/reselect": ["reselect@5.1.1", "", {}, "sha512-K/BG6eIky/SBpzfHZv/dd+9JBFiS4SWV7FIujVyJRux6e45+73RaUHXLmIR1f7WOMaQ0U1km6qwklRQxpJJY0w=="], + "@lobehub/ui/motion/framer-motion/motion-dom": ["motion-dom@12.40.0", "", { "dependencies": { "motion-utils": "^12.39.0" } }, "sha512-HxU3ZaBwNPVQUBQf1xxgq+7JrPNZvjLVxgbpEZL7RrWJnsxOf0/OM+yrHG9ogLQ31Do/r57Oz2gQWPK+6q62mg=="], "@ts-morph/common/minimatch/brace-expansion/balanced-match": ["balanced-match@4.0.4", "", {}, "sha512-BLrgEcRTwX2o6gGxGOCNyMvGSp35YofuYzw9h1IMTRmKqttAZZVU67bdb9Pr2vUHA8+j3i2tJfjO6C6+4myGTA=="], diff --git a/web/classic/src/components/settings/ChannelSelectorModal.jsx b/web/classic/src/components/settings/ChannelSelectorModal.jsx index 9879c392c3..165aafafd5 100644 --- a/web/classic/src/components/settings/ChannelSelectorModal.jsx +++ b/web/classic/src/components/settings/ChannelSelectorModal.jsx @@ -59,7 +59,7 @@ const ChannelSelectorModal = forwardRef( ) => { const [searchText, setSearchText] = useState(''); const [currentPage, setCurrentPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); const isMobile = useIsMobile(); const [filteredData, setFilteredData] = useState([]); diff --git a/web/classic/src/components/table/channels/modals/MultiKeyManageModal.jsx b/web/classic/src/components/table/channels/modals/MultiKeyManageModal.jsx index 746ae5d4fd..fa7870dada 100644 --- a/web/classic/src/components/table/channels/modals/MultiKeyManageModal.jsx +++ b/web/classic/src/components/table/channels/modals/MultiKeyManageModal.jsx @@ -58,7 +58,7 @@ const MultiKeyManageModal = ({ visible, onCancel, channel, onRefresh }) => { // Pagination states const [currentPage, setCurrentPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); const [total, setTotal] = useState(0); const [totalPages, setTotalPages] = useState(0); @@ -99,7 +99,7 @@ const MultiKeyManageModal = ({ visible, onCancel, channel, onRefresh }) => { setKeyStatusList(data.keys || []); setTotal(data.total || 0); setCurrentPage(data.page || 1); - setPageSize(data.page_size || 20); + setPageSize(data.page_size || 10); setTotalPages(data.total_pages || 0); // Update statistics (these are always the overall statistics) diff --git a/web/classic/src/components/table/users/modals/UserSubscriptionsModal.jsx b/web/classic/src/components/table/users/modals/UserSubscriptionsModal.jsx index 47c68b703f..455f7b1880 100644 --- a/web/classic/src/components/table/users/modals/UserSubscriptionsModal.jsx +++ b/web/classic/src/components/table/users/modals/UserSubscriptionsModal.jsx @@ -84,7 +84,7 @@ const UserSubscriptionsModal = ({ visible, onCancel, user, t, onSuccess }) => { const [subs, setSubs] = useState([]); const [currentPage, setCurrentPage] = useState(1); - const pageSize = 20; + const pageSize = 10; const planTitleMap = useMemo(() => { const map = new Map(); diff --git a/web/classic/src/components/topup/modals/TopupHistoryModal.jsx b/web/classic/src/components/topup/modals/TopupHistoryModal.jsx index b01baf72fd..1abd45df62 100644 --- a/web/classic/src/components/topup/modals/TopupHistoryModal.jsx +++ b/web/classic/src/components/topup/modals/TopupHistoryModal.jsx @@ -61,7 +61,7 @@ const TopupHistoryModal = ({ visible, onCancel, t }) => { const [topups, setTopups] = useState([]); const [total, setTotal] = useState(0); const [page, setPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); const [keyword, setKeyword] = useState(''); const isMobile = useIsMobile(); diff --git a/web/classic/src/constants/channel.constants.js b/web/classic/src/constants/channel.constants.js index 46879af7b1..278e756336 100644 --- a/web/classic/src/constants/channel.constants.js +++ b/web/classic/src/constants/channel.constants.js @@ -196,4 +196,4 @@ export const MODEL_FETCHABLE_CHANNEL_TYPES = new Set([ 1, 4, 14, 34, 17, 26, 27, 24, 47, 25, 20, 23, 31, 40, 42, 48, 43, ]); -export const MODEL_TABLE_PAGE_SIZE = 20; +export const MODEL_TABLE_PAGE_SIZE = 10; diff --git a/web/classic/src/constants/common.constant.js b/web/classic/src/constants/common.constant.js index f5398d9658..316356631d 100644 --- a/web/classic/src/constants/common.constant.js +++ b/web/classic/src/constants/common.constant.js @@ -17,7 +17,7 @@ along with this program. If not, see . For commercial licensing, please contact support@quantumnous.com */ -export const ITEMS_PER_PAGE = 20; // this value must keep same as the one defined in backend! +export const ITEMS_PER_PAGE = 10; // this value must keep same as the one defined in backend! export const DEFAULT_ENDPOINT = '/api/pricing'; diff --git a/web/classic/src/constants/dashboard.constants.js b/web/classic/src/constants/dashboard.constants.js index 337cdcf33b..7e930b479d 100644 --- a/web/classic/src/constants/dashboard.constants.js +++ b/web/classic/src/constants/dashboard.constants.js @@ -144,6 +144,6 @@ export const STORAGE_KEYS = { export const DEFAULTS = { PAGE_SIZE: 20, CHART_HEIGHT: 96, - MODEL_TABLE_PAGE_SIZE: 20, + MODEL_TABLE_PAGE_SIZE: 10, MAX_TREND_POINTS: 7, }; diff --git a/web/classic/src/hooks/subscriptions/useSubscriptionsData.jsx b/web/classic/src/hooks/subscriptions/useSubscriptionsData.jsx index 18b968f394..f426501b90 100644 --- a/web/classic/src/hooks/subscriptions/useSubscriptionsData.jsx +++ b/web/classic/src/hooks/subscriptions/useSubscriptionsData.jsx @@ -32,7 +32,7 @@ export const useSubscriptionsData = () => { // Pagination (client-side for now) const [activePage, setActivePage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); // Drawer states const [showEdit, setShowEdit] = useState(false); diff --git a/web/classic/src/index.css b/web/classic/src/index.css index 184f999cf1..387e248830 100644 --- a/web/classic/src/index.css +++ b/web/classic/src/index.css @@ -1021,22 +1021,6 @@ html.dark .with-pastel-balls::before { padding: 10px !important; } -/* Keep badge text complete and on one line. */ -.semi-tag { - flex-shrink: 0; - min-width: max-content; - max-width: none; - overflow: visible; - white-space: nowrap; -} - -.semi-tag-content { - max-width: none; - overflow: visible; - text-overflow: clip; - white-space: nowrap; -} - /* ==================== 使用日志: channel affinity tag ==================== */ .semi-tag.channel-affinity-tag { border: 1px solid rgba(var(--semi-cyan-5), 0.35); diff --git a/web/classic/src/pages/Setting/Chat/SettingsChats.jsx b/web/classic/src/pages/Setting/Chat/SettingsChats.jsx index a9d9ee1f05..fc1dae4cda 100644 --- a/web/classic/src/pages/Setting/Chat/SettingsChats.jsx +++ b/web/classic/src/pages/Setting/Chat/SettingsChats.jsx @@ -469,7 +469,7 @@ export default function SettingsChats(props) { dataSource={filteredConfigs} rowKey='id' pagination={{ - pageSize: 20, + pageSize: 10, showSizeChanger: false, showQuickJumper: true, showTotal: (total, range) => diff --git a/web/classic/src/pages/Setting/Dashboard/SettingsAPIInfo.jsx b/web/classic/src/pages/Setting/Dashboard/SettingsAPIInfo.jsx index 531d7e2841..8116cfc0fa 100644 --- a/web/classic/src/pages/Setting/Dashboard/SettingsAPIInfo.jsx +++ b/web/classic/src/pages/Setting/Dashboard/SettingsAPIInfo.jsx @@ -59,7 +59,7 @@ const SettingsAPIInfo = ({ options, refresh }) => { color: 'blue', }); const [currentPage, setCurrentPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); const [selectedRowKeys, setSelectedRowKeys] = useState([]); // 面板启用状态 state diff --git a/web/classic/src/pages/Setting/Dashboard/SettingsAnnouncements.jsx b/web/classic/src/pages/Setting/Dashboard/SettingsAnnouncements.jsx index 11f51da3e4..c61102f150 100644 --- a/web/classic/src/pages/Setting/Dashboard/SettingsAnnouncements.jsx +++ b/web/classic/src/pages/Setting/Dashboard/SettingsAnnouncements.jsx @@ -67,7 +67,7 @@ const SettingsAnnouncements = ({ options, refresh }) => { extra: '', }); const [currentPage, setCurrentPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); const [selectedRowKeys, setSelectedRowKeys] = useState([]); // 面板启用状态 diff --git a/web/classic/src/pages/Setting/Dashboard/SettingsFAQ.jsx b/web/classic/src/pages/Setting/Dashboard/SettingsFAQ.jsx index dfc81ebc62..3c6f696962 100644 --- a/web/classic/src/pages/Setting/Dashboard/SettingsFAQ.jsx +++ b/web/classic/src/pages/Setting/Dashboard/SettingsFAQ.jsx @@ -56,7 +56,7 @@ const SettingsFAQ = ({ options, refresh }) => { answer: '', }); const [currentPage, setCurrentPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); const [selectedRowKeys, setSelectedRowKeys] = useState([]); // 面板启用状态 diff --git a/web/classic/src/pages/Setting/Dashboard/SettingsUptimeKuma.jsx b/web/classic/src/pages/Setting/Dashboard/SettingsUptimeKuma.jsx index ec40c999e3..3f3d5dd8ef 100644 --- a/web/classic/src/pages/Setting/Dashboard/SettingsUptimeKuma.jsx +++ b/web/classic/src/pages/Setting/Dashboard/SettingsUptimeKuma.jsx @@ -56,7 +56,7 @@ const SettingsUptimeKuma = ({ options, refresh }) => { slug: '', }); const [currentPage, setCurrentPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); const [selectedRowKeys, setSelectedRowKeys] = useState([]); const [panelEnabled, setPanelEnabled] = useState(true); diff --git a/web/classic/src/pages/Setting/Ratio/UpstreamRatioSync.jsx b/web/classic/src/pages/Setting/Ratio/UpstreamRatioSync.jsx index 26e769dddd..20b0bdf318 100644 --- a/web/classic/src/pages/Setting/Ratio/UpstreamRatioSync.jsx +++ b/web/classic/src/pages/Setting/Ratio/UpstreamRatioSync.jsx @@ -122,7 +122,7 @@ export default function UpstreamRatioSync(props) { // 分页相关状态 const [currentPage, setCurrentPage] = useState(1); - const [pageSize, setPageSize] = useState(20); + const [pageSize, setPageSize] = useState(10); // 搜索相关状态 const [searchKeyword, setSearchKeyword] = useState(''); diff --git a/web/classic/src/pages/Setting/Ratio/hooks/useModelPricingEditorState.js b/web/classic/src/pages/Setting/Ratio/hooks/useModelPricingEditorState.js index 22c935f643..ba9efdfceb 100644 --- a/web/classic/src/pages/Setting/Ratio/hooks/useModelPricingEditorState.js +++ b/web/classic/src/pages/Setting/Ratio/hooks/useModelPricingEditorState.js @@ -23,7 +23,7 @@ import { splitBillingExprAndRequestRules, } from '../components/requestRuleExpr'; -export const PAGE_SIZE = 20; +export const PAGE_SIZE = 10; export const PRICE_SUFFIX = '$/1M tokens'; const EMPTY_CANDIDATE_MODEL_NAMES = []; diff --git a/web/default/.oxlintrc.json b/web/default/.oxlintrc.json index 8e607707c9..9faf2d7e32 100644 --- a/web/default/.oxlintrc.json +++ b/web/default/.oxlintrc.json @@ -44,33 +44,6 @@ "no-duplicate-imports": "error", "no-nested-ternary": "error", "no-new-wrappers": "error", - "no-restricted-imports": [ - "error", - { - "patterns": [ - { - "group": [ - "@/components/ui/alert-dialog", - "@/components/ui/button", - "@/components/ui/combobox", - "@/components/ui/combobox-input", - "@/components/ui/command", - "@/components/ui/dialog", - "@/components/ui/input", - "@/components/ui/input-group", - "@/components/ui/pagination", - "@/components/ui/select", - "@/components/ui/sidebar", - "@/components/ui/table", - "@/components/ui/tabs", - "@/components/ui/toggle", - "@/components/ui/toggle-group" - ], - "message": "Import policy-bearing controls from @/components/design-system so responsive sizing stays centralized." - } - ] - } - ], "no-regex-spaces": "error", "no-unsafe-finally": "warn", "no-unsafe-negation": "error", @@ -223,19 +196,6 @@ "react/only-export-components": "off" } }, - { - "files": ["src/components/design-system/**/*.{ts,tsx}"], - "rules": { - "no-restricted-imports": "off", - "react/only-export-components": [ - "error", - { - "allowConstantExport": true, - "allowExportNames": ["useComboboxAnchor", "useSidebar"] - } - ] - } - }, { "files": ["**/scripts/**/*.{js,mjs,cjs}"], "rules": { diff --git a/web/default/AGENTS.md b/web/default/AGENTS.md index 9605a6d352..4af5e86bfe 100644 --- a/web/default/AGENTS.md +++ b/web/default/AGENTS.md @@ -125,58 +125,10 @@ - 以 Tailwind 工具类为主,动态类名用 `cn()` 合并;非动态场景避免内联样式。 - 响应式采用移动优先与 Tailwind 断点(`sm:`、`md:`、`lg:` 等);主题与暗色用 CSS 变量与 `dark:`,自定义样式集中在 `src/styles/`,组件内尽量少写自定义 CSS。 -#### 3.10.1 设计系统纪律(强约束) - -以下规则为硬约束,代码评审与 AI 改动一律遵循;违反即为缺陷。 - -**颜色** - -- 后台界面(除 `features/home/` 营销页外)**禁止硬编码 Tailwind 调色板类**(如 `text-emerald-600`、`bg-amber-50`、`border-rose-200`),一律使用语义令牌:`success` / `warning` / `destructive` / `info` / `neutral`、`primary` / `muted` / `accent` / `border` / `ring`。暗色适配由令牌完成,禁止 `dark:text-emerald-400` 之类逐处覆写。 -- 状态色仅表达状态(成功/警告/错误/信息),不得用于装饰或分类;分类信息(模型名、分组名、渠道名等)一律中性呈现,身份靠文本与图标传达。`StatusBadge` 的 `autoColor` 已废弃为 neutral,禁止恢复字符串哈希取色。 -- 需要浅底状态胶囊时使用 `status-badge.tsx` 的 `tintedBadgeClassMap`,不要再手写 `bg-xxx-50 text-xxx-700 dark:...` 组合。 -- 图表用 `--chart-1..5`;用户头像身份色走 `getAvatarColorClass`。这两处是仅有的多色场景。 -- 禁止用 `!important`(`!text-*` 等)压制文字颜色/字号;若需要覆盖,说明层级设计有误,先修组件。 - -**排版** - -- 字体族只有两轨:正文 `--font-sans`(含 CJK 回退,勿删栈中中文字体)与 `--font-serif`(serif 主题轴)。`font-mono` 仅用于密钥、ID、代码、原始 JSON;**数字对齐一律 `tabular-nums`,不得再加 `font-mono`**。 -- 字号只用 `text-xs/sm/base/lg/xl/2xl`,**禁止任意值字号**(`text-[10px]`、`text-[11px]` 等;营销页除外)。 -- 字重只用 `font-medium`(强调/表头)与 `font-semibold`(标题/关键数值);后台正文与标题**禁用 `font-bold`**。 -- 标题三档契约:页题 `text-lg font-semibold tracking-tight`;卡片/区块题 `text-base font-semibold`;面板/小节题 `text-sm font-medium`。禁止响应式跳字号的标题(如 `text-base sm:text-lg`)。 -- 表头不使用 `uppercase + tracking-wider`。 - -**控件尺寸(移动优先响应式)** - -- `src/components/ui/` 是 shadcn CLI 管理的原始源码层:允许通过 `bunx --bun shadcn@latest add --dry-run/--diff` 审查并合并上游更新,但**禁止**在这里加入产品级响应式策略、业务语义或一次性样式。不得用 `--overwrite` 覆盖本地代码,除非用户明确批准。 -- `src/components/design-system/` 是产品设计系统适配层,只包装确实承载稳定跨站策略的控件(尺寸、产品级 variant、复合控件内部的策略传递);不要为了“统一入口”代理所有 shadcn 组件。业务代码对受管控件必须从该目录导入,`.oxlintrc.json` 的 `no-restricted-imports` 会阻止绕过边界。 -- 控件标准高度是响应式的:**手机(<640px)28px,桌面(`sm:` 起)32px**。断点由 `design-system` 适配层统一注入(`Button`/`Toggle` default 与 icon 档、`Input`、`InputGroup`、`SelectTrigger` default 档、`TabsList`、`Combobox`、`CommandInput`、分页、表头 `h-9 sm:h-10`),业务代码**不写**断点类即可获得正确尺寸。 -- 独立场景(工具栏、表单、对话框、卡片/列表行操作、页脚)一律用默认档,**禁止** `size='sm'`,也**禁止**用 `className` 写 `h-7`/`h-8`/`h-9`/`size-8` 等钉死尺寸——钉死的类会在某一断点上与内置的 `sm:h-8`/`sm:size-8` 打架(twMerge 不会跨断点去重)。 -- 密集场景(表格单元格内、行内编辑器一行多控件、紧凑抽屉行)统一 `size='sm'`(28px 恒定);微型场景用 `xs`(24px 恒定)。`sm`/`xs`/`icon-sm`/`icon-xs` 是**固定档**,不随断点缩放;需要"固定自定义尺寸"的特例(如覆盖层小按钮)应以固定档为基底再覆写,绝不以 default/icon 为基底。 -- 图标按钮用 `icon`(28→32px 响应式)/`icon-sm`(28px 恒定)/`icon-xs`(24px 恒定)并带 `aria-label`;禁止 `size-*`、`h-* w-*`、`p-0` 组合模拟。头部全局操作(侧栏开关/主题/语言/通知/头像)统一 `icon`。 -- CTA 档 `xl`(40→44px 响应式):auth 页主按钮(登录/注册/OTP/重置/OAuth/Passkey)与营销页 hero 按钮统一 `size='xl'`,禁止再写 `h-11`。 -- 确需自定义高度时必须**成对覆盖两个断点**:内容自适应写 `h-auto sm:h-auto`,特大输入写 `h-9 sm:h-10` 这类成对值;`min-h-*` 不与内置高度冲突可单独使用。flex-wrap 的 `TabsList` 用 `group-data-horizontal/tabs:h-auto sm:group-data-horizontal/tabs:h-auto`。 -- 手机端的“视觉紧凑”不得牺牲可操作性:所有指针目标至少满足 WCAG 2.2 AA 的 24×24 CSS px;相邻 28px 控件必须保留足够间距,主要提交/认证/高频操作优先使用 40px 的 `xl` 档。不要在手机端新增小于 `xs` 的交互目标。 -- 仅有例外:日历格(`--cell-size`)、OTP 输入格、营销页装饰元素。新增例外须在评审说明。 - -**圆角与阴影** - -- 圆角单源 `--radius`(默认 0.625rem),组件用派生档 `rounded-md/lg/xl`;禁止在业务代码里写死圆角像素或混用 `rounded-2xl`/`rounded-4xl` 表达同类容器。 -- 卡片边界「描边或投影二选一」:默认 `border`(或 Card 自带 ring),禁止再叠 `shadow-*`;`shadow` 只保留给浮层(popover/dropdown/dialog)。 - -**动效** - -- 后台界面禁止入场动画:无 stagger、无 translate/scale/blur 入场、无按钮按压缩放。页面切换只允许纯透明度 fade(见 `lib/motion.ts` 的 `pageEnter`)。`page-transition.tsx` 的 Stagger 系列组件已固化为纯容器,禁止恢复动画。 -- 允许的动效上限:颜色/透明度过渡 ≤150ms、骨架屏 shimmer、`Collapsible/Accordion` 展开、加载 spinner。装饰性动效只允许出现在 `features/home/`(landing)。 - -**徽章与图标** - -- 文本徽章统一 `StatusBadge`(五种语义 voice);模型/分组/渠道等实体徽章统一中性底(`border-border/60 bg-muted/30`)。不要新造第三种徽章样式。 -- 业务代码图标一律 `lucide-react`;`components/ui/` 由 shadcn 生成器维护(Hugeicons),不要手改基础组件图标库;AI 品牌图标用 `@lobehub/icons`(经 `getLobeIcon`)。 - ### 3.11 文件组织 - **功能模块**:置于 `src/features//`,内含 `components/`、`lib/`、`hooks/`,以及按需的 `api.ts`、`types.ts`、`constants.ts`、入口组件等。 -- **通用**:通用组件放 `src/components/`,其中 `components/ui/` 仅存 shadcn 原始源码、`components/design-system/` 存产品策略适配器;通用工具与类型放 `src/lib/`。组件文件 PascalCase,工具/类型文件 kebab-case 或 `types.ts`,类型使用 PascalCase 命名并 `export type`。 +- **通用**:通用组件放 `src/components/`,通用工具与类型放 `src/lib/`;组件文件 PascalCase,工具/类型文件 kebab-case 或 `types.ts`,类型使用 PascalCase 命名并 `export type`。 ### 3.12 可访问性 @@ -226,7 +178,3 @@ - **2026-01-29**:重组文档结构,合并重复内容,明确主次与交叉引用。 - **2026-01-31**:在 3.2 中补充「类型检查」要求:改动 TS/TSX 后须执行 typecheck 并修复至无错。 - **2026-06-21**:在 3.2 中补充「Lint 检查」要求:完成代码改动前须修复所涉及文件的所有 lint error。 -- **2026-07-11**:新增 3.10.1「设计系统纪律」:语义色硬约束(去彩虹徽章/硬编码调色板)、排版契约(字号/字重/标题三档/mono 边界)、圆角单源、后台零入场动效、徽章与图标单轨。 -- **2026-07-11**:3.10.1 新增「控件尺寸」:控件默认 32px(`h-8`)单一标准;独立场景禁用 `size='sm'` 与 `className` 高度硬改;密集行内统一 `sm`、微型 `xs`;图标按钮走 `icon/icon-sm/icon-xs` 档位。 -- **2026-07-11**:控件尺寸升级为移动优先响应式:设计系统统一手机 28px / 桌面 32px(default、icon 档随断点缩放,`sm`/`xs`/`icon-sm`/`icon-xs` 恒定);新增 CTA 档 `xl`(40→44px),auth 与 hero 主按钮统一迁入;调用点禁止钉死 `h-*`/`size-*`,自定义高度必须成对覆盖两个断点(如 `h-auto sm:h-auto`)。 -- **2026-07-11**:将响应式尺寸策略从 shadcn 原始源码迁至 `components/design-system/` 适配层;业务受管控件统一改从适配层导入,并由 lint 禁止绕过;`components/ui/` 恢复为可用 CLI `--diff` 维护的上游源码边界。 diff --git a/web/default/components.json b/web/default/components.json index 584672544b..4eaae3460d 100644 --- a/web/default/components.json +++ b/web/default/components.json @@ -18,7 +18,7 @@ "lib": "@/lib", "hooks": "@/hooks" }, - "menuColor": "default", + "menuColor": "inverted", "menuAccent": "subtle", "registries": { "@ai-elements": "https://registry.ai-sdk.dev/{name}.json" diff --git a/web/default/package.json b/web/default/package.json index 630f01100f..67906f26f4 100644 --- a/web/default/package.json +++ b/web/default/package.json @@ -34,6 +34,7 @@ "@tanstack/react-query": "^5.101.2", "@tanstack/react-router": "^1.170.17", "@tanstack/react-table": "^8.21.3", + "@tanstack/react-virtual": "^3.14.5", "@visactor/react-vchart": "^2.1.2", "@visactor/vchart": "^2.1.2", "ai": "^7.0.14", @@ -42,7 +43,6 @@ "class-variance-authority": "^0.7.1", "clsx": "catalog:", "cmdk": "^1.1.1", - "date-fns": "^4.4.0", "dayjs": "catalog:", "dompurify": "3.4.11", "i18next": "^26.3.4", @@ -53,6 +53,7 @@ "marked": "^18.0.5", "motion": "^12.42.2", "nanoid": "^5.1.16", + "next-themes": "^0.4.6", "qrcode.react": "catalog:", "react": "catalog:", "react-day-picker": "^10.0.1", @@ -62,7 +63,7 @@ "react-icons": "catalog:", "react-resizable-panels": "^4.12.0", "react-top-loading-bar": "^3.0.2", - "recharts": "3.8.0", + "recharts": "3.9.1", "shiki": "^4.3.0", "sonner": "^2.0.7", "sse.js": "catalog:", @@ -72,6 +73,7 @@ "tokenlens": "^1.3.1", "tw-animate-css": "^1.4.0", "use-stick-to-bottom": "^1.1.6", + "vaul": "^1.1.2", "zod": "^4.4.3", "zustand": "^5.0.14" }, diff --git a/web/default/src/components/ai-elements/actions.tsx b/web/default/src/components/ai-elements/actions.tsx index 93746fb849..9d3c2da433 100644 --- a/web/default/src/components/ai-elements/actions.tsx +++ b/web/default/src/components/ai-elements/actions.tsx @@ -20,7 +20,7 @@ For commercial licensing, please contact support@quantumnous.com import type { ComponentProps } from 'react' -import { Button } from '@/components/design-system/button' +import { Button } from '@/components/ui/button' import { Tooltip, TooltipContent, @@ -48,13 +48,13 @@ export const Action = ({ label, className, variant = 'ghost', - size = 'icon', + size = 'sm', ...props }: ActionProps) => { const button = (