diff --git a/packages/components/src/theme/index.tsx b/packages/components/src/theme/index.tsx
index b4c6dda..279e96b 100644
--- a/packages/components/src/theme/index.tsx
+++ b/packages/components/src/theme/index.tsx
@@ -1,6 +1,6 @@
import { createTheme, Shadows, ThemeOptions } from '@mui/material/styles';
import { useTheme as useMuiTheme, Theme } from '@mui/material/styles';
-import { amber } from '@mui/material/colors';
+import { amber, red } from '@mui/material/colors';
const generateShadows = (color: string): Shadows => {
return [
'none',
@@ -56,6 +56,9 @@ export const themeOptions: ThemeOptions = {
default: '#ffffff', // 设置默认背景颜色
// paper: '#f5f5f5', // 设置纸张背景颜色
},
+ error: {
+ main: red[500],
+ },
},
shadows: generateShadows('rgba(255, 193, 7, 0.2)'),
typography: {
@@ -103,6 +106,24 @@ export const themeOptions: ThemeOptions = {
},
},
},
+ MuiSelect: {
+ styleOverrides: {
+ root: {
+ '& .MuiOutlinedInput-notchedOutline': {
+ borderColor: amber[300],
+ },
+ '&:hover .MuiOutlinedInput-notchedOutline': {
+ borderColor: amber[500],
+ },
+ '&.Mui-focused .MuiOutlinedInput-notchedOutline': {
+ borderColor: amber[500],
+ },
+ '& .MuiSelect-icon': {
+ color: amber[500], // Set arrow icon color to primary
+ },
+ },
+ },
+ },
MuiCard: {
styleOverrides: {
root: {
diff --git a/packages/resources/index.html b/packages/resources/index.html
index a4cb3fe..f0a0768 100644
--- a/packages/resources/index.html
+++ b/packages/resources/index.html
@@ -20,7 +20,8 @@
height: 100%;
}
-
+
+
diff --git a/packages/resources/package.json b/packages/resources/package.json
index 7038575..146146c 100644
--- a/packages/resources/package.json
+++ b/packages/resources/package.json
@@ -3,10 +3,15 @@
"version": "0.0.1",
"description": "",
"main": "index.js",
+ "basename": "/root/resources",
"scripts": {
"dev": "vite",
- "build": "vite build"
+ "build": "vite build",
+ "pub": "envision deploy ./dist -k resources -v 0.0.1 -u -o root"
},
+ "files": [
+ "src"
+ ],
"keywords": [],
"author": "abearxiong ",
"license": "MIT",
@@ -17,7 +22,7 @@
"@kevisual/center-components": "workspace:*",
"@kevisual/router": "^0.0.9",
"@kevisual/store": "^0.0.2",
- "@mui/material": "^6.4.7",
+ "@mui/material": "^6.4.8",
"@types/lodash-es": "^4.17.12",
"@types/nprogress": "^0.2.3",
"@vitejs/plugin-basic-ssl": "^2.0.0",
@@ -25,10 +30,11 @@
"immer": "^10.1.1",
"lodash-es": "^4.17.21",
"lucide-react": "^0.482.0",
- "nanoid": "^5.1.3",
+ "nanoid": "^5.1.4",
"nprogress": "^0.2.0",
"pretty-bytes": "^6.1.1",
"react": "19.0.0",
+ "react-datepicker": "^8.2.1",
"react-dom": "19.0.0",
"react-dropzone": "^14.3.8",
"react-toastify": "^11.0.5",
@@ -37,4 +43,4 @@
"devDependencies": {
"@kevisual/types": "^0.0.6"
}
-}
+}
\ No newline at end of file
diff --git a/packages/resources/public/config.js b/packages/resources/public/config.js
new file mode 100644
index 0000000..7197d1c
--- /dev/null
+++ b/packages/resources/public/config.js
@@ -0,0 +1,6 @@
+export const config = {
+ api: () => location.origin,
+ apps: {
+ login: '/user/login',
+ },
+};
diff --git a/packages/resources/src/assets/index.css b/packages/resources/src/assets/index.css
index f7676de..535d44f 100644
--- a/packages/resources/src/assets/index.css
+++ b/packages/resources/src/assets/index.css
@@ -7,6 +7,8 @@
}
:root {
--scrollbar-color: #ffbf00;
+ --primary-color: #ffc107;
+ --secondary-color: #ffa000;
}
#root {
width: 100%;
@@ -26,3 +28,39 @@
scrollbar-width: thin;
scrollbar-color: var(--scrollbar-color) #fff;
}
+
+.scrollbar::-webkit-scrollbar {
+ height: 4px;
+ width: 4px;
+}
+
+.scrollbar::-webkit-scrollbar-thumb {
+ background-color: var(--scrollbar-color);
+ border-radius: 10px;
+}
+
+.scrollbar::-webkit-scrollbar-track {
+ background: #fff;
+}
+
+.ant-select-outlined.ant-select-multiple .ant-select-selection-item {
+ background: var(--secondary-color);
+ color: white;
+ svg {
+ color: white;
+ }
+}
+.ant-select-selection-item {
+ color: var(--primary-color);
+}
+.ant-select {
+ .ant-select-arrow {
+ display: none !important;
+ }
+}
+.ant-picker-input {
+ .ant-picker-suffix,
+ .ant-picker-clear {
+ color: var(--primary-color);
+ }
+}
diff --git a/packages/resources/src/main.ts b/packages/resources/src/main.ts
index 504665e..917d1dd 100644
--- a/packages/resources/src/main.ts
+++ b/packages/resources/src/main.ts
@@ -1,50 +1,4 @@
-import { page, app } from './app.ts';
-import { basename } from './modules/basename.ts';
-import './pages/main.tsx';
+import { bootstrap } from './pages/Bootstrap';
-export const render = ({ renderRoot }) => {
- renderRoot.innerHTML = `
- Hello, World!
- `;
-};
-console.log('basename', basename, page, app);
+bootstrap('#ai-root');
-if (page) {
- page.addPage('/', 'home');
- page.subscribe('home', () => {
- render({
- renderRoot: document.getElementById('ai-root'),
- });
- });
- page.addPage('', 'index');
- page.subscribe('index', () => {
- const root = document.getElementById('ai-root') as HTMLElement;
- root.innerHTML = `
- Hello, World!
- `;
- });
-}
-
-if (app) {
- app
- .route({
- path: 'app-template',
- key: 'render',
- })
- .define(async (ctx) => {
- let { renderRoot } = ctx.query;
- if (!renderRoot) {
- ctx.throw(404, 'renderRoot is required');
- }
- if (typeof renderRoot === 'string') {
- renderRoot = document.querySelector(renderRoot);
- }
- if (!renderRoot) {
- ctx.throw(404, 'renderRoot not found');
- }
- render({
- renderRoot,
- });
- })
- .addTo(app);
-}
diff --git a/packages/resources/src/modules/query.ts b/packages/resources/src/modules/query.ts
index f4660b4..5c3e436 100644
--- a/packages/resources/src/modules/query.ts
+++ b/packages/resources/src/modules/query.ts
@@ -1,3 +1,15 @@
+import { toastLogin } from '@/pages/message/ToastLogin';
import { QueryClient } from '@kevisual/query';
-export const query = new QueryClient();
\ No newline at end of file
+export const query = new QueryClient();
+
+query.afterResponse = async (response) => {
+ if (response.code === 401) {
+ toastLogin();
+ return {
+ ...response,
+ noMsg: true,
+ };
+ }
+ return response;
+};
diff --git a/packages/resources/src/pages/App.tsx b/packages/resources/src/pages/App.tsx
index 8532ba2..61e56c2 100644
--- a/packages/resources/src/pages/App.tsx
+++ b/packages/resources/src/pages/App.tsx
@@ -5,10 +5,47 @@ import { Left } from './layout/Left';
import { Main } from './main/index';
import { ToastContainer } from 'react-toastify';
import { useSettingsStore } from './store/settings';
-import { CircularProgress } from '@mui/material';
+import { CircularProgress, useTheme } from '@mui/material';
import { useResourceStore } from './store/resource';
+import dayjs from 'dayjs';
+import 'dayjs/locale/zh-cn';
-export const App = () => {
+import zhCN from 'antd/locale/zh_CN';
+import ConfigProvider from 'antd/es/config-provider';
+
+dayjs.locale('zh-cn');
+export const AntdConfigProvider = ({ children }: { children: React.ReactNode }) => {
+ const theme = useTheme();
+ const primaryColor = theme.palette.primary.main;
+ const secondaryColor = theme.palette.secondary.main;
+ return (
+
+ {children}
+
+ );
+};
+export const InitProvider = ({ children }: { children: React.ReactNode }) => {
const { init, mounted, settings } = useSettingsStore();
const { setPrefix, init: initResource } = useResourceStore();
useEffect(() => {
@@ -16,24 +53,46 @@ export const App = () => {
initResource();
}, []);
useEffect(() => {
- if (settings.prefix && mounted) {
+ if (settings.prefix && mounted === 'success') {
setPrefix(settings.prefix);
}
}, [mounted, settings.prefix]);
- if (!mounted) {
+
+ const handleRetry = () => {
+ init();
+ initResource();
+ };
+
+ if (mounted === 'loading') {
return (
);
+ } else if (mounted === 'error') {
+ return (
+
+
出现问题
+
加载设置时遇到错误。请重试。
+
+
+ );
}
-
+ return <>{children}>;
+};
+export const App = () => {
return (
-
-
-
-
+
+
+
+
+
+
+
+
);
};
diff --git a/packages/resources/src/pages/Bootstrap.tsx b/packages/resources/src/pages/Bootstrap.tsx
new file mode 100644
index 0000000..b9f76ba
--- /dev/null
+++ b/packages/resources/src/pages/Bootstrap.tsx
@@ -0,0 +1,61 @@
+import { createRoot } from 'react-dom/client';
+import { App } from './App';
+import React from 'react';
+
+export class ReactRenderer {
+ component: any;
+ element: HTMLElement;
+ ref: React.RefObject;
+ props: any;
+ root: any;
+ constructor(component: any, { props, className }: any) {
+ this.component = component;
+ const el = document.createElement('div');
+ this.element = el;
+ this.ref = React.createRef();
+ this.props = {
+ ...props,
+ ref: this.ref,
+ };
+ el.className = className;
+ this.root = createRoot(this.element);
+ this.render();
+ }
+
+ updateProps(props: any) {
+ this.props = {
+ ...this.props,
+ ...props,
+ };
+ this.render();
+ }
+
+ render() {
+ this.root.render(React.createElement(this.component, this.props));
+ }
+
+ destroy() {
+ this.root.unmount();
+ }
+}
+
+export default ReactRenderer;
+
+export const bootstrap = (el: HTMLElement | string) => {
+ // createRoot(document.getElementById('ai-root')!).render();
+ const root = typeof el === 'string' ? document.querySelector(el) : el;
+ if (root) {
+ const renderer = new ReactRenderer(App, {
+ props: {},
+ className: 'resources-root w-full h-full',
+ });
+ if (window.context) {
+ window.context.resourcesApp = renderer;
+ } else {
+ window.context = {
+ resourcesApp: renderer,
+ };
+ }
+ root.appendChild(renderer.element);
+ }
+};
diff --git a/packages/resources/src/pages/file/FileIcon.tsx b/packages/resources/src/pages/file/FileIcon.tsx
index 61c4826..ad1b7bd 100644
--- a/packages/resources/src/pages/file/FileIcon.tsx
+++ b/packages/resources/src/pages/file/FileIcon.tsx
@@ -90,3 +90,83 @@ export const getIcon = (name: string) => {
return ;
}
};
+
+/**
+ * 获取文件类型,文件大类
+ * @param name 文件名
+ * @returns 文件类型
+ */
+export const getFileType = (name?: string) => {
+ if (!name) {
+ return '';
+ }
+ const extension = getExtension(name);
+ switch (extension) {
+ case 'pdf':
+ return 'pdf';
+ case 'jpg':
+ case 'jpeg':
+ case 'gif':
+ case 'png':
+ return 'image';
+ case 'mp3':
+ case 'wav':
+ case 'ogg':
+ case 'm4a':
+ case 'aac':
+ case 'flac':
+ case 'wma':
+ return 'audio';
+ case 'mp4':
+ return 'video';
+ case 'doc':
+ case 'docx':
+ return 'word';
+ case 'ppt':
+ case 'pptx':
+ return 'ppt';
+ case 'xls':
+ case 'xlsx':
+ return 'excel';
+ case 'zip':
+ case 'rar':
+ case '7z':
+ case 'tar':
+ case 'gz':
+ case 'bz2':
+ return 'zip';
+ case 'txt':
+ case 'md':
+ case 'csv':
+ case 'json':
+ case 'xml':
+ case 'yaml':
+ case 'yml':
+ case 'toml':
+ case 'ini':
+ case 'conf':
+ case 'cfg':
+ case 'config':
+ case 'props':
+ case 'properties':
+ case 'log':
+ case 'sh':
+ case 'bash':
+ case 'zsh':
+ case 'fish':
+ case 'bat':
+ case 'cmd':
+ return 'text';
+ case 'html':
+ case 'htm':
+ return 'html';
+ case 'css':
+ case 'js':
+ case 'ts':
+ case 'jsx':
+ case 'tsx':
+ return 'code';
+ default:
+ return 'other';
+ }
+};
diff --git a/packages/resources/src/pages/file/draw/FileDrawer.tsx b/packages/resources/src/pages/file/draw/FileDrawer.tsx
index 53365f1..29e72f6 100644
--- a/packages/resources/src/pages/file/draw/FileDrawer.tsx
+++ b/packages/resources/src/pages/file/draw/FileDrawer.tsx
@@ -1,16 +1,60 @@
import { useResourceStore } from '@/pages/store/resource';
import { useResourceFileStore } from '@/pages/store/resource-file';
-import { Drawer } from '@mui/material';
+import { Box, Divider, Drawer, Tab, Tabs } from '@mui/material';
+import { useMemo, useState } from 'react';
+import { QuickValues, QuickTabs } from './QuickTabs';
export const FileDrawer = () => {
const { prefix } = useResourceStore();
const { resource, openDrawer, setOpenDrawer } = useResourceFileStore();
+ const [tab, setTab] = useState(QuickValues[0]);
+ const quickCom = useMemo(() => {
+ return QuickTabs.find((item) => item.value === tab)?.component;
+ }, [tab]);
return (
- setOpenDrawer(false)} anchor='right' {...(!openDrawer && { inert: true })}>
-
-
{resource?.name ? resource.name.replace(prefix, '') : resource?.prefix?.replace(prefix, '')}
-
{JSON.stringify(resource, null, 2)}
-
-
+ <>
+ {
+ // document.getElementById('focus-safe-element')?.focus();
+ const activeElement = document.activeElement as HTMLElement;
+ if (activeElement) {
+ activeElement.blur();
+ }
+ setOpenDrawer(false);
+ }}
+ ModalProps={{
+ keepMounted: true,
+ }}
+ anchor='right'
+ style={{
+ zIndex: 1000,
+ }}>
+
+
+
+ {resource?.name ? resource.name.replace(prefix, '') : resource?.prefix?.replace(prefix, '')}
+
+
+
+ setTab(value)}>
+ {QuickTabs.map((item) => (
+
+ ))}
+
+
+
+
+
+ {quickCom && quickCom()}
+
+
+
+
+
+ >
);
};
diff --git a/packages/resources/src/pages/file/draw/QuickTabs.tsx b/packages/resources/src/pages/file/draw/QuickTabs.tsx
new file mode 100644
index 0000000..76c1526
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/QuickTabs.tsx
@@ -0,0 +1,27 @@
+import { MetaForm } from './modules/MetaForm';
+import { ContentForm } from './modules/ContextForm';
+import { Cpu, File, FileText, Rabbit } from 'lucide-react';
+import { Quick } from './quick';
+export const QuickTabs = [
+ {
+ label: 'Quick',
+ value: 'quick',
+ icon: ,
+ index: 99,
+ component: () => ,
+ },
+ {
+ label: '元数据',
+ value: 'meta',
+ icon: ,
+ component: () => ,
+ },
+ {
+ label: '内容',
+ value: 'content',
+ icon: ,
+ component: () => ,
+ },
+].sort((a, b) => (b?.index || 0) - (a?.index || 0));
+
+export const QuickValues = QuickTabs.map((item) => item.value);
diff --git a/packages/resources/src/pages/file/draw/modules/ContextForm.tsx b/packages/resources/src/pages/file/draw/modules/ContextForm.tsx
new file mode 100644
index 0000000..3209b9e
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/modules/ContextForm.tsx
@@ -0,0 +1,29 @@
+import { useResourceFileStore } from '@/pages/store/resource-file';
+import { Box, Typography } from '@mui/material';
+import prettyBytes from 'pretty-bytes';
+import dayjs from 'dayjs';
+
+type ContentShowType = {
+ size: number;
+ lastModified: string;
+ etag: string;
+ name?: string;
+};
+export const ContentForm = () => {
+ const { resource } = useResourceFileStore();
+ const contentShow = resource as ContentShowType;
+ return (
+
+ {/* {contentShow?.name || 'No Name Available'} */}
+
+ Size: {contentShow?.size ? prettyBytes(contentShow?.size) : 'N/A'}
+
+
+ Last Modified: {contentShow?.lastModified ? dayjs(contentShow?.lastModified).format('YYYY-MM-DD HH:mm:ss') : 'N/A'}
+
+
+ ETag: {contentShow?.etag || 'N/A'}
+
+
+ );
+};
diff --git a/packages/resources/src/pages/file/draw/modules/DatePicker.tsx b/packages/resources/src/pages/file/draw/modules/DatePicker.tsx
new file mode 100644
index 0000000..4be43fb
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/modules/DatePicker.tsx
@@ -0,0 +1,28 @@
+import ReactDatePicker from 'antd/es/date-picker';
+import { useTheme } from '@mui/material';
+import 'antd/es/date-picker/style/index';
+interface DatePickerProps {
+ value?: Date | null;
+ onChange?: (date: Date | null) => void;
+}
+
+export const DatePicker = ({ value, onChange }: DatePickerProps) => {
+ const theme = useTheme();
+ const primaryColor = theme.palette.primary.main;
+ return (
+
+ onChange?.(date)} //
+ style={{
+ color: primaryColor,
+ }}
+ popupStyle={{ zIndex: 2000 }}
+ />
+
+ );
+};
diff --git a/packages/resources/src/pages/file/draw/modules/DialogKey.tsx b/packages/resources/src/pages/file/draw/modules/DialogKey.tsx
new file mode 100644
index 0000000..5c3f4ec
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/modules/DialogKey.tsx
@@ -0,0 +1,39 @@
+import { Button, Dialog, DialogContent, DialogTitle, FormControlLabel, TextField } from '@mui/material';
+import { useState } from 'react';
+import { useMetaStore } from './MetaForm';
+export const DialogKey = ({ onAdd }: { onAdd: (key: string) => void }) => {
+ const { openPropertyModal, setOpenPropertyModal } = useMetaStore();
+ const [key, setKey] = useState('');
+ return (
+
+ );
+};
diff --git a/packages/resources/src/pages/file/draw/modules/MetaForm.tsx b/packages/resources/src/pages/file/draw/modules/MetaForm.tsx
new file mode 100644
index 0000000..7505dbf
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/modules/MetaForm.tsx
@@ -0,0 +1,368 @@
+import { useResourceFileStore } from '@/pages/store/resource-file';
+import { FormControlLabel, Box, TextField, Button, IconButton, ButtonGroup, Tooltip, Select, MenuItem, Typography, FormGroup } from '@mui/material';
+import { Info, Plus, Save, Share, Shuffle, Trash } from 'lucide-react';
+import { useState, useEffect, useMemo } from 'react';
+import { toast } from 'react-toastify';
+import { create } from 'zustand';
+import { uniq } from 'lodash-es';
+import { DatePicker } from './DatePicker';
+import { SelectPicker } from './SelectPicker';
+import dayjs from 'dayjs';
+import { DialogKey } from './DialogKey';
+
+export const setShareKeysOperate = (value: 'public' | 'protected' | 'private') => {
+ const keys = ['password', 'usernames', 'expiration-time'];
+ const deleteKeys = keys.map((item) => {
+ return {
+ key: item,
+ operate: 'delete',
+ };
+ });
+ if (value === 'protected') {
+ return deleteKeys.map((item) => {
+ return {
+ ...item,
+ operate: 'add',
+ };
+ });
+ }
+ return deleteKeys;
+};
+export const keysTips = [
+ {
+ key: 'share',
+ tips: `共享设置
+ 1. 设置公共可以直接访问
+ 2. 设置受保护需要登录后访问
+ 3. 设置私有只有自己可以访问。\n
+ 受保护可以设置密码,设置访问的用户名。切换共享状态后,需要重新设置密码和用户名。`,
+ },
+ {
+ key: 'content-type',
+ tips: `内容类型,设置文件的内容类型。默认不要修改。`,
+ },
+ {
+ key: 'app-source',
+ tips: `应用来源,上传方式。默认不要修改。`,
+ },
+ {
+ key: 'cache-control',
+ tips: `缓存控制,设置文件的缓存控制。默认不要修改。`,
+ },
+ {
+ key: 'password',
+ tips: `密码,设置文件的密码。不设置默认是所有人都可以访问。`,
+ },
+ {
+ key: 'usernames',
+ tips: `用户名,设置文件的用户名。不设置默认是所有人都可以访问。`,
+ parse: (value: string) => {
+ if (!value) {
+ return [];
+ }
+ return value.split(',');
+ },
+ stringify: (value: string[]) => {
+ if (!value) {
+ return '';
+ }
+ return value.join(',');
+ },
+ },
+ {
+ key: 'expiration-time',
+ tips: `过期时间,设置文件的过期时间。不设置默认是永久。`,
+ parse: (value: Date) => {
+ if (!value) {
+ return null;
+ }
+ return dayjs(value);
+ },
+ stringify: (value?: dayjs.Dayjs) => {
+ if (!value) {
+ return '';
+ }
+ return value.toISOString();
+ },
+ },
+];
+export class KeyParse {
+ static parse(metadata: Record) {
+ const keys = Object.keys(metadata);
+ const newMetadata = {};
+ keys.forEach((key) => {
+ const tip = keysTips.find((item) => item.key === key);
+ if (tip && tip.parse) {
+ newMetadata[key] = tip.parse(metadata[key]);
+ } else {
+ newMetadata[key] = metadata[key];
+ }
+ });
+ return newMetadata;
+ }
+ static stringify(metadata: Record) {
+ const keys = Object.keys(metadata);
+ const newMetadata = {};
+ keys.forEach((key) => {
+ const tip = keysTips.find((item) => item.key === key);
+ if (tip && tip.stringify) {
+ newMetadata[key] = tip.stringify(metadata[key]);
+ } else {
+ newMetadata[key] = metadata[key];
+ }
+ });
+ return newMetadata;
+ }
+}
+export const useMetaOperate = ({
+ onSave,
+ metaStore,
+ handleFormDataChange,
+}: {
+ onSave: () => void;
+ metaStore: MetaStore;
+ handleFormDataChange: (key: string, value: string | Date | null | string[]) => void;
+}) => {
+ const { keys, setKeys, openPropertyModal, setOpenPropertyModal } = metaStore;
+ const hasShare = keys.includes('share');
+ const hasPassword = keys.includes('password');
+ const addMeta = (key: string) => {
+ setKeys(uniq([...keys, key]));
+ };
+ const defaultBtnList = [
+ {
+ icon: ,
+ key: 'save',
+ tooltip: '保存元数据, 修改后需要手动保存',
+ onClick: () => onSave(),
+ },
+ {
+ icon: ,
+ key: 'add',
+ tooltip: '添加元数据',
+ onClick: () => setOpenPropertyModal(true),
+ },
+ ];
+ if (!hasShare) {
+ defaultBtnList.push({
+ icon: ,
+ key: 'share',
+ tooltip: '开启共享',
+ onClick: () => addMeta('share'),
+ });
+ }
+ if (hasShare && hasPassword) {
+ defaultBtnList.push({
+ icon: ,
+ key: 'password',
+ tooltip: '随机生成密码',
+ onClick: () => {
+ const password = Math.random().toString(36).substring(2, 8);
+ handleFormDataChange('password', password);
+ },
+ });
+ }
+ return defaultBtnList;
+};
+type MetaStore = {
+ keys: string[];
+ setKeys: (keys: string[]) => void;
+ openPropertyModal: boolean;
+ setOpenPropertyModal: (openPropertyModal: boolean) => void;
+};
+export const useMetaStore = create((set) => ({
+ keys: [],
+ setKeys: (keys) => set({ keys }),
+ openPropertyModal: false,
+ setOpenPropertyModal: (openPropertyModal) => set({ openPropertyModal }),
+}));
+export const MetaForm = () => {
+ const { resource, updateMeta } = useResourceFileStore();
+ const [formData, setFormData] = useState({});
+ const metaStore = useMetaStore();
+ const { keys, setKeys } = metaStore;
+ useEffect(() => {
+ // setFormData(resource?.metaData || {});
+ setFormData(KeyParse.parse(resource?.metaData || {}));
+ }, [resource]);
+ useEffect(() => {
+ setKeys(Object.keys(resource?.metaData || {}));
+ }, [resource]);
+ if (!keys.length) {
+ return 没有元数据
;
+ }
+
+ const handleFormDataChange = (key: string, value: string | Date | null | string[]) => {
+ // setFormData({ ...formData, [key]: value });
+ const _formData = { ...formData };
+ if (key === 'share') {
+ const shareKeysOperate = setShareKeysOperate(value as 'public' | 'protected' | 'private');
+ shareKeysOperate.forEach((item) => {
+ if (item.operate === 'add') {
+ _formData[item.key] = '';
+ } else if (item.operate === 'delete') {
+ delete _formData[item.key];
+ }
+ });
+ _formData.share = value;
+ setFormData(_formData);
+ const newKeys = keys
+ .map((item) => {
+ const operate = shareKeysOperate.find((item2) => item2.key === item);
+ if (operate && operate.operate === 'delete') {
+ return null;
+ }
+ return item;
+ })
+ .filter((item) => item !== null);
+ const addKeys = shareKeysOperate.filter((item) => item.operate === 'add').map((item) => item.key);
+ const _newKeys = uniq([...newKeys, ...addKeys]);
+ setKeys(_newKeys);
+ console.log(_newKeys);
+ return;
+ } else {
+ _formData[key] = value;
+ }
+ setFormData(_formData);
+ };
+ const deleteMeta = (key: string) => {
+ setKeys(keys.filter((item) => item !== key));
+ delete formData[key];
+ setFormData({ ...formData });
+ };
+ const onSave = () => {
+ const newMetadata = KeyParse.stringify(formData);
+ updateMeta(newMetadata);
+ };
+ const addMetaKey = (key: string) => {
+ if (keys.includes(key)) {
+ toast.error('元数据key已存在');
+ return;
+ }
+ formData[key] = '';
+ setKeys([...keys, key]);
+ setFormData({ ...formData });
+ };
+ const btnList = useMetaOperate({ onSave, metaStore, handleFormDataChange });
+
+ return (
+
+
+
+
+
+ {btnList.map((item) => {
+ const icon = (
+
+ {item.icon}
+
+ );
+ if (item.tooltip) {
+ return (
+
+ {icon}
+
+ );
+ }
+ return <>{icon}>;
+ })}
+
+
+
+
+
+ {keys.map((key) => {
+ let control: React.ReactNode | null = null;
+ if (key === 'share') {
+ control = handleFormDataChange(key, value)} />;
+ } else if (key === 'expiration-time') {
+ control = handleFormDataChange(key, date)} />;
+ } else if (key === 'usernames') {
+ control = handleFormDataChange(key, value)} />;
+ } else {
+ control = handleFormDataChange(key, value)} />;
+ }
+ const Label = () => {
+ const tip = keysTips.find((item) => item.key === key);
+ return (
+
+
+
+ {key}
+
+ {tip && (
+
+
+
+ )}
+
+
deleteMeta(key)}>
+
+
+
+ );
+ };
+ return (
+
+ }
+ labelPlacement='top'
+ control={control}
+ sx={{
+ alignItems: 'flex-start',
+ '& .MuiFormControlLabel-label': {
+ textAlign: 'left',
+ width: '100%',
+ },
+ }}
+ />
+
+ );
+ })}
+
+
+
+ );
+};
+
+const KeyTextField = ({ name, value, onChange }: { name: string; value: string; onChange?: (value: string) => void }) => {
+ return (
+ onChange?.(e.target.value)}
+ sx={{
+ width: '100%',
+ marginBottom: '16px',
+ }}
+ />
+ );
+};
+const KeyShareSelect = ({ name, value, onChange }: { name: string; value: string; onChange?: (value: string) => void }) => {
+ return (
+
+ );
+};
diff --git a/packages/resources/src/pages/file/draw/modules/SelectPicker.tsx b/packages/resources/src/pages/file/draw/modules/SelectPicker.tsx
new file mode 100644
index 0000000..0f6b209
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/modules/SelectPicker.tsx
@@ -0,0 +1,18 @@
+import { styled } from '@mui/material';
+import Select from 'antd/es/select';
+import 'antd/es/select/style/index';
+
+interface SelectPickerProps {
+ value: string[];
+ onChange: (value: string[]) => void;
+}
+
+export const SelectPickerCom = ({ value, onChange }: SelectPickerProps) => {
+ return ;
+};
+
+export const SelectPicker = styled(SelectPickerCom)({
+ '& .ant-select-selector': {
+ color: 'var(--primary-color)',
+ },
+});
diff --git a/packages/resources/src/pages/file/draw/quick/QuickLink.tsx b/packages/resources/src/pages/file/draw/quick/QuickLink.tsx
new file mode 100644
index 0000000..3aed46a
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/quick/QuickLink.tsx
@@ -0,0 +1,11 @@
+/**
+ * 链接生成,markdown超链接, 多选项。
+ * 1. markdown
+ * 2. HTML image
+ * 3. URL https url
+ * @returns
+ */
+export const QuickLink = () => {
+ const url = 'https://ab.c.com/a/b/c.jpg';
+ return QuickLink
;
+};
diff --git a/packages/resources/src/pages/file/draw/quick/QuickPreview.tsx b/packages/resources/src/pages/file/draw/quick/QuickPreview.tsx
new file mode 100644
index 0000000..ce88845
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/quick/QuickPreview.tsx
@@ -0,0 +1,131 @@
+import { useResourceFileStore } from '@/pages/store/resource-file';
+import { useSettingsStore } from '@/pages/store/settings';
+import { Button, Tooltip, useTheme } from '@mui/material';
+import { useShallow } from 'zustand/shallow';
+import { Accordion, AccordionSummary, AccordionDetails } from '@mui/material';
+import { ChevronDown } from 'lucide-react';
+import { useMemo } from 'react';
+import { getFileType } from '../../FileIcon';
+import { toast } from 'react-toastify';
+import clsx from 'clsx';
+type AccordionItem = {
+ title?: string;
+ key?: string;
+ url?: string;
+ content?: any;
+ clickCopy?: boolean;
+};
+export const QuickPreview = () => {
+ const { resource } = useResourceFileStore(
+ useShallow((state) => ({
+ resource: state.resource,
+ })),
+ );
+ const { settings, baseUrl } = useSettingsStore(
+ useShallow((state) => ({
+ settings: state.settings,
+ baseUrl: state.baseUrl,
+ })),
+ );
+ const fileType = useMemo(() => getFileType(resource?.name), [resource]);
+ const accordionList = useMemo(() => {
+ const username = settings?.username;
+ if (!username) {
+ toast.error('请先登录');
+ return [];
+ }
+ const _url = new URL(`${baseUrl}/api/s1/share/${username}/${resource?.name}`);
+ const meta = resource?.metaData ?? {};
+ if (meta.password) {
+ _url.searchParams.set('p', meta.password);
+ }
+ const url = _url.toString();
+ let accordionList: AccordionItem[] = [];
+ const encodeUrl = encodeURIComponent(url);
+ const previewUrl = `${baseUrl}/app/preview?fileUrl=${encodeUrl}&fileType=${fileType}`;
+ accordionList.push({
+ title: '文件预览',
+ key: 'preview-file',
+ url: previewUrl,
+ content: (
+
+
{previewUrl}
+
+
+ ),
+ });
+
+ if (fileType === 'image') {
+ accordionList.push({
+ title: '预览图片',
+ key: 'preview-image',
+ url: url,
+ content:
,
+ });
+ accordionList.push({
+ title: 'markdown链接',
+ key: 'markdown-link',
+ url: url,
+ clickCopy: true,
+ content: ``,
+ });
+ accordionList.push({
+ title: 'HTML图片',
+ key: 'html-image',
+ url: url,
+ clickCopy: true,
+ content: `
`,
+ });
+ accordionList.push({
+ title: 'HTML超链接',
+ key: 'html-link',
+ url: url,
+ clickCopy: true,
+ content: `${resource?.name}`,
+ });
+ }
+ const downloadUrl = new URL(url);
+ downloadUrl.searchParams.set('download', 'true');
+ accordionList.push({
+ title: '下载地址',
+ key: 'download-url',
+ url: downloadUrl.toString(),
+ content: (
+
+
{downloadUrl.toString()}
+
+
+ ),
+ });
+
+ return accordionList;
+ }, [resource, baseUrl, settings]);
+ const theme = useTheme();
+ return (
+
+ {accordionList.map((item) => (
+
+ }>{item.title}
+
+ {
+ if (item.clickCopy) {
+ navigator.clipboard.writeText(item.content);
+ toast.success('复制成功');
+ }
+ }}>
+ {item.content}
+
+
+
+ ))}
+
+ );
+};
diff --git a/packages/resources/src/pages/file/draw/quick/index.tsx b/packages/resources/src/pages/file/draw/quick/index.tsx
new file mode 100644
index 0000000..b8445a6
--- /dev/null
+++ b/packages/resources/src/pages/file/draw/quick/index.tsx
@@ -0,0 +1,41 @@
+import { useResourceFileStore } from '@/pages/store/resource-file';
+import { useShallow } from 'zustand/shallow';
+import { QuickPreview } from './QuickPreview';
+import { useMemo } from 'react';
+import { getFileType } from '../../FileIcon';
+
+const QuickModules = [
+ {
+ key: 'link',
+ type: 'link',
+ categroy: ['image', 'video', 'audio'],
+ tooltips: `链接生成,markdown超链接`,
+ component: () => ,
+ },
+ {
+ key: 'preview',
+ type: 'all',
+ tooltips: `预览页面内容`,
+ component: () => ,
+ },
+];
+export const Quick = () => {
+ const { resource } = useResourceFileStore(
+ useShallow((state) => ({
+ resource: state.resource,
+ })),
+ );
+ const quickModule = useMemo(() => {
+ const fileType = getFileType(resource?.name);
+ const allCanUseModule = QuickModules.filter((item) => item.type === 'all');
+ if (!fileType) {
+ return allCanUseModule;
+ }
+ return QuickModules.filter((item) => item.type === fileType);
+ }, [resource]);
+ return (
+ <>
+
+ >
+ );
+};
diff --git a/packages/resources/src/pages/file/list/FileTable.tsx b/packages/resources/src/pages/file/list/FileTable.tsx
index e3808dc..dcf494c 100644
--- a/packages/resources/src/pages/file/list/FileTable.tsx
+++ b/packages/resources/src/pages/file/list/FileTable.tsx
@@ -11,14 +11,35 @@ export const FileTable = () => {
const { list, prefix, download, onOpenPrefix, deleteFile } = useResourceStore();
const { setOpenDrawer, setPrefix } = useResourceFileStore();
return (
-
-
+
+
Name
- Size
- Last Modified
- Actions
+ Size
+ Last Modified
+ Actions
diff --git a/packages/resources/src/pages/main.tsx b/packages/resources/src/pages/main.tsx
index e832c9a..c5270c7 100644
--- a/packages/resources/src/pages/main.tsx
+++ b/packages/resources/src/pages/main.tsx
@@ -1,4 +1,3 @@
-import { createRoot } from 'react-dom/client';
-import { App } from './App.tsx';
+import { bootstrap } from './Bootstrap';
-createRoot(document.getElementById('ai-root')!).render();
+bootstrap('#ai-root');
diff --git a/packages/resources/src/pages/message/ToastLogin.tsx b/packages/resources/src/pages/message/ToastLogin.tsx
index eda1245..05ced54 100644
--- a/packages/resources/src/pages/message/ToastLogin.tsx
+++ b/packages/resources/src/pages/message/ToastLogin.tsx
@@ -4,8 +4,11 @@ import { toast } from 'react-toastify';
const LoginMessage = () => {
const handleClick = () => {
const currentUrl = window.location.href;
+ console.log(currentUrl);
const redirect = encodeURIComponent(currentUrl);
- window.location.href = '/user/login?redirect=' + redirect;
+ console.log('redirect', redirect);
+ const newUrl = location.origin + '/user/login/?redirect=' + redirect;
+ window.open(newUrl, '_self');
};
return (
diff --git a/packages/resources/src/pages/settings/index.tsx b/packages/resources/src/pages/settings/index.tsx
index 2f0c8ed..7386c92 100644
--- a/packages/resources/src/pages/settings/index.tsx
+++ b/packages/resources/src/pages/settings/index.tsx
@@ -40,7 +40,6 @@ export const Settings = () => {
}, [settings]);
const handleChange = (e: React.ChangeEvent) => {
let { name, value } = e.target;
- console.log(name, value, e.target);
name = name.toLowerCase();
setConfig({ ...config, [name]: value });
};
diff --git a/packages/resources/src/pages/store/resource-file.ts b/packages/resources/src/pages/store/resource-file.ts
index 057d977..346ce8a 100644
--- a/packages/resources/src/pages/store/resource-file.ts
+++ b/packages/resources/src/pages/store/resource-file.ts
@@ -1,6 +1,7 @@
import { create } from 'zustand';
import { Resource } from './resource';
import { query } from '@/modules/query';
+import { toast } from 'react-toastify';
interface ResourceFileStore {
resource: Resource | null;
@@ -10,6 +11,7 @@ interface ResourceFileStore {
prefix: string;
setPrefix: (prefix: string, replace?: string) => void;
getStatFile: () => Promise;
+ updateMeta: (metadata: any) => Promise;
}
export const useResourceFileStore = create((set, get) => ({
@@ -32,4 +34,21 @@ export const useResourceFileStore = create((set, get) => ({
set({ resource: { ...res.data, name: prefix } });
}
},
+ updateMeta: async (metadata: any) => {
+ const { resource, getStatFile } = get();
+ const res = await query.post({
+ path: 'file',
+ key: 'update-metadata',
+ data: {
+ prefix: resource?.name,
+ metadata: metadata,
+ },
+ });
+ if (res.code === 200) {
+ // set({ resource: { ...res.data, name: resource?.name } });
+ getStatFile();
+ } else {
+ toast.error(res.message || '更新元数据失败');
+ }
+ },
}));
diff --git a/packages/resources/src/pages/store/resource.ts b/packages/resources/src/pages/store/resource.ts
index d3c5887..1b4eb34 100644
--- a/packages/resources/src/pages/store/resource.ts
+++ b/packages/resources/src/pages/store/resource.ts
@@ -2,6 +2,7 @@ import { create } from 'zustand';
import { query } from '@/modules/query';
import { sortBy } from 'lodash-es';
import { toast } from 'react-toastify';
+import { useSettingsStore } from './settings';
export type Resource = {
name: string;
@@ -67,9 +68,16 @@ export const useResourceStore = create((set, get) => ({
}
},
download: (resource: Resource) => {
- const { prefix } = get();
- const url = `${prefix}/${resource.name}`;
- window.open(url, '_blank');
+ const { baseUrl, settings } = useSettingsStore.getState();
+ const username = settings?.username;
+ const _url = new URL(`${baseUrl}/api/s1/share/${username}/${resource?.name}`);
+ _url.searchParams.set('download', 'true');
+ const downloadUrl = _url.toString();
+ console.log('downloadUrl', downloadUrl);
+ const a = document.createElement('a');
+ a.href = downloadUrl;
+ a.download = resource.name;
+ a.click();
},
listType: 'table',
setListType: (listType: 'table' | 'card') => {
diff --git a/packages/resources/src/pages/store/settings.ts b/packages/resources/src/pages/store/settings.ts
index 977a711..9a3d9d3 100644
--- a/packages/resources/src/pages/store/settings.ts
+++ b/packages/resources/src/pages/store/settings.ts
@@ -12,16 +12,18 @@ interface SettingsStore {
settings: Settings;
setSettings: (settings: Settings) => void;
querySettings: () => Promise;
- mounted: boolean;
- setMounted: (mounted: boolean) => void;
+ mounted: 'loading' | 'error' | 'success';
+ setMounted: (mounted: 'loading' | 'error' | 'success') => void;
init: () => Promise;
updateSettings: (settings: Settings) => void;
+ baseUrl: string;
+ setBaseUrl: (baseUrl: string) => void;
}
export const useSettingsStore = create((set, get) => ({
settings: {},
setSettings: (settings) => set({ settings }),
- mounted: false,
+ mounted: 'loading',
setMounted: (mounted) => set({ mounted }),
querySettings: async () => {
const settings = get().settings;
@@ -29,37 +31,48 @@ export const useSettingsStore = create((set, get) => ({
path: 'config',
key: 'getUploadConfig',
});
- console.log(res);
if (res.code === 200) {
const config = res.data;
localStorage.setItem('upload-config', JSON.stringify(config));
set({ settings: config });
if (JSON.stringify(settings) !== JSON.stringify(config)) {
- set({ mounted: false });
- set({ mounted: true });
+ set({ mounted: 'success' });
}
} else {
- toast.error(res.message || '获取配置失败');
+ !res.noMsg && toast.error(res.message || '获取配置失败');
+ set({ mounted: 'error' });
}
},
updateSettings: async (settings) => {
- console.log('setinng', settings);
- // const res = await query.post({
- // path: 'config',
- // key: 'updateUploadConfig',
- // data: settings,
- // });
+ const res = await query.post({
+ path: 'config',
+ key: 'updateUploadConfig',
+ data: {
+ key: settings.key,
+ version: settings.version,
+ },
+ });
+ if (res.code === 200) {
+ toast.success('更新配置成功');
+ get().querySettings();
+ } else {
+ toast.error(res.message || '更新配置失败');
+ }
},
init: async () => {
const cacheConfig = localStorage.getItem('upload-config');
if (cacheConfig) {
try {
- set({ settings: JSON.parse(cacheConfig), mounted: true });
+ set({ settings: JSON.parse(cacheConfig), mounted: 'success' });
} catch (error) {
toast.error('配置文件损坏');
localStorage.removeItem('upload-config');
}
}
get().querySettings();
+ const baseUrl = location.origin;
+ set({ baseUrl });
},
+ baseUrl: '',
+ setBaseUrl: (baseUrl) => set({ baseUrl }),
}));
diff --git a/packages/resources/src/pages/upload/index.tsx b/packages/resources/src/pages/upload/index.tsx
index 8f5b8d4..0b71741 100644
--- a/packages/resources/src/pages/upload/index.tsx
+++ b/packages/resources/src/pages/upload/index.tsx
@@ -3,7 +3,7 @@ import { useDropzone } from 'react-dropzone';
import { uploadFiles } from './utils/upload';
import { FileText, CloudUpload as UploadIcon } from 'lucide-react';
import { uploadFileChunked } from './utils/upload-chunk';
-export const UploadButton = (props: { prefix?: string; onUpload?: (res: any) => void }) => {
+export const UploadButton = (props: { prefix?: string; onUpload?: (res: any) => void; hasDirectory?: boolean; uploadDirectory?: boolean }) => {
const onDrop = async (acceptedFiles) => {
console.log(acceptedFiles);
if (acceptedFiles.length > 1) {
@@ -27,11 +27,18 @@ export const UploadButton = (props: { prefix?: string; onUpload?: (res: any) =>
}}>
-
+
);
};
-export const Upload = () => {
+export const Upload = ({ uploadDirectory = false }: { uploadDirectory?: boolean }) => {
const onDrop = async (acceptedFiles) => {
console.log(acceptedFiles);
if (acceptedFiles.length > 1) {
@@ -87,7 +94,14 @@ export const Upload = () => {
}}>
diff --git a/packages/resources/src/pages/upload/utils/upload.ts b/packages/resources/src/pages/upload/utils/upload.ts
index 595d7fb..6a18638 100644
--- a/packages/resources/src/pages/upload/utils/upload.ts
+++ b/packages/resources/src/pages/upload/utils/upload.ts
@@ -14,12 +14,25 @@ export const uploadFiles = async (files: File[], opts: ConvertOpts) => {
const { directory } = opts;
return new Promise((resolve, reject) => {
const formData = new FormData();
+ const webkitRelativePath = files[0]?.webkitRelativePath;
+ const keepDirectory = webkitRelativePath !== '';
+ const root = keepDirectory ? webkitRelativePath.split('/')[0] : '';
for (let i = 0; i < files.length; i++) {
- formData.append('file', files[i], files[i].name);
+ const file = files[i];
+ if (keepDirectory) {
+ // relativePath 去除第一级
+ const webkitRelativePath = file.webkitRelativePath.replace(root + '/', '');
+ formData.append('file', file, webkitRelativePath); // 保留文件夹路径
+ } else {
+ formData.append('file', files[i], files[i].name);
+ }
}
if (directory) {
formData.append('directory', directory);
}
+ console.log('formData', formData, files);
+ resolve(null);
+ return;
const token = localStorage.getItem('token');
if (!token) {
toastLogin();
diff --git a/packages/resources/vite.config.mjs b/packages/resources/vite.config.mjs
index 8d4ecb2..a74ea76 100644
--- a/packages/resources/vite.config.mjs
+++ b/packages/resources/vite.config.mjs
@@ -15,6 +15,7 @@ if (true) {
target: 'https://kevisual.silkyai.cn',
changeOrigin: true,
ws: true,
+ cookieDomainRewrite: 'localhost',
rewrite: (path) => path.replace(/^\/api/, '/api'),
},
'/api/router': {
@@ -27,6 +28,7 @@ if (true) {
'/user/login': {
target: 'https://kevisual.silkyai.cn',
changeOrigin: true,
+ cookieDomainRewrite: 'localhost',
rewrite: (path) => path.replace(/^\/user/, '/user'),
},
};
@@ -41,12 +43,27 @@ export default defineConfig({
resolve: {
alias: {
'@': path.resolve(__dirname, './src'),
+ // 'react/jsx-dev-runtime': 'https://cdn.jsdelivr.net/npm/react/jsx-dev-runtime/+esm',
+ // 'react/jsx-runtime': 'https://cdn.jsdelivr.net/npm/react/jsx-runtime/+esm',
+ // 'react/jsx-runtime': path.resolve(__dirname, './node_modules/react/jsx-runtime'),
+ // 'react/jsx-dev-runtime': path.resolve(__dirname, './node_modules/react/jsx-dev-runtime'),
+ // 'react-dom/client': 'https://cdn.jsdelivr.net/npm/react-dom/client/+esm',
+ // react: 'https://cdn.jsdelivr.net/npm/react@19.0.0/+esm',
+ // 'react-dom': 'https://cdn.jsdelivr.net/npm/react-dom@19.0.0/+esm',
+
},
},
define: {
DEV_SERVER: JSON.stringify(process.env.NODE_ENV === 'development'),
+ BASE_NAME: JSON.stringify('/root/resources/'),
+ },
+ base: './',
+ // base: isDev ? '/' : '/root/resources/',
+ build: {
+ rollupOptions: {
+ // external: ['react', 'react-dom'],
+ },
},
- base: isDev ? '/' : '/root/resources/',
server: {
port: 6022,
host: '0.0.0.0',
@@ -59,6 +76,7 @@ export default defineConfig({
target: 'http://localhost:4005',
changeOrigin: true,
ws: true,
+ cookieDomainRewrite: 'localhost',
rewrite: (path) => path.replace(/^\/api/, '/api'),
},
'/api/router': {
@@ -68,12 +86,6 @@ export default defineConfig({
rewriteWsOrigin: true,
rewrite: (path) => path.replace(/^\/api/, '/api'),
},
- '/api/s1/events': {
- target: 'https://kevisual.silkyai.cn',
- changeOrigin: true,
- ws: true,
- rewrite: (path) => path.replace(/^\/api/, '/api'),
- },
...proxy,
},
},
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index c1fc20c..5a0f18f 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -52,7 +52,7 @@ importers:
version: 12.4.4(@types/react@19.0.10)(immer@10.1.1)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
antd:
specifier: ^5.24.3
- version: 5.24.3(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
+ version: 5.24.3(date-fns@4.1.0)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
classnames:
specifier: ^2.5.1
version: 2.5.1
@@ -227,8 +227,8 @@ importers:
specifier: ^0.0.2
version: 0.0.2(rollup@4.34.7)
'@mui/material':
- specifier: ^6.4.7
- version: 6.4.7(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
+ specifier: ^6.4.8
+ version: 6.4.8(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
'@types/lodash-es':
specifier: ^4.17.12
version: 4.17.12
@@ -251,8 +251,8 @@ importers:
specifier: ^0.482.0
version: 0.482.0(react@19.0.0)
nanoid:
- specifier: ^5.1.3
- version: 5.1.3
+ specifier: ^5.1.4
+ version: 5.1.4
nprogress:
specifier: ^0.2.0
version: 0.2.0
@@ -262,6 +262,9 @@ importers:
react:
specifier: 19.0.0
version: 19.0.0
+ react-datepicker:
+ specifier: ^8.2.1
+ version: 8.2.1(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
react-dom:
specifier: 19.0.0
version: 19.0.0(react@19.0.0)
@@ -685,6 +688,27 @@ packages:
resolution: {integrity: sha512-JubJ5B2pJ4k4yGxaNLdbjrnk9d/iDz6/q8wOilpIowd6PJPgaxCuHBnBszq7Ce2TyMrywm5r4PnKm6V3iiZF+g==}
engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0}
+ '@floating-ui/core@1.6.9':
+ resolution: {integrity: sha512-uMXCuQ3BItDUbAMhIXw7UPXRfAlOAvZzdK9BWpE60MCn+Svt3aLn9jsPTi/WNGlRUu2uI0v5S7JiIUsbsvh3fw==}
+
+ '@floating-ui/dom@1.6.13':
+ resolution: {integrity: sha512-umqzocjDgNRGTuO7Q8CU32dkHkECqI8ZdMZ5Swb6QAM0t5rnlrN3lGo1hdpscRd3WS8T6DKYK4ephgIH9iRh3w==}
+
+ '@floating-ui/react-dom@2.1.2':
+ resolution: {integrity: sha512-06okr5cgPzMNBy+Ycse2A6udMi4bqwW/zgBF/rwjcNqWkyr82Mcg8b0vjX8OJpZFy/FKjJmw6wV7t44kK6kW7A==}
+ peerDependencies:
+ react: '>=16.8.0'
+ react-dom: '>=16.8.0'
+
+ '@floating-ui/react@0.27.5':
+ resolution: {integrity: sha512-BX3jKxo39Ba05pflcQmqPPwc0qdNsdNi/eweAFtoIdrJWNen2sVEWMEac3i6jU55Qfx+lOcdMNKYn2CtWmlnOQ==}
+ peerDependencies:
+ react: '>=17.0.0'
+ react-dom: '>=17.0.0'
+
+ '@floating-ui/utils@0.2.9':
+ resolution: {integrity: sha512-MDWhGtE+eHw5JW7lq4qhc5yRLS11ERl1c7Z6Xd0a58DozHES6EnNNwUWbMiG4J9Cgj053Bhk8zvlhFYKVhULwg==}
+
'@humanfs/core@0.19.1':
resolution: {integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==}
engines: {node: '>=18.18.0'}
@@ -777,6 +801,9 @@ packages:
'@mui/core-downloads-tracker@6.4.7':
resolution: {integrity: sha512-XjJrKFNt9zAKvcnoIIBquXyFyhfrHYuttqMsoDS7lM7VwufYG4fAPw4kINjBFg++fqXM2BNAuWR9J7XVIuKIKg==}
+ '@mui/core-downloads-tracker@6.4.8':
+ resolution: {integrity: sha512-vjP4+A1ybyCRhDZC7r5EPWu/gLseFZxaGyPdDl94vzVvk6Yj6gahdaqcjbhkaCrJjdZj90m3VioltWPAnWF/zw==}
+
'@mui/material@6.4.7':
resolution: {integrity: sha512-K65StXUeGAtFJ4ikvHKtmDCO5Ab7g0FZUu2J5VpoKD+O6Y3CjLYzRi+TMlI3kaL4CL158+FccMoOd/eaddmeRQ==}
engines: {node: '>=14.0.0'}
@@ -797,6 +824,26 @@ packages:
'@types/react':
optional: true
+ '@mui/material@6.4.8':
+ resolution: {integrity: sha512-5S9UTjKZZBd9GfbcYh/nYfD9cv6OXmj5Y7NgKYfk7JcSoshp8/pW5zP4wecRiroBSZX8wcrywSgogpVNO+5W0Q==}
+ engines: {node: '>=14.0.0'}
+ peerDependencies:
+ '@emotion/react': ^11.5.0
+ '@emotion/styled': ^11.3.0
+ '@mui/material-pigment-css': ^6.4.8
+ '@types/react': ^17.0.0 || ^18.0.0 || ^19.0.0
+ react: ^17.0.0 || ^18.0.0 || ^19.0.0
+ react-dom: ^17.0.0 || ^18.0.0 || ^19.0.0
+ peerDependenciesMeta:
+ '@emotion/react':
+ optional: true
+ '@emotion/styled':
+ optional: true
+ '@mui/material-pigment-css':
+ optional: true
+ '@types/react':
+ optional: true
+
'@mui/private-theming@6.4.6':
resolution: {integrity: sha512-T5FxdPzCELuOrhpA2g4Pi6241HAxRwZudzAuL9vBvniuB5YU82HCmrARw32AuCiyTfWzbrYGGpZ4zyeqqp9RvQ==}
engines: {node: '>=14.0.0'}
@@ -807,6 +854,16 @@ packages:
'@types/react':
optional: true
+ '@mui/private-theming@6.4.8':
+ resolution: {integrity: sha512-sWwQoNSn6elsPTAtSqCf+w5aaGoh7AASURNmpy+QTTD/zwJ0Jgwt0ZaaP6mXq2IcgHxYnYloM/+vJgHPMkRKTQ==}
+ engines: {node: '>=14.0.0'}
+ peerDependencies:
+ '@types/react': ^17.0.0 || ^18.0.0 || ^19.0.0
+ react: ^17.0.0 || ^18.0.0 || ^19.0.0
+ peerDependenciesMeta:
+ '@types/react':
+ optional: true
+
'@mui/styled-engine@6.4.6':
resolution: {integrity: sha512-vSWYc9ZLX46be5gP+FCzWVn5rvDr4cXC5JBZwSIkYk9xbC7GeV+0kCvB8Q6XLFQJy+a62bbqtmdwS4Ghi9NBlQ==}
engines: {node: '>=14.0.0'}
@@ -820,6 +877,19 @@ packages:
'@emotion/styled':
optional: true
+ '@mui/styled-engine@6.4.8':
+ resolution: {integrity: sha512-oyjx1b1FvUCI85ZMO4trrjNxGm90eLN3Ohy0AP/SqK5gWvRQg1677UjNf7t6iETOKAleHctJjuq0B3aXO2gtmw==}
+ engines: {node: '>=14.0.0'}
+ peerDependencies:
+ '@emotion/react': ^11.4.1
+ '@emotion/styled': ^11.3.0
+ react: ^17.0.0 || ^18.0.0 || ^19.0.0
+ peerDependenciesMeta:
+ '@emotion/react':
+ optional: true
+ '@emotion/styled':
+ optional: true
+
'@mui/system@6.4.7':
resolution: {integrity: sha512-7wwc4++Ak6tGIooEVA9AY7FhH2p9fvBMORT4vNLMAysH3Yus/9B9RYMbrn3ANgsOyvT3Z7nE+SP8/+3FimQmcg==}
engines: {node: '>=14.0.0'}
@@ -836,6 +906,22 @@ packages:
'@types/react':
optional: true
+ '@mui/system@6.4.8':
+ resolution: {integrity: sha512-gV7iBHoqlsIenU2BP0wq14BefRoZcASZ/4LeyuQglayBl+DfLX5rEd3EYR3J409V2EZpR0NOM1LATAGlNk2cyA==}
+ engines: {node: '>=14.0.0'}
+ peerDependencies:
+ '@emotion/react': ^11.5.0
+ '@emotion/styled': ^11.3.0
+ '@types/react': ^17.0.0 || ^18.0.0 || ^19.0.0
+ react: ^17.0.0 || ^18.0.0 || ^19.0.0
+ peerDependenciesMeta:
+ '@emotion/react':
+ optional: true
+ '@emotion/styled':
+ optional: true
+ '@types/react':
+ optional: true
+
'@mui/types@7.2.21':
resolution: {integrity: sha512-6HstngiUxNqLU+/DPqlUJDIPbzUBxIVHb1MmXP0eTWDIROiCR2viugXpEif0PPe2mLqqakPzzRClWAnK+8UJww==}
peerDependencies:
@@ -844,6 +930,14 @@ packages:
'@types/react':
optional: true
+ '@mui/types@7.2.24':
+ resolution: {integrity: sha512-3c8tRt/CbWZ+pEg7QpSwbdxOk36EfmhbKf6AGZsD1EcLDLTSZoxxJ86FVtcjxvjuhdyBiWKSTGZFaXCnidO2kw==}
+ peerDependencies:
+ '@types/react': ^17.0.0 || ^18.0.0 || ^19.0.0
+ peerDependenciesMeta:
+ '@types/react':
+ optional: true
+
'@mui/utils@6.4.6':
resolution: {integrity: sha512-43nZeE1pJF2anGafNydUcYFPtHwAqiBiauRtaMvurdrZI3YrUjHkAu43RBsxef7OFtJMXGiHFvq43kb7lig0sA==}
engines: {node: '>=14.0.0'}
@@ -854,6 +948,16 @@ packages:
'@types/react':
optional: true
+ '@mui/utils@6.4.8':
+ resolution: {integrity: sha512-C86gfiZ5BfZ51KqzqoHi1WuuM2QdSKoFhbkZeAfQRB+jCc4YNhhj11UXFVMMsqBgZ+Zy8IHNJW3M9Wj/LOwRXQ==}
+ engines: {node: '>=14.0.0'}
+ peerDependencies:
+ '@types/react': ^17.0.0 || ^18.0.0 || ^19.0.0
+ react: ^17.0.0 || ^18.0.0 || ^19.0.0
+ peerDependenciesMeta:
+ '@types/react':
+ optional: true
+
'@nodelib/fs.scandir@2.1.5':
resolution: {integrity: sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==}
engines: {node: '>= 8'}
@@ -1676,6 +1780,9 @@ packages:
resolution: {integrity: sha512-e1U46jVP+w7Iut8Jt8ri1YsPOvFpg46k+K8TpCb0P+zjCkjkPnV7WzfDJzMHy1LnA+wj5pLT1wjO901gLXeEhA==}
engines: {node: '>=12'}
+ date-fns@4.1.0:
+ resolution: {integrity: sha512-Ukq0owbQXxa/U3EGtsdVBkR1w7KOQ5gIBqdH2hkvknzZPYvBxb/aa6E8L7tmjFtkwZBu3UXBbjIgPo/Ez4xaNg==}
+
dayjs@1.11.13:
resolution: {integrity: sha512-oaMBel6gjolK862uaPQOVTA7q3TZhuSvuMQAAglQDOWYO9A91IrAOUJEyKVlqJlHE0vq5p5UXxzdPfMH/x6xNg==}
@@ -2189,6 +2296,11 @@ packages:
engines: {node: ^18 || >=20}
hasBin: true
+ nanoid@5.1.4:
+ resolution: {integrity: sha512-GTFcMIDgR7tqji/LpSY8rtg464VnJl/j6ypoehYnuGb+Y8qZUdtKB8WVCXon0UEZgFDbuUxpIl//6FHLHgXSNA==}
+ engines: {node: ^18 || >=20}
+ hasBin: true
+
natural-compare@1.4.0:
resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==}
@@ -2550,6 +2662,12 @@ packages:
react: '>=16.9.0'
react-dom: '>=16.9.0'
+ react-datepicker@8.2.1:
+ resolution: {integrity: sha512-1pyALWM9mTZ7DG7tfcApwBy2kkld9Kz/EI++LhPnoXJAASbvuq6fdsDfkoB3q1JrxF7vhghVmQ759H/rOwUNNw==}
+ peerDependencies:
+ react: ^16.9.0 || ^17 || ^18 || ^19 || ^19.0.0-rc
+ react-dom: ^16.9.0 || ^17 || ^18 || ^19 || ^19.0.0-rc
+
react-dom@19.0.0:
resolution: {integrity: sha512-4GV5sHFG0e/0AD4X+ySy6UJd3jVl1iNsNHdpad0qhABJ11twS3TTBnseqsKurKcsNqCEFeGL3uLpVChpIO3QfQ==}
peerDependencies:
@@ -2767,6 +2885,9 @@ packages:
resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==}
engines: {node: '>= 0.4'}
+ tabbable@6.2.0:
+ resolution: {integrity: sha512-Cat63mxsVJlzYvN51JmVXIgNoUokrIaT2zLclCXjRd8boZ0004U4KCs/sToJ75C6sdlByWxpYnb5Boif1VSFew==}
+
tailwind-merge@3.0.2:
resolution: {integrity: sha512-l7z+OYZ7mu3DTqrL88RiKrKIqO3NcpEO8V/Od04bNpvk0kiIFndGEoqfuzvj4yuhRkHKjRkII2z+KS2HfPcSxw==}
@@ -3432,6 +3553,31 @@ snapshots:
'@eslint/core': 0.12.0
levn: 0.4.1
+ '@floating-ui/core@1.6.9':
+ dependencies:
+ '@floating-ui/utils': 0.2.9
+
+ '@floating-ui/dom@1.6.13':
+ dependencies:
+ '@floating-ui/core': 1.6.9
+ '@floating-ui/utils': 0.2.9
+
+ '@floating-ui/react-dom@2.1.2(react-dom@19.0.0(react@19.0.0))(react@19.0.0)':
+ dependencies:
+ '@floating-ui/dom': 1.6.13
+ react: 19.0.0
+ react-dom: 19.0.0(react@19.0.0)
+
+ '@floating-ui/react@0.27.5(react-dom@19.0.0(react@19.0.0))(react@19.0.0)':
+ dependencies:
+ '@floating-ui/react-dom': 2.1.2(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
+ '@floating-ui/utils': 0.2.9
+ react: 19.0.0
+ react-dom: 19.0.0(react@19.0.0)
+ tabbable: 6.2.0
+
+ '@floating-ui/utils@0.2.9': {}
+
'@humanfs/core@0.19.1': {}
'@humanfs/node@0.16.6':
@@ -3479,7 +3625,7 @@ snapshots:
'@emotion/css': 11.13.4
crypto-js: 4.2.0
eventemitter3: 5.0.1
- nanoid: 5.1.3
+ nanoid: 5.1.4
rollup-plugin-dts: 6.1.1(rollup@4.34.7)(typescript@5.8.2)
scheduler: 0.23.2
zustand: 4.5.5(@types/react@19.0.10)(immer@10.1.1)(react@19.0.0)
@@ -3548,6 +3694,8 @@ snapshots:
'@mui/core-downloads-tracker@6.4.7': {}
+ '@mui/core-downloads-tracker@6.4.8': {}
+
'@mui/material@6.4.7(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)':
dependencies:
'@babel/runtime': 7.26.0
@@ -3569,6 +3717,27 @@ snapshots:
'@emotion/styled': 11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)
'@types/react': 19.0.10
+ '@mui/material@6.4.8(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)':
+ dependencies:
+ '@babel/runtime': 7.26.0
+ '@mui/core-downloads-tracker': 6.4.8
+ '@mui/system': 6.4.8(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)
+ '@mui/types': 7.2.24(@types/react@19.0.10)
+ '@mui/utils': 6.4.8(@types/react@19.0.10)(react@19.0.0)
+ '@popperjs/core': 2.11.8
+ '@types/react-transition-group': 4.4.12(@types/react@19.0.10)
+ clsx: 2.1.1
+ csstype: 3.1.3
+ prop-types: 15.8.1
+ react: 19.0.0
+ react-dom: 19.0.0(react@19.0.0)
+ react-is: 19.0.0
+ react-transition-group: 4.4.5(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
+ optionalDependencies:
+ '@emotion/react': 11.14.0(@types/react@19.0.10)(react@19.0.0)
+ '@emotion/styled': 11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)
+ '@types/react': 19.0.10
+
'@mui/private-theming@6.4.6(@types/react@19.0.10)(react@19.0.0)':
dependencies:
'@babel/runtime': 7.26.0
@@ -3578,6 +3747,15 @@ snapshots:
optionalDependencies:
'@types/react': 19.0.10
+ '@mui/private-theming@6.4.8(@types/react@19.0.10)(react@19.0.0)':
+ dependencies:
+ '@babel/runtime': 7.26.0
+ '@mui/utils': 6.4.8(@types/react@19.0.10)(react@19.0.0)
+ prop-types: 15.8.1
+ react: 19.0.0
+ optionalDependencies:
+ '@types/react': 19.0.10
+
'@mui/styled-engine@6.4.6(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(react@19.0.0)':
dependencies:
'@babel/runtime': 7.26.0
@@ -3591,6 +3769,19 @@ snapshots:
'@emotion/react': 11.14.0(@types/react@19.0.10)(react@19.0.0)
'@emotion/styled': 11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)
+ '@mui/styled-engine@6.4.8(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(react@19.0.0)':
+ dependencies:
+ '@babel/runtime': 7.26.0
+ '@emotion/cache': 11.14.0
+ '@emotion/serialize': 1.3.3
+ '@emotion/sheet': 1.4.0
+ csstype: 3.1.3
+ prop-types: 15.8.1
+ react: 19.0.0
+ optionalDependencies:
+ '@emotion/react': 11.14.0(@types/react@19.0.10)(react@19.0.0)
+ '@emotion/styled': 11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)
+
'@mui/system@6.4.7(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)':
dependencies:
'@babel/runtime': 7.26.0
@@ -3607,10 +3798,30 @@ snapshots:
'@emotion/styled': 11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)
'@types/react': 19.0.10
+ '@mui/system@6.4.8(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)':
+ dependencies:
+ '@babel/runtime': 7.26.0
+ '@mui/private-theming': 6.4.8(@types/react@19.0.10)(react@19.0.0)
+ '@mui/styled-engine': 6.4.8(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@emotion/styled@11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0))(react@19.0.0)
+ '@mui/types': 7.2.24(@types/react@19.0.10)
+ '@mui/utils': 6.4.8(@types/react@19.0.10)(react@19.0.0)
+ clsx: 2.1.1
+ csstype: 3.1.3
+ prop-types: 15.8.1
+ react: 19.0.0
+ optionalDependencies:
+ '@emotion/react': 11.14.0(@types/react@19.0.10)(react@19.0.0)
+ '@emotion/styled': 11.14.0(@emotion/react@11.14.0(@types/react@19.0.10)(react@19.0.0))(@types/react@19.0.10)(react@19.0.0)
+ '@types/react': 19.0.10
+
'@mui/types@7.2.21(@types/react@19.0.10)':
optionalDependencies:
'@types/react': 19.0.10
+ '@mui/types@7.2.24(@types/react@19.0.10)':
+ optionalDependencies:
+ '@types/react': 19.0.10
+
'@mui/utils@6.4.6(@types/react@19.0.10)(react@19.0.0)':
dependencies:
'@babel/runtime': 7.26.0
@@ -3623,6 +3834,18 @@ snapshots:
optionalDependencies:
'@types/react': 19.0.10
+ '@mui/utils@6.4.8(@types/react@19.0.10)(react@19.0.0)':
+ dependencies:
+ '@babel/runtime': 7.26.0
+ '@mui/types': 7.2.24(@types/react@19.0.10)
+ '@types/prop-types': 15.7.14
+ clsx: 2.1.1
+ prop-types: 15.8.1
+ react: 19.0.0
+ react-is: 19.0.0
+ optionalDependencies:
+ '@types/react': 19.0.10
+
'@nodelib/fs.scandir@2.1.5':
dependencies:
'@nodelib/fs.stat': 2.0.5
@@ -4187,7 +4410,7 @@ snapshots:
dependencies:
color-convert: 2.0.1
- antd@5.24.3(react-dom@19.0.0(react@19.0.0))(react@19.0.0):
+ antd@5.24.3(date-fns@4.1.0)(react-dom@19.0.0(react@19.0.0))(react@19.0.0):
dependencies:
'@ant-design/colors': 7.2.0
'@ant-design/cssinjs': 1.23.0(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
@@ -4219,7 +4442,7 @@ snapshots:
rc-motion: 2.9.5(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
rc-notification: 5.6.3(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
rc-pagination: 5.1.0(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
- rc-picker: 4.11.3(dayjs@1.11.13)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
+ rc-picker: 4.11.3(date-fns@4.1.0)(dayjs@1.11.13)(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
rc-progress: 4.0.0(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
rc-rate: 2.13.1(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
rc-resize-observer: 1.4.3(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
@@ -4542,6 +4765,8 @@ snapshots:
d3-transition: 3.0.1(d3-selection@3.0.0)
d3-zoom: 3.0.0
+ date-fns@4.1.0: {}
+
dayjs@1.11.13: {}
debug@4.3.7:
@@ -5062,6 +5287,8 @@ snapshots:
nanoid@5.1.3: {}
+ nanoid@5.1.4: {}
+
natural-compare@1.4.0: {}
node-forge@1.3.1: {}
@@ -5329,7 +5556,7 @@ snapshots:
react: 19.0.0
react-dom: 19.0.0(react@19.0.0)
- rc-picker@4.11.3(dayjs@1.11.13)(react-dom@19.0.0(react@19.0.0))(react@19.0.0):
+ rc-picker@4.11.3(date-fns@4.1.0)(dayjs@1.11.13)(react-dom@19.0.0(react@19.0.0))(react@19.0.0):
dependencies:
'@babel/runtime': 7.26.0
'@rc-component/trigger': 2.2.6(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
@@ -5340,6 +5567,7 @@ snapshots:
react: 19.0.0
react-dom: 19.0.0(react@19.0.0)
optionalDependencies:
+ date-fns: 4.1.0
dayjs: 1.11.13
rc-progress@4.0.0(react-dom@19.0.0(react@19.0.0))(react@19.0.0):
@@ -5505,6 +5733,14 @@ snapshots:
react: 19.0.0
react-dom: 19.0.0(react@19.0.0)
+ react-datepicker@8.2.1(react-dom@19.0.0(react@19.0.0))(react@19.0.0):
+ dependencies:
+ '@floating-ui/react': 0.27.5(react-dom@19.0.0(react@19.0.0))(react@19.0.0)
+ clsx: 2.1.1
+ date-fns: 4.1.0
+ react: 19.0.0
+ react-dom: 19.0.0(react@19.0.0)
+
react-dom@19.0.0(react@19.0.0):
dependencies:
react: 19.0.0
@@ -5737,6 +5973,8 @@ snapshots:
supports-preserve-symlinks-flag@1.0.0: {}
+ tabbable@6.2.0: {}
+
tailwind-merge@3.0.2: {}
tailwindcss-animate@1.0.7(tailwindcss@4.0.12):