feat: support edit profile item

This commit is contained in:
GyDi 2022-01-17 02:16:17 +08:00
parent 08587d8f2f
commit 99a8e25411
No known key found for this signature in database
GPG Key ID: 1C95E0D3467B3084
6 changed files with 61 additions and 5 deletions

12
src-tauri/Cargo.lock generated
View File

@ -58,6 +58,7 @@ dependencies = [
"tauri-plugin-vibrancy", "tauri-plugin-vibrancy",
"tokio", "tokio",
"warp", "warp",
"which",
"winreg 0.10.1", "winreg 0.10.1",
] ]
@ -4110,6 +4111,17 @@ dependencies = [
"cc", "cc",
] ]
[[package]]
name = "which"
version = "4.2.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ea187a8ef279bc014ec368c27a920da2024d2a711109bfbe3440585d5cf27ad9"
dependencies = [
"either",
"lazy_static",
"libc",
]
[[package]] [[package]]
name = "wildmatch" name = "wildmatch"
version = "2.1.0" version = "2.1.0"

View File

@ -29,6 +29,7 @@ tokio = { version = "1", features = ["full"] }
log = "0.4.14" log = "0.4.14"
log4rs = "1.0.0" log4rs = "1.0.0"
warp = "0.3" warp = "0.3"
which = "4.2.2"
auto-launch = "0.2" auto-launch = "0.2"
port_scanner = "0.1.5" port_scanner = "0.1.5"

View File

@ -3,11 +3,13 @@ use crate::{
states::{ClashState, ProfilesState, VergeState}, states::{ClashState, ProfilesState, VergeState},
utils::{ utils::{
config::{read_clash, save_clash}, config::{read_clash, save_clash},
dirs::app_home_dir,
fetch::fetch_profile, fetch::fetch_profile,
sysopt::SysProxyConfig, sysopt::SysProxyConfig,
}, },
}; };
use serde_yaml::Mapping; use serde_yaml::Mapping;
use std::process::Command;
use tauri::State; use tauri::State;
/// get all profiles from `profiles.yaml` /// get all profiles from `profiles.yaml`
@ -142,6 +144,34 @@ pub fn patch_profile(
} }
} }
/// run vscode command to edit the profile
#[tauri::command]
pub fn edit_profile(index: usize, profiles_state: State<'_, ProfilesState>) -> Result<(), String> {
let mut profiles = profiles_state.0.lock().unwrap();
let items = profiles.items.take().unwrap_or(vec![]);
if index >= items.len() {
profiles.items = Some(items);
return Err("the index out of bound".into());
}
let file = items[index].file.clone().unwrap_or("".into());
profiles.items = Some(items);
let path = app_home_dir().join("profiles").join(file);
if !path.exists() {
return Err("failed to open the file".into());
}
match which::which("code") {
Ok(code) => match Command::new(code).arg(path).status() {
Ok(_) => Ok(()),
Err(_) => Err("failed to open file by VScode".into()),
},
Err(_) => Err("please install VScode for edit".into()),
}
}
/// restart the sidecar /// restart the sidecar
#[tauri::command] #[tauri::command]
pub fn restart_sidecar( pub fn restart_sidecar(

View File

@ -3,8 +3,6 @@
windows_subsystem = "windows" windows_subsystem = "windows"
)] )]
extern crate tauri;
mod cmds; mod cmds;
mod core; mod core;
mod states; mod states;
@ -82,13 +80,14 @@ fn main() -> std::io::Result<()> {
cmds::get_verge_config, cmds::get_verge_config,
cmds::patch_verge_config, cmds::patch_verge_config,
// profile // profile
cmds::edit_profile,
cmds::patch_profile,
cmds::import_profile, cmds::import_profile,
cmds::update_profile, cmds::update_profile,
cmds::delete_profile, cmds::delete_profile,
cmds::select_profile, cmds::select_profile,
cmds::patch_profile,
cmds::sync_profiles,
cmds::get_profiles, cmds::get_profiles,
cmds::sync_profiles,
]) ])
.build(tauri::generate_context!()) .build(tauri::generate_context!())
.expect("error while running tauri application") .expect("error while running tauri application")

View File

@ -14,7 +14,7 @@ import {
import { useSWRConfig } from "swr"; import { useSWRConfig } from "swr";
import { RefreshRounded } from "@mui/icons-material"; import { RefreshRounded } from "@mui/icons-material";
import { CmdType } from "../services/types"; import { CmdType } from "../services/types";
import { updateProfile, deleteProfile } from "../services/cmds"; import { updateProfile, deleteProfile, editProfile } from "../services/cmds";
import Notice from "./notice"; import Notice from "./notice";
import parseTraffic from "../utils/parse-traffic"; import parseTraffic from "../utils/parse-traffic";
import relativeTime from "dayjs/plugin/relativeTime"; import relativeTime from "dayjs/plugin/relativeTime";
@ -59,6 +59,15 @@ const ProfileItem: React.FC<Props> = (props) => {
const progress = Math.round(((download + upload) * 100) / (total + 0.1)); const progress = Math.round(((download + upload) * 100) / (total + 0.1));
const fromnow = updated > 0 ? dayjs(updated * 1000).fromNow() : ""; const fromnow = updated > 0 ? dayjs(updated * 1000).fromNow() : "";
const onEdit = async () => {
setAnchorEl(null);
try {
await editProfile(index);
} catch (err: any) {
Notice.error(err.toString());
}
};
const onUpdateWrapper = (withProxy: boolean) => async () => { const onUpdateWrapper = (withProxy: boolean) => async () => {
setAnchorEl(null); setAnchorEl(null);
if (loading) return; if (loading) return;
@ -202,6 +211,7 @@ const ProfileItem: React.FC<Props> = (props) => {
anchorPosition={position} anchorPosition={position}
anchorReference="anchorPosition" anchorReference="anchorPosition"
> >
<MenuItem onClick={onEdit}>Edit</MenuItem>
<MenuItem onClick={onUpdateWrapper(false)}>Update</MenuItem> <MenuItem onClick={onUpdateWrapper(false)}>Update</MenuItem>
<MenuItem onClick={onUpdateWrapper(true)}>Update(Proxy)</MenuItem> <MenuItem onClick={onUpdateWrapper(true)}>Update(Proxy)</MenuItem>
<MenuItem onClick={onDelete}>Delete</MenuItem> <MenuItem onClick={onDelete}>Delete</MenuItem>

View File

@ -9,6 +9,10 @@ export async function syncProfiles() {
return invoke<void>("sync_profiles"); return invoke<void>("sync_profiles");
} }
export async function editProfile(index: number) {
return invoke<void>("edit_profile", { index });
}
export async function importProfile(url: string) { export async function importProfile(url: string) {
return invoke<void>("import_profile", { url, withProxy: true }); return invoke<void>("import_profile", { url, withProxy: true });
} }