diff --git a/package.json b/package.json index 57e3ec0..24ef22e 100644 --- a/package.json +++ b/package.json @@ -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", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index f53eb1d..158d090 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -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: diff --git a/src/main/backend/constants/index.ts b/src/main/backend/constants/index.ts index 8aee3e4..94397cd 100644 --- a/src/main/backend/constants/index.ts +++ b/src/main/backend/constants/index.ts @@ -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', diff --git a/src/renderer/index.tsx b/src/renderer/index.tsx index c5c169e..e366123 100644 --- a/src/renderer/index.tsx +++ b/src/renderer/index.tsx @@ -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(); +root.render( + + + , +); // calling IPC exposed from preload script window.electron.ipcRenderer.once('ipc-example', (arg) => { diff --git a/src/renderer/pages/Home/PlatformTabs.tsx b/src/renderer/pages/Home/AppManager/PlatformTabs.tsx similarity index 90% rename from src/renderer/pages/Home/PlatformTabs.tsx rename to src/renderer/pages/Home/AppManager/PlatformTabs.tsx index f44081b..70bea7b 100644 --- a/src/renderer/pages/Home/PlatformTabs.tsx +++ b/src/renderer/pages/Home/AppManager/PlatformTabs.tsx @@ -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) { diff --git a/src/renderer/pages/Home/AppManager/index.tsx b/src/renderer/pages/Home/AppManager/index.tsx new file mode 100644 index 0000000..9bb5f00 --- /dev/null +++ b/src/renderer/pages/Home/AppManager/index.tsx @@ -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 ( + + + + + + + + } + variant="ghost" + colorScheme="brand" + aria-label="Search" + size="sm" + /> + + + + + + {[...Array(20)].map((_, i) => ( + + + + {i === 1 && ( + + 2 + + )} + {i === 2 && ( + + 5 + + )} + + ))} + + + + + {[...Array(20)].map((_, i) => ( + + ))} + + + + + + + + + + ); +}; + +export default React.memo(AppManagerComponent); diff --git a/src/renderer/pages/Home/EditKeyword.tsx b/src/renderer/pages/Home/EditKeyword/index.tsx similarity index 97% rename from src/renderer/pages/Home/EditKeyword.tsx rename to src/renderer/pages/Home/EditKeyword/index.tsx index 289bb0f..79c28e2 100644 --- a/src/renderer/pages/Home/EditKeyword.tsx +++ b/src/renderer/pages/Home/EditKeyword/index.tsx @@ -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; diff --git a/src/renderer/pages/Home/LogBox.tsx b/src/renderer/pages/Home/LogBox/index.tsx similarity index 93% rename from src/renderer/pages/Home/LogBox.tsx rename to src/renderer/pages/Home/LogBox/index.tsx index 948aa10..f5e3438 100644 --- a/src/renderer/pages/Home/LogBox.tsx +++ b/src/renderer/pages/Home/LogBox/index.tsx @@ -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(); diff --git a/src/renderer/pages/Home/DriverSettings.tsx b/src/renderer/pages/Home/Panels/index.tsx similarity index 53% rename from src/renderer/pages/Home/DriverSettings.tsx rename to src/renderer/pages/Home/Panels/index.tsx index db972c1..7fdf59d 100644 --- a/src/renderer/pages/Home/DriverSettings.tsx +++ b/src/renderer/pages/Home/Panels/index.tsx @@ -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 ( - - - 连接 - 日志 - - - - - - - - - 暂停软件 - - - - - 关键词匹配 - - - - - GPT 回复 - - - - - - - - - - - - + <> + + + + 暂停软件 + + + + 关键词匹配 + + + + + GPT 回复 + + + + + ); }; -export default DriverSettings; +export default React.memo(Panels); diff --git a/src/renderer/pages/Home/ReplyKeyword.tsx b/src/renderer/pages/Home/ReplyKeyword/index.tsx similarity index 98% rename from src/renderer/pages/Home/ReplyKeyword.tsx rename to src/renderer/pages/Home/ReplyKeyword/index.tsx index dcb73bd..8a297bb 100644 --- a/src/renderer/pages/Home/ReplyKeyword.tsx +++ b/src/renderer/pages/Home/ReplyKeyword/index.tsx @@ -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([]); diff --git a/src/renderer/pages/Home/index.tsx b/src/renderer/pages/Home/index.tsx index 46a43f4..ece569d 100644 --- a/src/renderer/pages/Home/index.tsx +++ b/src/renderer/pages/Home/index.tsx @@ -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 ( - + + + 应用 + 连接 + 日志 + + + + + + + + + + + + + + + + - + {/* */} ); }; diff --git a/src/renderer/pages/MsgList/index.tsx b/src/renderer/pages/MsgList/index.tsx index b610b5a..a0576df 100644 --- a/src/renderer/pages/MsgList/index.tsx +++ b/src/renderer/pages/MsgList/index.tsx @@ -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(''); diff --git a/src/renderer/pages/Settings/index.tsx b/src/renderer/pages/Settings/index.tsx index eb162aa..a08d499 100644 --- a/src/renderer/pages/Settings/index.tsx +++ b/src/renderer/pages/Settings/index.tsx @@ -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 { diff --git a/src/renderer/services/analytics/index_template.ts b/src/renderer/services/analytics/index_template.ts index aa07a55..6ce8697 100644 --- a/src/renderer/services/analytics/index_template.ts +++ b/src/renderer/services/analytics/index_template.ts @@ -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); +}