mirror of
https://github.com/router-for-me/Cli-Proxy-API-Management-Center.git
synced 2026-02-02 02:40:50 +08:00
refactor(quota,auth): change page size selector to number input with range 3-30
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -12,6 +12,7 @@ CLAUDE.md
|
||||
AGENTS.md
|
||||
antigravity_usage.json
|
||||
codex_usage.json
|
||||
style.md
|
||||
|
||||
node_modules
|
||||
dist
|
||||
|
||||
@@ -19,6 +19,12 @@ type QuotaUpdater<T> = T | ((prev: T) => T);
|
||||
|
||||
type QuotaSetter<T> = (updater: QuotaUpdater<T>) => void;
|
||||
|
||||
const MIN_CARD_PAGE_SIZE = 3;
|
||||
const MAX_CARD_PAGE_SIZE = 30;
|
||||
|
||||
const clampCardPageSize = (value: number) =>
|
||||
Math.min(MAX_CARD_PAGE_SIZE, Math.max(MIN_CARD_PAGE_SIZE, Math.round(value)));
|
||||
|
||||
interface QuotaPaginationState<T> {
|
||||
pageSize: number;
|
||||
totalPages: number;
|
||||
@@ -34,7 +40,7 @@ interface QuotaPaginationState<T> {
|
||||
|
||||
const useQuotaPagination = <T,>(items: T[], defaultPageSize = 6): QuotaPaginationState<T> => {
|
||||
const [page, setPage] = useState(1);
|
||||
const [pageSize, setPageSizeState] = useState(defaultPageSize);
|
||||
const [pageSize, setPageSizeState] = useState(() => clampCardPageSize(defaultPageSize));
|
||||
const [loading, setLoadingState] = useState(false);
|
||||
const [loadingScope, setLoadingScope] = useState<'page' | 'all' | null>(null);
|
||||
|
||||
@@ -51,7 +57,7 @@ const useQuotaPagination = <T,>(items: T[], defaultPageSize = 6): QuotaPaginatio
|
||||
}, [items, currentPage, pageSize]);
|
||||
|
||||
const setPageSize = useCallback((size: number) => {
|
||||
setPageSizeState(size);
|
||||
setPageSizeState(clampCardPageSize(size));
|
||||
setPage(1);
|
||||
}, []);
|
||||
|
||||
@@ -183,17 +189,19 @@ export function QuotaSection<TState extends QuotaStatusState, TData>({
|
||||
<div className={config.controlsClassName}>
|
||||
<div className={config.controlClassName}>
|
||||
<label>{t('auth_files.page_size_label')}</label>
|
||||
<select
|
||||
<input
|
||||
className={styles.pageSizeSelect}
|
||||
type="number"
|
||||
min={MIN_CARD_PAGE_SIZE}
|
||||
max={MAX_CARD_PAGE_SIZE}
|
||||
step={1}
|
||||
value={pageSize}
|
||||
onChange={(e) => setPageSize(Number(e.target.value) || 6)}
|
||||
>
|
||||
<option value={6}>6</option>
|
||||
<option value={9}>9</option>
|
||||
<option value={12}>12</option>
|
||||
<option value={18}>18</option>
|
||||
<option value={24}>24</option>
|
||||
</select>
|
||||
onChange={(e) => {
|
||||
const value = e.currentTarget.valueAsNumber;
|
||||
if (!Number.isFinite(value)) return;
|
||||
setPageSize(value);
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
<div className={config.controlClassName}>
|
||||
<label>{t('common.info')}</label>
|
||||
|
||||
@@ -124,7 +124,7 @@
|
||||
background-color: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
cursor: text;
|
||||
height: 38px;
|
||||
box-sizing: border-box;
|
||||
|
||||
|
||||
@@ -78,6 +78,11 @@ const OAUTH_PROVIDER_PRESETS = [
|
||||
];
|
||||
|
||||
const OAUTH_PROVIDER_EXCLUDES = new Set(['all', 'unknown', 'empty']);
|
||||
const MIN_CARD_PAGE_SIZE = 3;
|
||||
const MAX_CARD_PAGE_SIZE = 30;
|
||||
|
||||
const clampCardPageSize = (value: number) =>
|
||||
Math.min(MAX_CARD_PAGE_SIZE, Math.max(MIN_CARD_PAGE_SIZE, Math.round(value)));
|
||||
|
||||
interface ExcludedFormState {
|
||||
provider: string;
|
||||
@@ -172,10 +177,10 @@ export function AuthFilesPage() {
|
||||
const [modelsFileType, setModelsFileType] = useState('');
|
||||
const [modelsError, setModelsError] = useState<'unsupported' | null>(null);
|
||||
|
||||
// OAuth 排除模型相关
|
||||
const [excluded, setExcluded] = useState<Record<string, string[]>>({});
|
||||
// OAuth 排除模型相关
|
||||
const [excluded, setExcluded] = useState<Record<string, string[]>>({});
|
||||
const [excludedError, setExcludedError] = useState<'unsupported' | null>(null);
|
||||
const [excludedModalOpen, setExcludedModalOpen] = useState(false);
|
||||
const [excludedModalOpen, setExcludedModalOpen] = useState(false);
|
||||
const [excludedForm, setExcludedForm] = useState<ExcludedFormState>({ provider: '', modelsText: '' });
|
||||
const [savingExcluded, setSavingExcluded] = useState(false);
|
||||
|
||||
@@ -184,6 +189,13 @@ export function AuthFilesPage() {
|
||||
const excludedUnsupportedRef = useRef(false);
|
||||
|
||||
const disableControls = connectionStatus !== 'connected';
|
||||
|
||||
const handlePageSizeChange = (event: React.ChangeEvent<HTMLInputElement>) => {
|
||||
const value = event.currentTarget.valueAsNumber;
|
||||
if (!Number.isFinite(value)) return;
|
||||
setPageSize(clampCardPageSize(value));
|
||||
setPage(1);
|
||||
};
|
||||
|
||||
// 格式化修改时间
|
||||
const formatModified = (item: AuthFileItem): string => {
|
||||
@@ -853,23 +865,18 @@ export function AuthFilesPage() {
|
||||
placeholder={t('auth_files.search_placeholder')}
|
||||
/>
|
||||
</div>
|
||||
<div className={styles.filterItem}>
|
||||
<label>{t('auth_files.page_size_label')}</label>
|
||||
<select
|
||||
className={styles.pageSizeSelect}
|
||||
value={pageSize}
|
||||
onChange={(e) => {
|
||||
setPageSize(Number(e.target.value) || 9);
|
||||
setPage(1);
|
||||
}}
|
||||
>
|
||||
<option value={6}>6</option>
|
||||
<option value={9}>9</option>
|
||||
<option value={12}>12</option>
|
||||
<option value={18}>18</option>
|
||||
<option value={24}>24</option>
|
||||
</select>
|
||||
</div>
|
||||
<div className={styles.filterItem}>
|
||||
<label>{t('auth_files.page_size_label')}</label>
|
||||
<input
|
||||
className={styles.pageSizeSelect}
|
||||
type="number"
|
||||
min={MIN_CARD_PAGE_SIZE}
|
||||
max={MAX_CARD_PAGE_SIZE}
|
||||
step={1}
|
||||
value={pageSize}
|
||||
onChange={handlePageSizeChange}
|
||||
/>
|
||||
</div>
|
||||
<div className={styles.filterItem}>
|
||||
<label>{t('common.info')}</label>
|
||||
<div className={styles.statsInfo}>
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
background-color: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
cursor: text;
|
||||
height: 38px;
|
||||
box-sizing: border-box;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user