From faeb46ed14fa74c6bbd0f73233a2730a43d27c27 Mon Sep 17 00:00:00 2001 From: liuyi <> Date: Thu, 20 Jul 2023 22:59:19 +0800 Subject: [PATCH 1/3] feat: remove hotjar --- app/web/app.tsx | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/app/web/app.tsx b/app/web/app.tsx index 11fc9d1..4701067 100644 --- a/app/web/app.tsx +++ b/app/web/app.tsx @@ -15,18 +15,7 @@ declare var window: any; const App = () => { const { changeLocalIp } = bindActionCreators(actions, useDispatch()); - const hotJar = () => { - (function (h: any, o: any, t: any, j: any, a?: any, r?: any) { - h.hj = h.hj || function () { (h.hj.q = h.hj.q || []).push(arguments) }; - h._hjSettings = { hjid: 2133522, hjsv: 6 }; - a = o.getElementsByTagName('head')[0]; - r = o.createElement('script'); r.async = 1; - r.src = t + h._hjSettings.hjid + j + h._hjSettings.hjsv; - a.appendChild(r); - })(window, document, 'https://static.hotjar.com/c/hotjar-', '.js?sv='); - } useEffect(() => { - hotJar(); changeLocalIp(); }, []) return ( From bb379a46e443171378cee6b338b52101d1e17513 Mon Sep 17 00:00:00 2001 From: liuyi <> Date: Thu, 20 Jul 2023 23:02:13 +0800 Subject: [PATCH 2/3] feat: use localIp from redux props --- app/web/pages/proxyServer/index.tsx | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/app/web/pages/proxyServer/index.tsx b/app/web/pages/proxyServer/index.tsx index 90e3d28..666a575 100644 --- a/app/web/pages/proxyServer/index.tsx +++ b/app/web/pages/proxyServer/index.tsx @@ -17,8 +17,6 @@ const { Paragraph } = Typography; class ProxyServer extends React.PureComponent { state: any = { - //代理服务 - localIp: '', currentProxyServer: {}, proxyServerModalVisible: false, proxyServerModalConfirmLoading: false, @@ -135,7 +133,7 @@ class ProxyServer extends React.PureComponent { } //获取子表格数据 loadSubTableData(row: any) { - const { localIp } = this.state; + const { localIp } = this.props; const { id } = row; const allIPChecked = localStorage.getItem(`${ localIp }-${ id }-all-ip-checked`) !== 'no' this.setState({ @@ -438,7 +436,8 @@ class ProxyServer extends React.PureComponent { localStorage.setItem('collection-tags', JSON.stringify(newList)); }; tableExpandedRowRender = (mainTableRow: any) => { - const { subTableLoading, subTableData, localIp, allIPChecked } = this.state; + const { subTableLoading, subTableData, allIPChecked } = this.state; + const { localIp } = this.props; const columns: any = [{ title: '序号', key: 'index', @@ -530,7 +529,7 @@ class ProxyServer extends React.PureComponent { // 只看我的 IP (false)或者全部(true) handleIPFilter = (allIPChecked, mainTableRow) => { - const { localIp } = this.state; + const { localIp } = this.props; localStorage.setItem(`${ localIp }-${ mainTableRow.id }-all-ip-checked`, allIPChecked ? 'yes' : 'no') Message.success(`${ allIPChecked ? '查看全部' : '只看我的IP' }`) this.setState({ @@ -549,8 +548,8 @@ class ProxyServer extends React.PureComponent { }) } render() { + const { localIp } = this.props; const { - localIp, maintTableList, mainTableParams, maintTableTotal, From 71fa5dce52d0c4d2f4763b544606b767b6510653 Mon Sep 17 00:00:00 2001 From: liuyi <> Date: Thu, 20 Jul 2023 23:02:52 +0800 Subject: [PATCH 3/3] feat: set localIp by yourself --- app/web/app.tsx | 6 +- app/web/layouts/header/header.tsx | 118 ++++++++++++++++-- app/web/pages/proxyServer/index.tsx | 26 +--- app/web/store/actions.ts | 53 ++++++-- app/web/store/constant.ts | 1 - app/web/store/reducer.ts | 4 +- app/web/utils/localIp.ts | 16 +++ docs/docsify/zh-cn/configuration/envConfig.md | 13 ++ env.json | 3 +- 9 files changed, 186 insertions(+), 54 deletions(-) delete mode 100644 app/web/store/constant.ts create mode 100644 app/web/utils/localIp.ts diff --git a/app/web/app.tsx b/app/web/app.tsx index 4701067..a22e0a1 100644 --- a/app/web/app.tsx +++ b/app/web/app.tsx @@ -14,10 +14,12 @@ import 'ant-design-dtinsight-theme/theme/dt-theme/index.less'; declare var window: any; const App = () => { - const { changeLocalIp } = bindActionCreators(actions, useDispatch()); + const { fetchLocalIp } = bindActionCreators(actions, useDispatch()); + useEffect(() => { - changeLocalIp(); + fetchLocalIp(); }, []) + return (
diff --git a/app/web/layouts/header/header.tsx b/app/web/layouts/header/header.tsx index 8f2b8a3..6242aff 100644 --- a/app/web/layouts/header/header.tsx +++ b/app/web/layouts/header/header.tsx @@ -1,19 +1,28 @@ import React, { useState, useEffect } from 'react'; -import { AppstoreOutlined, CloudOutlined, DesktopOutlined, TagOutlined, SettingOutlined, QuestionCircleOutlined } from '@ant-design/icons'; -import { Layout, Menu } from 'antd'; +import { AppstoreOutlined, CloudOutlined, DesktopOutlined, TagOutlined, SettingOutlined, QuestionCircleOutlined, EditOutlined } from '@ant-design/icons'; +import { Form, Layout, Menu, Modal, FormInstance, Input, Tooltip, Popconfirm } from 'antd'; import { SyncOutlined } from '@ant-design/icons'; import { Link } from 'react-router-dom'; import { useSelector, useDispatch } from 'react-redux'; import { bindActionCreators } from 'redux'; import * as actions from '@/store/actions'; +import { API } from '@/api'; import logo from '@/asset/images/logo.png'; import config from '../../../../env.json'; import './style.scss'; const { SubMenu } = Menu; - const { Header } = Layout; +const formItemLayout: any = { + labelCol: { + span: 5 + }, + wrapperCol: { + span: 18 + } +}; + const navMenuList: any = [{ name: '应用中心', path: '/page/toolbox', @@ -40,19 +49,58 @@ const navMenuList: any = [{ icon: , routers: ['tags'] }] + const HeaderComponent = (props: any) => { - const { location } = props; + const { location, proxyServer } = props; const { localIp = '127.0.0.1' } = useSelector((state: any) => state.global); const { pathname } = location; const [selectedKeys, setSelectedKeys] = useState([pathname]); - const { changeLocalIp } = bindActionCreators(actions, useDispatch()); - const handleSelectedKeys = (e: any) => { - setSelectedKeys(e.key); - } + const [visible, setVisible] = useState(false); + const [popconfirmOpen, setPopconfirmOpen] = useState(false); + const { setLocalIp } = bindActionCreators(actions, useDispatch()); + let formRef: FormInstance = null; + useEffect(() => { let current = navMenuList.filter(item => item.routers.some((ele) => pathname.indexOf(ele) > -1)) current.length && setSelectedKeys([current[0].path]) }, [pathname]) + // 检测是否通过 VPN 访问哆啦A梦 + useEffect(() => { + checkIsVPN(); + }, [localIp]); + + const handleSelectedKeys = (e: any) => { + setSelectedKeys(e.key); + } + + // 刷新获取真实IP + const handleGetRealIp = () => { + API.getLocalIp().then((response: any) => { + const { success, data } = response; + if (success) { + formRef.setFieldsValue({ localIp: data.localIp }); + // 记录真实IP + localStorage.setItem('real-localIp', data.localIp); + } + }) + } + + const handleModalOk = () => { + formRef.validateFields().then((values: any) => { + setLocalIp(values.localIp); + setVisible(false); + }); + } + + // 检测当前本地IP是否为 VPN 服务器的IP,是则代表通过 VPN 使用哆啦A梦代理,提示右上角可以进行设置自定义本地IP + const checkIsVPN = () => { + const vpnIp = config.vpnIp || []; + const tipTime = Number(localStorage.getItem('vpnIp-tip-time') || ''); + console.log(111, Date.now() - tipTime - 24 * 60 * 60) + if ((Date.now() - tipTime - 24 * 60 * 60) > 0) { + setPopconfirmOpen(vpnIp.includes(localIp)) + } + } return (
@@ -85,10 +133,60 @@ const HeaderComponent = (props: any) => { {`本机IP: ${localIp}`} - {/* 主动更新本地IP */} - changeLocalIp(true)} /> + {/* 自定义本地IP */} + { + setVisible(true); + setPopconfirmOpen(false); + // 关闭提示后记录时间 + localStorage.setItem('vpnIp-tip-time', `${Date.now()}`); + }} + onCancel={() => { + setPopconfirmOpen(false); + // 关闭提示后记录时间 + localStorage.setItem('vpnIp-tip-time', `${Date.now()}`); + }} + > + { + !popconfirmOpen && setVisible(true); + }} /> +
+ + { setVisible(false) }} + > +
formRef = form} + initialValues={{ + localIp: proxyServer?.ip || localIp + }} + scrollToFirstError={true} + > + + + + + } /> + +
+
); } diff --git a/app/web/pages/proxyServer/index.tsx b/app/web/pages/proxyServer/index.tsx index 666a575..ae6d462 100644 --- a/app/web/pages/proxyServer/index.tsx +++ b/app/web/pages/proxyServer/index.tsx @@ -4,7 +4,6 @@ import { Input, Button, Typography, Tag, Table, message as Message, Divider, Mod import { API } from '@/api'; import ProxyServerModal from './components/proxyServerModal'; import ProxyRuleModal from './components/proxyRuleModal'; -import Cookies from 'js-cookie'; import { connect } from 'react-redux' import helpIcon from '@/asset/images/help-icon.png'; import config from '../../../../env.json'; @@ -59,8 +58,8 @@ class ProxyServer extends React.PureComponent { loadMainData = () => { this.getProxyServerList() this.getCollectTagList() - this.getLocalIp() } + getCollectTagList = () => { let collectTagList = [] try { @@ -71,29 +70,6 @@ class ProxyServer extends React.PureComponent { } this.setState({ collectTagList }) } - getLocalIp = () => { - API.getLocalIp().then((response: any) => { - const { success, data, message } = response; - if (success) { - const localIp = data.localIp; - const rememberIp = Cookies.get('rememberIp') || '' - if (rememberIp && rememberIp !== localIp) { - notification.warning({ - message: 'IP地址变更', - description: '您的IP地址【较上次登录时】已发生变更、请留意代理服务配置!', - duration: 30, - onClose: () => { - Cookies.set('rememberIp', localIp) - } - }); - } - - this.setState({ - localIp - }) - } - }) - } getProxyServerList = (checked?: boolean) => { const { mainTableParams, collectTagList } = this.state; this.setState({ diff --git a/app/web/store/actions.ts b/app/web/store/actions.ts index efcb1c3..89c07ab 100644 --- a/app/web/store/actions.ts +++ b/app/web/store/actions.ts @@ -1,18 +1,45 @@ -import { message } from 'antd'; -import { CHANGE_LOCAL_IP } from './constant'; +import { handleLocalIpChanged } from '@/utils/localIp'; +import config from '../../../env.json' -export const changeLocalIp = (showMsg = false) => (dispatch: any, getState: any, { API }: any) => { - API.getLocalIp().then((response: any) => { - const { success, data } = response; - if (success) { - console.log(data); - showMsg && message.success('刷新成功!') +// 从接口获取本机IP +export const fetchLocalIp = () => (dispatch: any, getState: any, { API }: any) => { + // 本地没有 localIp 再从接口获取 + const localIp = localStorage.getItem('localIp'); + if (localIp) { dispatch({ - type: CHANGE_LOCAL_IP, - payload: data + type: 'CHANGE_LOCAL_IP', + payload: { + host: `${localIp}:7001`, + localIp, + protocol: 'http' + } }) + handleLocalIpChanged(localIp); + } else { + API.getLocalIp().then((response: any) => { + const { success, data } = response; + if (success) { + dispatch({ + type: 'CHANGE_LOCAL_IP', + payload: data + }) + handleLocalIpChanged(data.localIp); + // 记录真实IP + localStorage.setItem('real-localIp', localIp); + } + }); } - }).catch(() => { - showMsg && message.warning('刷新失败!') - }); +} + +// 自定义本机IP +export const setLocalIp = (localIp) => (dispatch: any) => { + dispatch({ + type: 'CHANGE_LOCAL_IP', + payload: { + host: `${localIp}:7001`, + localIp, + protocol: 'http' + } + }) + handleLocalIpChanged(localIp); } diff --git a/app/web/store/constant.ts b/app/web/store/constant.ts deleted file mode 100644 index b0afc10..0000000 --- a/app/web/store/constant.ts +++ /dev/null @@ -1 +0,0 @@ -export const CHANGE_LOCAL_IP = 'CHANGE_LOCAL_IP'; diff --git a/app/web/store/reducer.ts b/app/web/store/reducer.ts index 0fe52fb..a7a47aa 100644 --- a/app/web/store/reducer.ts +++ b/app/web/store/reducer.ts @@ -1,4 +1,3 @@ -import { CHANGE_LOCAL_IP } from './constant'; const initialState: any = { localIp: '', serverInfo: { @@ -9,8 +8,9 @@ const initialState: any = { export default (state = initialState, action: any) => { const { type, payload } = action; switch (type) { - case CHANGE_LOCAL_IP: + case 'CHANGE_LOCAL_IP': const { localIp, protocol, host } = payload; + localStorage.setItem('localIp', localIp); return { ...state, localIp, diff --git a/app/web/utils/localIp.ts b/app/web/utils/localIp.ts new file mode 100644 index 0000000..911404d --- /dev/null +++ b/app/web/utils/localIp.ts @@ -0,0 +1,16 @@ +import { notification } from 'antd'; + +// 本机IP发生变化进行提示 +export const handleLocalIpChanged = (localIp) => { + const rememberIp = localStorage.getItem('rememberIp'); + if (rememberIp !== null && rememberIp !== localIp) { + notification.warning({ + message: 'IP地址变更', + description: '您的IP地址【较上次访问时】已发生变更,请留意代理服务配置!', + duration: 5, + onClose: () => { + localStorage.setItem('rememberIp', localIp) + } + }); + } +} diff --git a/docs/docsify/zh-cn/configuration/envConfig.md b/docs/docsify/zh-cn/configuration/envConfig.md index 08e6dd3..6c2a28e 100644 --- a/docs/docsify/zh-cn/configuration/envConfig.md +++ b/docs/docsify/zh-cn/configuration/envConfig.md @@ -109,3 +109,16 @@ dingBot 的通知模板的跳转路径,默认跳转到帮助文档,可自行 } } ``` + +## vpnIp + +- 类型:string[] +- 默认值:[] + +使用公司内部 VPN 时,本地地址会变成 VPN 的机器地址 + +```json +{ + "vpnIp": ["127.0.0.1"] +} +``` diff --git a/env.json b/env.json index 2370b40..31313be 100644 --- a/env.json +++ b/env.json @@ -7,5 +7,6 @@ "proxyHelpDocUrl": "https://dtstack.github.io/doraemon/docsify/#/zh-cn/guide/%E4%BB%A3%E7%90%86%E6%9C%8D%E5%8A%A1", "mysql": { "prod": {} - } + }, + "vpnIp": [] }