mv: 重新编写首页布局

This commit is contained in:
lrhh123
2024-06-06 21:11:11 +08:00
parent 9b4f034ef6
commit 0751fbd8ad
14 changed files with 246 additions and 241 deletions
+2 -3
View File
@@ -92,15 +92,13 @@
}
},
"dependencies": {
"@agconnect/api": "^1.3.2",
"@agconnect/instance": "^1.3.2",
"@chakra-ui/anatomy": "^2.2.2",
"@chakra-ui/icons": "^2.1.1",
"@chakra-ui/react": "^2.8.2",
"@emotion/react": "^11.11.3",
"@emotion/styled": "^11.11.0",
"@hw-hmscore/analytics-web": "6.9.9-301",
"@tanstack/react-query": "4.36.1",
"@vercel/analytics": "^1.3.1",
"ansi-styles": "^6.2.1",
"axios": "^1.6.7",
"body-parser": "^1.20.2",
@@ -130,6 +128,7 @@
"pg-hstore": "^2.3.4",
"react": "^18.2.0",
"react-dom": "^18.2.0",
"react-ga4": "^2.1.0",
"react-hook-form": "^7.50.1",
"react-icons": "^5.0.1",
"react-markdown": "^9.0.1",
+29 -118
View File
@@ -5,12 +5,6 @@ settings:
excludeLinksFromLockfile: false
dependencies:
'@agconnect/api':
specifier: ^1.3.2
version: 1.3.2
'@agconnect/instance':
specifier: ^1.3.2
version: 1.3.2
'@chakra-ui/anatomy':
specifier: ^2.2.2
version: 2.2.2
@@ -26,12 +20,12 @@ dependencies:
'@emotion/styled':
specifier: ^11.11.0
version: 11.11.5(@emotion/react@11.11.4)(@types/react@18.3.0)(react@18.3.0)
'@hw-hmscore/analytics-web':
specifier: 6.9.9-301
version: 6.9.9-301(debug@4.3.4)
'@tanstack/react-query':
specifier: 4.36.1
version: 4.36.1(react-dom@18.3.0)(react@18.3.0)
'@vercel/analytics':
specifier: ^1.3.1
version: 1.3.1(react@18.3.0)
ansi-styles:
specifier: ^6.2.1
version: 6.2.1
@@ -119,6 +113,9 @@ dependencies:
react-dom:
specifier: ^18.2.0
version: 18.3.0(react@18.3.0)
react-ga4:
specifier: ^2.1.0
version: 2.1.0
react-hook-form:
specifier: ^7.50.1
version: 7.51.3(react@18.3.0)
@@ -431,90 +428,6 @@ packages:
resolution: {integrity: sha512-rE0Pygv0sEZ4vBWHlAgJLGDU7Pm8xoO6p3wsEceb7GYAjScrOHpEo8KK/eVkAcnSM+slAEtXjA2JpdjLp4fJQQ==}
dev: true
/@agconnect/api-types@1.3.2:
resolution: {integrity: sha512-ON91lFZrolyAwlebx284lXQaDpYEUa5Krg+AfgZsLf+LQxm+/8gNxt90NPfPwvn1Y0Qt0WpCId09dofUrNB9FA==}
dev: false
/@agconnect/api@1.3.2:
resolution: {integrity: sha512-9GR0yqvfvltL2yvNpo8thrmf8mG2C3yUjZSkLI/WYD/PIVmt0zW4JaMEZSwsmyvaln+a/wL2aTA3Lcf/hkyxnQ==}
dependencies:
'@agconnect/api-types': 1.3.2
dev: false
/@agconnect/core@1.3.2:
resolution: {integrity: sha512-7gRO/NpaltGc1UKqEmWSlmEsQ+E4QIlMVCAsz5pgN3LGT3uKPkbLTE4QFBFhU+ZtCnj4o93kUMjf/tQOdIWZ/g==}
dev: false
/@agconnect/instance-types@1.3.2:
resolution: {integrity: sha512-7fwFO8LsPXoQSWhfFq9ZOczaOK/oWSrYui93MMT6YW089cXBrBxWHwzAwCoJ4dZ7bQKPSNzfdQFmSbheTGnd4w==}
dev: false
/@agconnect/instance@1.3.2:
resolution: {integrity: sha512-AeNvv7sdQGKSNo5XPe+2QzS77Dv1oNIaQqgXIj/BKEUl01ZSGBjAcMCLLMNjdSTJgGLhN2hc5Sse8TJXbRqRuQ==}
dependencies:
'@agconnect/api': 1.3.2
'@agconnect/api-types': 1.3.2
'@agconnect/core': 1.3.2
'@agconnect/instance-types': 1.3.2
'@agconnect/log': 1.3.2
dev: false
/@agconnect/log@1.3.2:
resolution: {integrity: sha512-qOXNMr2AC+GivMbuI9dgYjmOVe02AEKyMimUmz17NAccmBDvO+WgOOxoigoDdyGhdnGYJcF2BRC1UXZ8LYIz/g==}
dependencies:
'@agconnect/api': 1.3.2
'@agconnect/api-types': 1.3.2
'@agconnect/instance-types': 1.3.2
dev: false
/@agconnect/network-types@1.3.2:
resolution: {integrity: sha512-r92hbxBWWHqVvAFf2AUlvkcnjbJP2flf/zb9f/ZOrir35I/RXoWVlPrCOZskcnsLwc5MFJCnvGqKoh6fXRUJZQ==}
dev: false
/@agconnect/network@1.3.2(debug@4.3.4):
resolution: {integrity: sha512-ftOLzrCgMsq/I9Qisi+5Um1papxUViLRZB8KLOQD3iolvh/RI+/JaMsgubvp/INX6Pf5A1qbdwHPFnVxUWKuHg==}
dependencies:
'@agconnect/api': 1.3.2
'@agconnect/api-types': 1.3.2
'@agconnect/instance': 1.3.2
'@agconnect/instance-types': 1.3.2
'@agconnect/log': 1.3.2
'@agconnect/network-types': 1.3.2
axios: 0.21.4(debug@4.3.4)
ua-parser-js: 0.7.28
transitivePeerDependencies:
- debug
dev: false
/@agconnect/storage-types@1.3.2:
resolution: {integrity: sha512-HCugEBmMPAFa4ZeyOooOtyaY9GlPt00HGZDFWV4o0ckmslQrLSEVHRozIoOxhBdRBH5VllK20eY9Ip4vxMv18Q==}
dev: false
/@agconnect/storage@1.3.2:
resolution: {integrity: sha512-COBUvtZR7MBItZ7Fc5lQBPQfe2rqMAbAB3hvfwcLDOUlvWm33QL3aa9Yfl9iiogLoV4GNmelS3M+Yb+IsX/7ow==}
dependencies:
'@agconnect/api': 1.3.2
'@agconnect/api-types': 1.3.2
'@agconnect/core': 1.3.2
'@agconnect/instance': 1.3.2
'@agconnect/instance-types': 1.3.2
'@agconnect/log': 1.3.2
'@agconnect/storage-types': 1.3.2
dev: false
/@agconnect/util@1.3.2:
resolution: {integrity: sha512-ud69EkUwDGrQ5fe/lp0hQWUWqxUjC0J+sDHtEBIKLYbWG0C1YSd/Uybc5TqJC7qN8rsGo9zOl0h71xeEGbdK4w==}
dependencies:
'@agconnect/api': 1.3.2
'@agconnect/api-types': 1.3.2
'@agconnect/core': 1.3.2
'@agconnect/instance': 1.3.2
'@agconnect/instance-types': 1.3.2
'@agconnect/log': 1.3.2
'@agconnect/storage': 1.3.2
'@agconnect/storage-types': 1.3.2
dev: false
/@ampproject/remapping@2.3.0:
resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==}
engines: {node: '>=6.0.0'}
@@ -3258,19 +3171,6 @@ packages:
resolution: {integrity: sha512-93zYdMES/c1D69yZiKDBj0V24vqNzB/koF26KPaagAfd3P/4gUlh3Dys5ogAK+Exi9QyzlD8x/08Zt7wIKcDcA==}
dev: true
/@hw-hmscore/analytics-web@6.9.9-301(debug@4.3.4):
resolution: {integrity: sha512-37hZGpGxSXpGRMDmU1zFxK5+woDkKXjyHq0IFLWUGa2ChnQwHs1OUuYKSOt1JOrasa2dfyHGpAImETc4AR/JPA==}
dependencies:
'@agconnect/api': 1.3.2
'@agconnect/core': 1.3.2
'@agconnect/instance': 1.3.2
'@agconnect/network': 1.3.2(debug@4.3.4)
'@agconnect/storage': 1.3.2
'@agconnect/util': 1.3.2
transitivePeerDependencies:
- debug
dev: false
/@isaacs/cliui@8.0.2:
resolution: {integrity: sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==}
engines: {node: '>=12'}
@@ -4646,6 +4546,21 @@ packages:
/@ungap/structured-clone@1.2.0:
resolution: {integrity: sha512-zuVdFrMJiuCDQUMCzQaD6KL28MjnqqN8XnAqiEq9PNm/hCPTSGfrXCOfwj1ow4LFb/tNymJPwsNbVePc1xFqrQ==}
/@vercel/analytics@1.3.1(react@18.3.0):
resolution: {integrity: sha512-xhSlYgAuJ6Q4WQGkzYTLmXwhYl39sWjoMA3nHxfkvG+WdBT25c563a7QhwwKivEOZtPJXifYHR1m2ihoisbWyA==}
peerDependencies:
next: '>= 13'
react: ^18 || ^19
peerDependenciesMeta:
next:
optional: true
react:
optional: true
dependencies:
react: 18.3.0
server-only: 0.0.1
dev: false
/@webassemblyjs/ast@1.12.1:
resolution: {integrity: sha512-EKfMUOPRRUTy5UII4qJDGPpqfwjOmZ5jeGFwid9mnoqIFK+e0vqoi1qH56JpmZSzEL53jKnNzScdmftJyG5xWg==}
dependencies:
@@ -5370,14 +5285,6 @@ packages:
engines: {node: '>=4'}
dev: true
/axios@0.21.4(debug@4.3.4):
resolution: {integrity: sha512-ut5vewkiu8jjGBdqpM44XxjuCjq9LAKeHVmoVfHVzy8eHgxxq8SbAVQNovDA8mVi05kP0Ea/n/UzcSHcTJQfNg==}
dependencies:
follow-redirects: 1.15.6(debug@4.3.4)
transitivePeerDependencies:
- debug
dev: false
/axios@1.6.8(debug@4.3.4):
resolution: {integrity: sha512-v/ZHtJDU39mDpyBoFVkETcd/uNdxrWRrg3bKpOKzXFA6Bvqopts6ALSMU3y6ijYxbw2B+wPrIv46egTzJXCLGQ==}
dependencies:
@@ -12420,6 +12327,10 @@ packages:
use-sidecar: 1.1.2(@types/react@18.3.0)(react@18.3.0)
dev: false
/react-ga4@2.1.0:
resolution: {integrity: sha512-ZKS7PGNFqqMd3PJ6+C2Jtz/o1iU9ggiy8Y8nUeksgVuvNISbmrQtJiZNvC/TjDsqD0QlU5Wkgs7i+w9+OjHhhQ==}
dev: false
/react-hook-form@7.51.3(react@18.3.0):
resolution: {integrity: sha512-cvJ/wbHdhYx8aviSWh28w9ImjmVsb5Y05n1+FW786vEZQJV5STNM0pW6ujS+oiBecb0ARBxJFyAnXj9+GHXACQ==}
engines: {node: '>=12.22.0'}
@@ -13216,6 +13127,10 @@ packages:
transitivePeerDependencies:
- supports-color
/server-only@0.0.1:
resolution: {integrity: sha512-qepMx2JxAa5jjfzxG79yPPq+8BuFToHd1hm7kI+Z4zAq1ftQiP7HcxMhDDItrbtwVeLg/cY2JnKnrcFkmiswNA==}
dev: false
/set-blocking@2.0.0:
resolution: {integrity: sha512-KiKBS8AnWGEyLzofFfmvKwpdPzqiy16LvQfK3yv/fVH7Bj13/wl3JSR1J+rfgRE9q7xUJK4qvgS8raSOeLUehw==}
requiresBuild: true
@@ -14326,10 +14241,6 @@ packages:
hasBin: true
dev: true
/ua-parser-js@0.7.28:
resolution: {integrity: sha512-6Gurc1n//gjp9eQNXjD9O3M/sMwVtN5S8Lv9bvOYBfKfDNiIIhqiyi01vMBO45u4zkDE420w/e0se7Vs+sIg+g==}
dev: false
/unbox-primitive@1.0.2:
resolution: {integrity: sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==}
dependencies:
+1 -1
View File
@@ -309,7 +309,7 @@ export const ALL_PLATFORMS: Platform[] = [
avatar:
'https://wwcdn.weixin.qq.com/node/wwnl/wwnl/style/images/independent/favicon/favicon_32h$a41a4426.png',
desc: '',
impl: false,
impl: true,
},
{
id: 'win_qianniu',
+9 -2
View File
@@ -1,10 +1,17 @@
import React from 'react';
import { createRoot } from 'react-dom/client';
import ReactGA from 'react-ga4';
import App from './App';
import { trackingID } from './services/analytics';
ReactGA.initialize(trackingID);
const container = document.getElementById('root') as HTMLElement;
const root = createRoot(container);
root.render(<App />);
root.render(
<React.StrictMode>
<App />
</React.StrictMode>,
);
// calling IPC exposed from preload script
window.electron.ipcRenderer.once('ipc-example', (arg) => {
@@ -21,17 +21,17 @@ import { useQuery } from '@tanstack/react-query';
import {
getPlatformList,
updatePlatform,
} from '../../services/platform/controller';
import { Platform } from '../../services/platform/platform';
import PlatformSettings from '../../components/PlatformConfigs';
} from '../../../services/platform/controller';
import { Platform } from '../../../services/platform/platform';
import PlatformSettings from '../../../components/PlatformConfigs';
import {
PlatformTypeMap,
PlatformTypeEnum,
} from '../../services/platform/constant';
import { useSystemStore } from '../../stores/useSystemStore';
} from '../../../services/platform/constant';
import { useSystemStore } from '../../../stores/useSystemStore';
import defaultPlatformIcon from '../../../../assets/base/default-platform-icon.png';
import windowsIcon from '../../../../assets/base/windows.png';
import analytics from '../../services/analytics';
import { trackCheckboxChange } from '../../../services/analytics';
const PlatformTabs = () => {
const { data, isLoading } = useQuery(['platformList'], getPlatformList);
@@ -63,15 +63,9 @@ const PlatformTabs = () => {
}, [firstLoad, setFirstLoad, selectedPlatforms]);
const handleCheckboxChange = async (selectedIds: string[]) => {
const oldSelectedIds = selectedPlatforms;
setSelectedPlatforms(selectedIds);
await updatePlatform(selectedIds);
analytics.onEvent('$ModifySetting', {
$NewValue: selectedIds,
$OldValue: oldSelectedIds,
$Type: 'platforms',
});
trackCheckboxChange('platforms', selectedIds);
};
if (isLoading) {
@@ -0,0 +1,81 @@
import React from 'react';
import {
Box,
Flex,
Input,
InputGroup,
InputRightElement,
Badge,
Text,
VStack,
IconButton,
Spacer,
} from '@chakra-ui/react';
import { SearchIcon } from '@chakra-ui/icons';
const AppManagerComponent = () => {
const high = '42vh'; // 调整为合适的全局高度
return (
<Flex h={high}>
<Box w="40%" bg="brand.50" display="flex" flexDirection="column">
<Box p={4} position="sticky" top="0" zIndex="1">
<Flex align="center">
<InputGroup>
<Input placeholder="搜索" />
<InputRightElement>
<IconButton
icon={<SearchIcon />}
variant="ghost"
colorScheme="brand"
aria-label="Search"
size="sm"
/>
</InputRightElement>
</InputGroup>
</Flex>
</Box>
<VStack spacing={3} align="stretch" overflowY="auto" flex="1" p={4}>
{[...Array(20)].map((_, i) => (
<Flex key={i} bg="red.100" borderRadius="md" p={3} align="center">
<Box w="100%" h="50px" bg="gray.200" borderRadius="md" />
<Spacer />
{i === 1 && (
<Badge ml="1" colorScheme="red">
2
</Badge>
)}
{i === 2 && (
<Badge ml="1" colorScheme="red">
5
</Badge>
)}
</Flex>
))}
</VStack>
</Box>
<Box w="60%" p={4} bg="gray.50" overflowY="auto">
<VStack spacing={4}>
{[...Array(20)].map((_, i) => (
<Box key={i} w="100%" h="100px" bg="gray.200" borderRadius="md" />
))}
<Box
w="100%"
h="100px"
bg="gray.300"
borderRadius="md"
display="flex"
justifyContent="center"
alignItems="center"
>
<Text fontSize="3xl" color="gray.500">
+
</Text>
</Box>
</VStack>
</Box>
</Flex>
);
};
export default React.memo(AppManagerComponent);
@@ -23,11 +23,11 @@ import {
getPlatformList,
addReplyKeyword,
updateReplyKeyword,
} from '../../services/platform/controller';
import MyTextarea from '../../components/MyTextarea';
import Markdown from '../../components/Markdown';
import MyModal from '../../components/MyModal';
import { Reply, Platform } from '../../services/platform/platform';
} from '../../../services/platform/controller';
import MyTextarea from '../../../components/MyTextarea';
import Markdown from '../../../components/Markdown';
import MyModal from '../../../components/MyModal';
import { Reply, Platform } from '../../../services/platform/platform';
interface EditKeywordProps {
editKeyword: Reply | null;
@@ -12,8 +12,8 @@ import {
Box,
VStack,
} from '@chakra-ui/react';
import { useWebSocketContext } from '../../hooks/useBroadcastContext';
import useGlobalStore from '../../stores/useGlobalStore';
import { useWebSocketContext } from '../../../hooks/useBroadcastContext';
import useGlobalStore from '../../../stores/useGlobalStore';
const LogBox = () => {
const { logs, clearLogs, addLog } = useGlobalStore();
@@ -1,22 +1,10 @@
import React, { useEffect } from 'react';
import {
Tabs,
TabList,
Tab,
TabPanels,
TabPanel,
Checkbox,
Stack,
HStack,
Tooltip,
} from '@chakra-ui/react';
import { Checkbox, Stack, HStack, Tooltip } from '@chakra-ui/react';
import { updateRunner } from '../../../services/platform/controller';
import { useSystemStore } from '../../../stores/useSystemStore';
import { useToast } from '../../../hooks/useToast';
import { updateRunner } from '../../services/platform/controller';
import { useSystemStore } from '../../stores/useSystemStore';
import { useToast } from '../../hooks/useToast';
import LogBox from './LogBox';
const DriverSettings = () => {
const Panels = () => {
const { toast } = useToast();
const { driverSettings, setDriverSettings, selectedPlatforms } =
useSystemStore();
@@ -43,7 +31,7 @@ const DriverSettings = () => {
window.electron.ipcRenderer.remove('refresh-config');
};
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [toast]);
}, []);
const handleFormChange = (field: string) => (event: any) => {
const { value, checked, type } = event.target;
@@ -94,52 +82,36 @@ const DriverSettings = () => {
};
return (
<Tabs>
<TabList>
<Tab></Tab>
<Tab></Tab>
</TabList>
<TabPanels>
<TabPanel>
<Stack spacing={4}>
<HStack width="full" alignItems="center">
<Checkbox
mr={4}
isChecked={driverSettings.isPaused}
onChange={handleFormChange('isPaused')}
>
<Tooltip label="暂停软件后,将不再自动回复消息">
</Tooltip>
</Checkbox>
<Checkbox
isChecked={driverSettings.isKeywordMatch}
onChange={handleFormChange('isKeywordMatch')}
>
<Tooltip label="将优先匹配关键词,未匹配的才去调用 GPT 接口">
</Tooltip>
</Checkbox>
<Checkbox
isChecked={driverSettings.isUseGpt}
onChange={handleFormChange('isUseGpt')}
>
<Tooltip label="是否开启 GPT 回复,关闭后只会使用关键词回复">
GPT
</Tooltip>
</Checkbox>
</HStack>
</Stack>
</TabPanel>
<TabPanel>
<Stack spacing={4}>
<LogBox />
</Stack>
</TabPanel>
</TabPanels>
</Tabs>
<>
<Stack spacing={4}>
<HStack width="full" alignItems="center">
<Checkbox
mr={4}
isChecked={driverSettings.isPaused}
onChange={handleFormChange('isPaused')}
>
<Tooltip label="暂停软件后,将不再自动回复消息"></Tooltip>
</Checkbox>
<Checkbox
isChecked={driverSettings.isKeywordMatch}
onChange={handleFormChange('isKeywordMatch')}
>
<Tooltip label="将优先匹配关键词,未匹配的才去调用 GPT 接口">
</Tooltip>
</Checkbox>
<Checkbox
isChecked={driverSettings.isUseGpt}
onChange={handleFormChange('isUseGpt')}
>
<Tooltip label="是否开启 GPT 回复,关闭后只会使用关键词回复">
GPT
</Tooltip>
</Checkbox>
</HStack>
</Stack>
</>
);
};
export default DriverSettings;
export default React.memo(Panels);
@@ -22,14 +22,14 @@ import {
} from '@chakra-ui/react';
import { DeleteIcon, AddIcon, EditIcon } from '@chakra-ui/icons';
import { useQuery } from '@tanstack/react-query';
import EditKeyword from './EditKeyword';
import EditKeyword from '../EditKeyword';
import {
getReplyList,
deleteReplyKeyword,
updateReplyExcel,
exportReplyExcel,
} from '../../services/platform/controller';
import { Reply } from '../../services/platform/platform';
} from '../../../services/platform/controller';
import { Reply } from '../../../services/platform/platform';
const ReplyKeyword = () => {
const [keywords, setKeywords] = useState<Reply[]>([]);
+36 -9
View File
@@ -1,26 +1,53 @@
import React, { useEffect } from 'react';
import { Box } from '@chakra-ui/react';
import {
Box,
Tabs,
TabList,
Tab,
TabPanels,
TabPanel,
Stack,
} from '@chakra-ui/react';
import PageContainer from '../../components/PageContainer';
import PlatformTabs from './PlatformTabs';
import DriverSettings from './DriverSettings';
import ReplyKeyword from './ReplyKeyword';
import analytics from '../../services/analytics';
import { trackPageView } from '../../services/analytics';
import AppManager from './AppManager';
import Panels from './Panels';
import LogBox from './LogBox';
const HomePage = () => {
useEffect(() => {
// 页面访问埋点
analytics.onEvent('$PageView', {
$PageName: 'home',
});
trackPageView('Home');
}, []);
return (
<PageContainer>
<ReplyKeyword />
<Box mb={4}>
<DriverSettings />
<Tabs>
<TabList>
<Tab></Tab>
<Tab></Tab>
<Tab></Tab>
</TabList>
<TabPanels>
<TabPanel padding="0">
<Stack>
<AppManager />
</Stack>
</TabPanel>
<TabPanel>
<Panels />
</TabPanel>
<TabPanel>
<LogBox />
</TabPanel>
</TabPanels>
</Tabs>
</Box>
<PlatformTabs />
{/* <PlatformTabs /> */}
</PageContainer>
);
};
+2 -4
View File
@@ -16,16 +16,14 @@ import {
getMessageList,
} from '../../services/platform/controller';
import SessionBox from './SessionBox';
import analytics from '../../services/analytics';
import { trackPageView } from '../../services/analytics';
import { Message } from '../../services/platform/platform';
// 假设数据通过 props.sessions 传递
const MsgList = () => {
useEffect(() => {
// 页面访问埋点
analytics.onEvent('$PageView', {
$PageName: 'msg_list',
});
trackPageView('Message List');
}, []);
const [ptf, setPtf] = useState<string>('');
+2 -4
View File
@@ -5,14 +5,12 @@ import GptSettings from './GptSettings';
import CustomerServiceSettings from './CustomerServiceSettings';
import { getConfig, updateConfig } from '../../services/platform/controller';
import { useSettings } from './SettingsContext';
import analytics from '../../services/analytics';
import { trackPageView } from '../../services/analytics';
const SettingsPage = () => {
useEffect(() => {
// 页面访问埋点
analytics.onEvent('$PageView', {
$PageName: 'settings',
});
trackPageView('Settings');
}, []);
const {
@@ -1,16 +1,34 @@
import agconnect from '@agconnect/api';
import '@agconnect/instance';
import '@hw-hmscore/analytics-web';
import ua from 'universal-analytics';
const agConnectConfig = {
// TODO: 请替换为您的应用 ID
// 修改该文件名称为 index.ts
// 这里使用的是华为的服务用于打点
};
// 这里使用了 Google Analytics 的跟踪 ID,如果不使用,可以直接注释掉相关代码,Mock 掉相关函数
const trackingID = 'UA-XXXXXXXXX-X';
const visitor = ua(trackingID);
// 初始化分析实例
// @ts-ignore
agconnect.instance().configInstance(agConnectConfig);
const analytics = agconnect.analytics();
export function sendEvent(
category: string,
action: string,
label: string,
value: string | number,
) {
visitor.event(category, action, label, value).send();
}
export default analytics;
// 预制事件:打开按钮
export function trackButtonClick(buttonName: string) {
sendEvent('UI Interaction', 'Click', `Button: ${buttonName}`, 1);
}
// 预制事件:多选框
export function trackCheckboxChange(checkboxName: string, value: string[]) {
sendEvent(
'UI Interaction',
'Change',
`Checkbox: ${checkboxName}`,
value.join(','),
);
}
// 预制事件:打开页面
export function trackPageView(pageName: string) {
sendEvent('Navigation', 'Open', `Page: ${pageName}`, 1);
}