Browse Source

add:实现frpc增删改查

master
秋田弘 5 months ago
parent
commit
3137669dfb
  1. 105
      frontend/src/components/setting/NetProxy.vue
  2. 130
      frontend/src/stores/proxy.ts
  3. 14
      godo/proxy/frpc.go

105
frontend/src/components/setting/NetProxy.vue

@ -2,9 +2,18 @@
import { useProxyStore } from "@/stores/proxy";
import { notifyError, notifySuccess } from "@/util/msg";
import { Plus } from "@element-plus/icons-vue";
import { ref } from "vue";
import { onMounted, ref } from "vue";
import { useRoute } from "vue-router";
const route = useRoute();
const proxyStore = useProxyStore();
const {
proxies,
fetchProxies,
fetchProxyByName,
deleteProxyByName,
updateProxyByName,
} = proxyStore;
const proxyDialogShow = ref(false);
const isEditing = ref(false);
@ -24,20 +33,11 @@
const addProxy = () => {
if (pwdRef.value.validate()) {
// const isNameDuplicate = proxyStore.proxies.some(
// (p) => p.name === proxyStore.proxyData.name
// );
// if (isNameDuplicate) {
// notifyError("");
// return;
// }
// proxyStore.addProxy({ ...proxyStore.proxyData });
// proxyDialogShow.value = false;
// proxyStore.resetProxyData();
// store createFrpcConfig
proxyStore
.createFrpcConfig()
.then(() => {
proxyDialogShow.value = false;
proxyStore.addProxy({ ...proxyStore.proxyData });
proxyDialogShow.value = false;
proxyStore.resetProxyData();
notifySuccess("代理配置已成功创建");
@ -48,24 +48,16 @@
}
};
const updateProxy = () => {
const updateProxy = async () => {
if (pwdRef.value.validate()) {
const index = proxyStore.proxies.findIndex(
(p) => p.id === proxyStore.proxyData.id
);
if (index !== -1) {
const isNameDuplicate = proxyStore.proxies.some(
(p, i) =>
p.name === proxyStore.proxyData.name && i !== index
);
if (isNameDuplicate) {
notifyError("代理名称已存在");
return;
}
proxyStore.updateProxy({ ...proxyStore.proxyData });
try {
await updateProxyByName(proxyStore.proxyData);
notifySuccess("编辑成功");
proxyDialogShow.value = false;
proxyStore.resetProxyData();
isEditing.value = false;
} catch (error) {
notifyError(`编辑失败: ${error.message}`);
}
}
};
@ -120,6 +112,34 @@
}
});
};
const loadProxies = async () => {
await fetchProxies();
};
const editProxyBefore = async (proxy: any) => {
await fetchProxyByName(proxy.name);
proxyDialogShow.value = true;
isEditing.value = true;
};
const deleteProxy = async (name: string) => {
try {
await deleteProxyByName(name);
notifySuccess("删除成功");
} catch (error) {
console.error("Error deleting proxy:", error);
notifyError(`删除失败: ${error.message}`);
}
};
onMounted(() => {
loadProxies();
const name = route.query.name as string;
if (name) {
fetchProxyByName(name);
}
});
</script>
<template>
@ -154,21 +174,29 @@
<el-table-column
prop="domain"
label="代理域名"
width="180"
/>
<el-table-column label="操作">
<template #default="scope">
<el-button
size="small"
@click="editProxy(scope.row)"
>编辑</el-button
>
<el-button
size="small"
type="danger"
@click="deleteProxy(scope.row.id)"
>删除</el-button
<el-row
:gutter="24"
justify="start"
>
<el-col :span="10">
<el-button
size="small"
@click="editProxyBefore(scope.row)"
>编辑</el-button
>
</el-col>
<el-col :span="10">
<el-button
size="small"
type="danger"
@click="deleteProxy(scope.row.name)"
>删除</el-button
>
</el-col>
</el-row>
</template>
</el-table-column>
</el-table>
@ -525,8 +553,9 @@
type="primary"
@click="saveProxy"
style="width: 100px"
>保存</el-button
>
{{ isEditing ? '编辑' : '保存' }}
</el-button>
<el-button
type="primary"
style="width: 100px"

130
frontend/src/stores/proxy.ts

