mirror of
https://gh.catmak.name/https://github.com/mihomo-party-org/mihomo-party
synced 2025-12-26 20:50:30 +08:00
Compare commits
3 Commits
848f6277cb
...
99a5505d16
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
99a5505d16 | ||
|
|
76a849e376 | ||
|
|
74b65430be |
@ -183,6 +183,11 @@ export const mihomoUpgrade = async (): Promise<void> => {
|
|||||||
return await instance.post('/upgrade')
|
return await instance.post('/upgrade')
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export const mihomoUpgradeUI = async (): Promise<void> => {
|
||||||
|
const instance = await getAxios()
|
||||||
|
return await instance.post('/upgrade/ui')
|
||||||
|
}
|
||||||
|
|
||||||
// Smart 内核 API
|
// Smart 内核 API
|
||||||
export const mihomoSmartGroupWeights = async (
|
export const mihomoSmartGroupWeights = async (
|
||||||
groupName: string
|
groupName: string
|
||||||
|
|||||||
@ -15,6 +15,7 @@ import {
|
|||||||
mihomoUpdateRuleProviders,
|
mihomoUpdateRuleProviders,
|
||||||
mihomoUpgrade,
|
mihomoUpgrade,
|
||||||
mihomoUpgradeGeo,
|
mihomoUpgradeGeo,
|
||||||
|
mihomoUpgradeUI,
|
||||||
mihomoVersion,
|
mihomoVersion,
|
||||||
patchMihomoConfig,
|
patchMihomoConfig,
|
||||||
mihomoSmartGroupWeights,
|
mihomoSmartGroupWeights,
|
||||||
@ -167,6 +168,7 @@ export function registerIpcMainHandlers(): void {
|
|||||||
ipcMain.handle('mihomoUnfixedProxy', (_e, group) => ipcErrorWrapper(mihomoUnfixedProxy)(group))
|
ipcMain.handle('mihomoUnfixedProxy', (_e, group) => ipcErrorWrapper(mihomoUnfixedProxy)(group))
|
||||||
ipcMain.handle('mihomoUpgradeGeo', ipcErrorWrapper(mihomoUpgradeGeo))
|
ipcMain.handle('mihomoUpgradeGeo', ipcErrorWrapper(mihomoUpgradeGeo))
|
||||||
ipcMain.handle('mihomoUpgrade', ipcErrorWrapper(mihomoUpgrade))
|
ipcMain.handle('mihomoUpgrade', ipcErrorWrapper(mihomoUpgrade))
|
||||||
|
ipcMain.handle('mihomoUpgradeUI', ipcErrorWrapper(mihomoUpgradeUI))
|
||||||
ipcMain.handle('mihomoProxyDelay', (_e, proxy, url) =>
|
ipcMain.handle('mihomoProxyDelay', (_e, proxy, url) =>
|
||||||
ipcErrorWrapper(mihomoProxyDelay)(proxy, url)
|
ipcErrorWrapper(mihomoProxyDelay)(proxy, url)
|
||||||
)
|
)
|
||||||
|
|||||||
@ -138,3 +138,9 @@
|
|||||||
background: #c0c1c58f;
|
background: #c0c1c58f;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.sider-card-title {
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
@ -218,7 +218,7 @@ const ConnCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold sider-card-title ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.connections')}
|
{t('sider.cards.connections')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -102,7 +102,7 @@ const DNSCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold sider-card-title ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.dns')}
|
{t('sider.cards.dns')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -84,7 +84,7 @@ const LogCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold text-ellipsis whitespace-nowrap overflow-hidden ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.logs')}
|
{t('sider.cards.logs')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -158,7 +158,7 @@ const MihomoCoreCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold text-ellipsis whitespace-nowrap overflow-hidden ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.core')}
|
{t('sider.cards.core')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -83,7 +83,7 @@ const OverrideCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold text-ellipsis whitespace-nowrap overflow-hidden ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.override')}
|
{t('sider.cards.override')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -238,7 +238,7 @@ const ProfileCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold sider-card-title ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.profiles')}
|
{t('sider.cards.profiles')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -103,7 +103,7 @@ const ProxyCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold sider-card-title ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('proxies.card.title')}
|
{t('proxies.card.title')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -84,7 +84,7 @@ const ResourceCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold text-ellipsis whitespace-nowrap overflow-hidden ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.resources')}
|
{t('sider.cards.resources')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -104,7 +104,7 @@ const RuleCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold text-ellipsis whitespace-nowrap overflow-hidden ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.rules')}
|
{t('sider.cards.rules')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -102,7 +102,7 @@ const SniffCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold text-ellipsis whitespace-nowrap overflow-hidden ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.sniff')}
|
{t('sider.cards.sniff')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -84,7 +84,7 @@ const SubStoreCard: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold text-ellipsis whitespace-nowrap overflow-hidden ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.substore')}
|
{t('sider.cards.substore')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -116,7 +116,7 @@ const SysproxySwitcher: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold sider-card-title ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.systemProxy')}
|
{t('sider.cards.systemProxy')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -150,7 +150,7 @@ const TunSwitcher: React.FC<Props> = (props) => {
|
|||||||
</CardBody>
|
</CardBody>
|
||||||
<CardFooter className="pt-1">
|
<CardFooter className="pt-1">
|
||||||
<h3
|
<h3
|
||||||
className={`text-md font-bold ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
className={`text-md font-bold sider-card-title ${match ? 'text-primary-foreground' : 'text-foreground'}`}
|
||||||
>
|
>
|
||||||
{t('sider.cards.tun')}
|
{t('sider.cards.tun')}
|
||||||
</h3>
|
</h3>
|
||||||
|
|||||||
@ -400,6 +400,12 @@
|
|||||||
"profiles.remote": "Remote",
|
"profiles.remote": "Remote",
|
||||||
"profiles.local": "Local",
|
"profiles.local": "Local",
|
||||||
"profiles.trafficUsage": "Traffic Usage Progress",
|
"profiles.trafficUsage": "Traffic Usage Progress",
|
||||||
|
"profiles.openWebUI.title": "WebUI Management Panel",
|
||||||
|
"profiles.openWebUI.description": "Select a WebUI panel to open",
|
||||||
|
"profiles.openWebUI.local": "Local WebUI",
|
||||||
|
"profiles.updateWebUI.button": "Update Panel",
|
||||||
|
"profiles.updateWebUI.success": "WebUI panel updated successfully",
|
||||||
|
"profiles.updateWebUI.failed": "WebUI panel update failed: {{error}}",
|
||||||
"profiles.editInfo.title": "Edit Information",
|
"profiles.editInfo.title": "Edit Information",
|
||||||
"profiles.editInfo.name": "Name",
|
"profiles.editInfo.name": "Name",
|
||||||
"profiles.editInfo.url": "Subscription URL",
|
"profiles.editInfo.url": "Subscription URL",
|
||||||
|
|||||||
@ -25,9 +25,9 @@
|
|||||||
"common.notification.systemProxyDisabled": "Системный прокси отключен",
|
"common.notification.systemProxyDisabled": "Системный прокси отключен",
|
||||||
"common.notification.tunEnabled": "TUN включен",
|
"common.notification.tunEnabled": "TUN включен",
|
||||||
"common.notification.tunDisabled": "TUN отключен",
|
"common.notification.tunDisabled": "TUN отключен",
|
||||||
"common.notification.ruleMode": "Режим правил",
|
"common.notification.ruleMode": "Правило",
|
||||||
"common.notification.globalMode": "Глобальный режим",
|
"common.notification.globalMode": "Глобальный",
|
||||||
"common.notification.directMode": "Прямой режим",
|
"common.notification.directMode": "Прямой",
|
||||||
"common.error.appCrash": "Приложение завершилось аварийно :( Пожалуйста, отправьте следующую информацию разработчику для устранения проблемы",
|
"common.error.appCrash": "Приложение завершилось аварийно :( Пожалуйста, отправьте следующую информацию разработчику для устранения проблемы",
|
||||||
"common.error.copyErrorMessage": "Копировать сообщение об ошибке",
|
"common.error.copyErrorMessage": "Копировать сообщение об ошибке",
|
||||||
"common.error.invalidCron": "Неверное выражение Cron",
|
"common.error.invalidCron": "Неверное выражение Cron",
|
||||||
@ -249,7 +249,7 @@
|
|||||||
"sider.cards.trafficUsage": "Использование трафика",
|
"sider.cards.trafficUsage": "Использование трафика",
|
||||||
"sider.cards.neverExpire": "Бессрочно",
|
"sider.cards.neverExpire": "Бессрочно",
|
||||||
"sider.cards.outbound.title": "Режим исходящего трафика",
|
"sider.cards.outbound.title": "Режим исходящего трафика",
|
||||||
"sider.cards.outbound.rule": "По правилам",
|
"sider.cards.outbound.rule": "Правило",
|
||||||
"sider.cards.outbound.global": "Глобальный",
|
"sider.cards.outbound.global": "Глобальный",
|
||||||
"sider.cards.outbound.direct": "Прямой",
|
"sider.cards.outbound.direct": "Прямой",
|
||||||
"sider.size.large": "Большой",
|
"sider.size.large": "Большой",
|
||||||
@ -508,9 +508,9 @@
|
|||||||
"tray.showWindow": "Показать окно",
|
"tray.showWindow": "Показать окно",
|
||||||
"tray.showFloatingWindow": "Показать плавающее окно",
|
"tray.showFloatingWindow": "Показать плавающее окно",
|
||||||
"tray.hideFloatingWindow": "Скрыть плавающее окно",
|
"tray.hideFloatingWindow": "Скрыть плавающее окно",
|
||||||
"tray.ruleMode": "Режим правил",
|
"tray.ruleMode": "Правило",
|
||||||
"tray.globalMode": "Глобальный режим",
|
"tray.globalMode": "Глобальный",
|
||||||
"tray.directMode": "Прямой режим",
|
"tray.directMode": "Прямой",
|
||||||
"tray.systemProxy": "Системный прокси",
|
"tray.systemProxy": "Системный прокси",
|
||||||
"tray.tun": "TUN",
|
"tray.tun": "TUN",
|
||||||
"tray.profiles": "Профили",
|
"tray.profiles": "Профили",
|
||||||
|
|||||||
@ -405,6 +405,12 @@
|
|||||||
"profiles.traffic.expired": "已过期",
|
"profiles.traffic.expired": "已过期",
|
||||||
"profiles.traffic.remainingDays": "剩余 {{days}} 天",
|
"profiles.traffic.remainingDays": "剩余 {{days}} 天",
|
||||||
"profiles.traffic.lastUpdate": "最后更新:{{time}}",
|
"profiles.traffic.lastUpdate": "最后更新:{{time}}",
|
||||||
|
"profiles.openWebUI.title": "WebUI 管理面板",
|
||||||
|
"profiles.openWebUI.description": "选择一个 WebUI 面板打开",
|
||||||
|
"profiles.openWebUI.local": "本地 WebUI",
|
||||||
|
"profiles.updateWebUI.button": "更新面板",
|
||||||
|
"profiles.updateWebUI.success": "WebUI 面板更新成功",
|
||||||
|
"profiles.updateWebUI.failed": "WebUI 面板更新失败: {{error}}",
|
||||||
"profiles.editInfo.title": "编辑信息",
|
"profiles.editInfo.title": "编辑信息",
|
||||||
"profiles.editInfo.name": "名称",
|
"profiles.editInfo.name": "名称",
|
||||||
"profiles.editInfo.url": "订阅地址",
|
"profiles.editInfo.url": "订阅地址",
|
||||||
|
|||||||
@ -7,12 +7,16 @@ import {
|
|||||||
DropdownItem,
|
DropdownItem,
|
||||||
DropdownMenu,
|
DropdownMenu,
|
||||||
DropdownTrigger,
|
DropdownTrigger,
|
||||||
Input
|
Input,
|
||||||
|
Card,
|
||||||
|
CardBody,
|
||||||
|
CardHeader
|
||||||
} from '@heroui/react'
|
} from '@heroui/react'
|
||||||
import BasePage from '@renderer/components/base/base-page'
|
import BasePage from '@renderer/components/base/base-page'
|
||||||
import ProfileItem from '@renderer/components/profiles/profile-item'
|
import ProfileItem from '@renderer/components/profiles/profile-item'
|
||||||
import { useProfileConfig } from '@renderer/hooks/use-profile-config'
|
import { useProfileConfig } from '@renderer/hooks/use-profile-config'
|
||||||
import { useAppConfig } from '@renderer/hooks/use-app-config'
|
import { useAppConfig } from '@renderer/hooks/use-app-config'
|
||||||
|
import { useControledMihomoConfig } from '@renderer/hooks/use-controled-mihomo-config'
|
||||||
import { getFilePath, readTextFile, subStoreCollections, subStoreSubs } from '@renderer/utils/ipc'
|
import { getFilePath, readTextFile, subStoreCollections, subStoreSubs } from '@renderer/utils/ipc'
|
||||||
import type { KeyboardEvent } from 'react'
|
import type { KeyboardEvent } from 'react'
|
||||||
import { ReactNode, useCallback, useEffect, useMemo, useRef, useState } from 'react'
|
import { ReactNode, useCallback, useEffect, useMemo, useRef, useState } from 'react'
|
||||||
@ -32,6 +36,7 @@ import SubStoreIcon from '@renderer/components/base/substore-icon'
|
|||||||
import useSWR from 'swr'
|
import useSWR from 'swr'
|
||||||
import { useNavigate } from 'react-router-dom'
|
import { useNavigate } from 'react-router-dom'
|
||||||
import { useTranslation } from 'react-i18next'
|
import { useTranslation } from 'react-i18next'
|
||||||
|
import { mihomoUpgradeUI } from '@renderer/utils/ipc'
|
||||||
|
|
||||||
const Profiles: React.FC = () => {
|
const Profiles: React.FC = () => {
|
||||||
const { t } = useTranslation()
|
const { t } = useTranslation()
|
||||||
@ -45,6 +50,9 @@ const Profiles: React.FC = () => {
|
|||||||
mutateProfileConfig
|
mutateProfileConfig
|
||||||
} = useProfileConfig()
|
} = useProfileConfig()
|
||||||
const { appConfig } = useAppConfig()
|
const { appConfig } = useAppConfig()
|
||||||
|
const { controledMihomoConfig } = useControledMihomoConfig()
|
||||||
|
const externalController = controledMihomoConfig?.['external-controller'] || ''
|
||||||
|
const externalUI = (controledMihomoConfig as any)?.['external-ui']
|
||||||
const { useSubStore = true, useCustomSubStore = false, customSubStoreUrl = '' } = appConfig || {}
|
const { useSubStore = true, useCustomSubStore = false, customSubStoreUrl = '' } = appConfig || {}
|
||||||
const { current, items = [] } = profileConfig || {}
|
const { current, items = [] } = profileConfig || {}
|
||||||
const navigate = useNavigate()
|
const navigate = useNavigate()
|
||||||
@ -195,6 +203,26 @@ const Profiles: React.FC = () => {
|
|||||||
setSortedItems(items)
|
setSortedItems(items)
|
||||||
}, [items])
|
}, [items])
|
||||||
|
|
||||||
|
// 获取本地WebUI的URL
|
||||||
|
const getLocalWebUIUrl = (): string => {
|
||||||
|
if (externalController) {
|
||||||
|
// 将地址转换为WebUI URL
|
||||||
|
// 例如: 127.0.0.1:9090 -> http://127.0.0.1:9090/ui
|
||||||
|
const controller = externalController.replace('0.0.0.0', '127.0.0.1')
|
||||||
|
// 如果配置了external-ui,使用/ui路径,否则可能需要使用不同的路径
|
||||||
|
const uiPath = externalUI ? '/ui' : '/ui' // 默认使用/ui路径
|
||||||
|
return `http://${controller}${uiPath}`
|
||||||
|
}
|
||||||
|
// 默认URL
|
||||||
|
return 'http://127.0.0.1:9090/ui'
|
||||||
|
}
|
||||||
|
|
||||||
|
// 检查本地WebUI是否可用
|
||||||
|
const isLocalWebUIAvailable = (): boolean => {
|
||||||
|
// 如果有配置的external-controller,则认为本地WebUI可用
|
||||||
|
return !!externalController
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<BasePage
|
<BasePage
|
||||||
ref={pageRef}
|
ref={pageRef}
|
||||||
@ -378,6 +406,53 @@ const Profiles: React.FC = () => {
|
|||||||
</div>
|
</div>
|
||||||
<Divider />
|
<Divider />
|
||||||
</div>
|
</div>
|
||||||
|
{/* WebUI Card with Multiple Options */}
|
||||||
|
<div className="m-2">
|
||||||
|
<Card>
|
||||||
|
<CardHeader className="flex gap-3">
|
||||||
|
<div className="flex flex-col">
|
||||||
|
<p className="text-md">{t('profiles.openWebUI.title')}</p>
|
||||||
|
<p className="text-small text-default-500">{t('profiles.openWebUI.description')}</p>
|
||||||
|
</div>
|
||||||
|
</CardHeader>
|
||||||
|
<CardBody>
|
||||||
|
<div className="flex gap-2 flex-wrap">
|
||||||
|
<Button
|
||||||
|
onPress={() => window.open('https://metacubexd.pages.dev/', '_blank')}
|
||||||
|
>
|
||||||
|
MetaCubeXD
|
||||||
|
</Button>
|
||||||
|
<Button
|
||||||
|
onPress={() => window.open('https://zashboard.pages.dev/', '_blank')}
|
||||||
|
>
|
||||||
|
Zashboard
|
||||||
|
</Button>
|
||||||
|
{isLocalWebUIAvailable() && (
|
||||||
|
<>
|
||||||
|
<Button
|
||||||
|
onPress={() => window.open(getLocalWebUIUrl(), '_blank')}
|
||||||
|
>
|
||||||
|
{t('profiles.openWebUI.local')}
|
||||||
|
</Button>
|
||||||
|
<Button
|
||||||
|
color="success"
|
||||||
|
onPress={async () => {
|
||||||
|
try {
|
||||||
|
await mihomoUpgradeUI()
|
||||||
|
new Notification(t('profiles.updateWebUI.success'))
|
||||||
|
} catch (e) {
|
||||||
|
new Notification(t('profiles.updateWebUI.failed', { error: String(e) }))
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{t('profiles.updateWebUI.button')}
|
||||||
|
</Button>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</CardBody>
|
||||||
|
</Card>
|
||||||
|
</div>
|
||||||
<DndContext sensors={sensors} collisionDetection={closestCenter} onDragEnd={onDragEnd}>
|
<DndContext sensors={sensors} collisionDetection={closestCenter} onDragEnd={onDragEnd}>
|
||||||
<div
|
<div
|
||||||
className={`${fileOver ? 'blur-sm' : ''} grid sm:grid-cols-2 md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4 gap-2 m-2`}
|
className={`${fileOver ? 'blur-sm' : ''} grid sm:grid-cols-2 md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4 gap-2 m-2`}
|
||||||
|
|||||||
@ -84,6 +84,10 @@ export async function mihomoUpgrade(): Promise<void> {
|
|||||||
return ipcErrorWrapper(await window.electron.ipcRenderer.invoke('mihomoUpgrade'))
|
return ipcErrorWrapper(await window.electron.ipcRenderer.invoke('mihomoUpgrade'))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export async function mihomoUpgradeUI(): Promise<void> {
|
||||||
|
return ipcErrorWrapper(await window.electron.ipcRenderer.invoke('mihomoUpgradeUI'))
|
||||||
|
}
|
||||||
|
|
||||||
export async function mihomoProxyDelay(proxy: string, url?: string): Promise<IMihomoDelay> {
|
export async function mihomoProxyDelay(proxy: string, url?: string): Promise<IMihomoDelay> {
|
||||||
return ipcErrorWrapper(await window.electron.ipcRenderer.invoke('mihomoProxyDelay', proxy, url))
|
return ipcErrorWrapper(await window.electron.ipcRenderer.invoke('mihomoProxyDelay', proxy, url))
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user