@ -28,7 +28,7 @@ export interface ProxyItem {
export const useProxyStore = defineStore('proxyStore', () => {
const localKey = "godoos_net_proxy";
const proxies = ref<ProxyItem[]>(getProxies());
const proxies = ref<ProxyItem[]>([]);
const customDomains = ref<string[]>([""]);
const proxyData = ref<ProxyItem>(createNewProxyData());
@ -58,10 +58,6 @@ export const useProxyStore = defineStore('proxyStore', () => {
};
}
function getProxies(): ProxyItem[] {
const proxies = localStorage.getItem(localKey);
return proxies ? JSON.parse(proxies) : [];
}
function saveProxies(proxies: ProxyItem[]) {
localStorage.setItem(localKey, JSON.stringify(proxies));
@ -160,10 +156,126 @@ export const useProxyStore = defineStore('proxyStore', () => {
const data = await response.json();
console.log("Response data:", data);
// 可以在这里添加成功通知
} catch (error) {
console.error("Error:", error);
// 可以在这里添加错误通知
}
};
const fetchProxies = async () => {
const url = "http://localhost:56780/frpc/list";
try {
const response = await fetch(url, {
method: "GET",
headers: {
"Content-Type": "application/json"
}
});
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const data = await response.json();
if (data.success) {
proxies.value = data.data;
saveProxies(proxies.value);
} else {
console.error("Failed to retrieve proxies:", data.message);
}
} catch (error) {
console.error("Error fetching proxies:", error);
}
};
const fetchProxyByName = async (name: string) => {
const url = `http://localhost:56780/frpc/get?name=${encodeURIComponent(name)}`;
try {
const response = await fetch(url, {
method: "GET",
headers: {
"Content-Type": "application/json"
}
});
const text = await response.text();
console.log("Response text:", text);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const data = JSON.parse(text);
if (data.success) {
proxyData.value = data.data.proxy;
customDomains.value = proxyData.value.customDomains || [""];
} else {
console.error("Failed to retrieve proxy:", data.message);
}
} catch (error) {
console.error("Error fetching proxy:", error);
}
};
const deleteProxyByName = async (name: string) => {
const url = `http://localhost:56780/frpc/delete?name=${encodeURIComponent(name)}`;
try {
const response = await fetch(url, {
method: "GET",
headers: {
"Content-Type": "application/json"
}
});
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const data = await response.json();
if (data.success) {
proxies.value = proxies.value.filter(p => p.name !== name);
saveProxies(proxies.value);
console.log("Proxy deleted successfully");
} else {
console.error("Failed to delete proxy:", data.message);
}
} catch (error) {
console.error("Error deleting proxy:", error);
}
};
const updateProxyByName = async (proxy: ProxyItem) => {
const url = `http://localhost:56780/frpc/update`;
try {
const response = await fetch(url, {
method: "POST",
headers: {
"Content-Type": "application/json"
},
body: JSON.stringify(proxy)
});
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const data = await response.json();
if (data.success) {
const index = proxies.value.findIndex(p => p.name === proxy.name);
if (index !== -1) {
proxies.value[index] = proxy;
saveProxies(proxies.value);
console.log("Proxy updated successfully");
}
} else {
console.error("Failed to update proxy:", data.message);
}
} catch (error) {
console.error("Error updating proxy:", error);
}
};
@ -178,5 +290,9 @@ export const useProxyStore = defineStore('proxyStore', () => {
removeCustomDomain,
resetProxyData,
createFrpcConfig,
fetchProxies,
fetchProxyByName,
deleteProxyByName,
updateProxyByName,
};
});

14
godo/proxy/frpc.go

@ -579,13 +579,6 @@ func DeleteFrpcConfigHandler(w http.ResponseWriter, r *http.Request) {
}
func UpdateFrpcConfigHandler(w http.ResponseWriter, r *http.Request) {
// 获取请求参数中的 name
name := r.URL.Query().Get("name")
if name == "" {
http.Error(w, "Name parameter is required", http.StatusBadRequest)
return
}
// 解析请求体中的更新数据
var updateData Proxy
err := json.NewDecoder(r.Body).Decode(&updateData)
@ -594,6 +587,13 @@ func UpdateFrpcConfigHandler(w http.ResponseWriter, r *http.Request) {
return
}
// 从更新数据中获取 name
name := updateData.Name
if name == "" {
http.Error(w, "Name field is required in the request body", http.StatusBadRequest)
return
}
// 使用 os.ReadFile 读取配置文件内容
path := libs.GetAppExecDir()
filePath := filepath.Join(path, "frpc", "frpc.ini")

Loading…
Cancel
Save