mirror of
https://github.com/alireza0/x-ui.git
synced 2026-03-14 05:23:09 +00:00
[feature] backup from panel #151
This commit is contained in:
@@ -39,6 +39,8 @@ func (a *ServerController) initRouter(g *gin.RouterGroup) {
|
||||
g.POST("/restartXrayService", a.restartXrayService)
|
||||
g.POST("/installXray/:version", a.installXray)
|
||||
g.POST("/logs/:count", a.getLogs)
|
||||
g.POST("/getConfigJson", a.getConfigJson)
|
||||
g.GET("/getDb", a.getDb)
|
||||
}
|
||||
|
||||
func (a *ServerController) refreshStatus() {
|
||||
@@ -117,3 +119,26 @@ func (a *ServerController) getLogs(c *gin.Context) {
|
||||
}
|
||||
jsonObj(c, logs, nil)
|
||||
}
|
||||
|
||||
func (a *ServerController) getConfigJson(c *gin.Context) {
|
||||
configJson, err := a.serverService.GetConfigJson()
|
||||
if err != nil {
|
||||
jsonMsg(c, I18n(c, "getLogs"), err)
|
||||
return
|
||||
}
|
||||
jsonObj(c, configJson, nil)
|
||||
}
|
||||
|
||||
func (a *ServerController) getDb(c *gin.Context) {
|
||||
db, err := a.serverService.GetDb()
|
||||
if err != nil {
|
||||
jsonMsg(c, I18n(c, "getLogs"), err)
|
||||
return
|
||||
}
|
||||
// Set the headers for the response
|
||||
c.Header("Content-Type", "application/octet-stream")
|
||||
c.Header("Content-Disposition", "attachment; filename=xui.db")
|
||||
|
||||
// Write the file contents to the response
|
||||
c.Writer.Write(db)
|
||||
}
|
||||
|
||||
@@ -76,24 +76,12 @@
|
||||
<a-row>
|
||||
<a-col :sm="24" :md="12">
|
||||
<a-card hoverable :class="siderDrawer.isDarkTheme ? darkClass : ''">
|
||||
{{ i18n "pages.index.xrayStatus" }}:
|
||||
<a-tag :color="status.xray.color">[[ status.xray.state ]]</a-tag>
|
||||
<a-tooltip v-if="status.xray.state === State.Error">
|
||||
<template slot="title">
|
||||
<p v-for="line in status.xray.errorMsg.split('\n')">[[ line ]]</p>
|
||||
</template>
|
||||
<a-icon type="question-circle" theme="filled"></a-icon>
|
||||
</a-tooltip>
|
||||
<a-tag color="green" style="cursor: pointer;" @click="openSelectV2rayVersion">[[ status.xray.version ]]</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="stopXrayService">{{ i18n "pages.index.stopXray" }}</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="restartXrayService">{{ i18n "pages.index.restartXray" }}</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="openSelectV2rayVersion">{{ i18n "pages.index.xraySwitch" }}</a-tag>
|
||||
x-ui: <a-tag color="green">{{ .cur_ver }}</a-tag>
|
||||
xray: <a-tag color="green" style="cursor: pointer;" @click="openSelectV2rayVersion">[[ status.xray.version ]]</a-tag>
|
||||
</a-card>
|
||||
</a-col>
|
||||
<a-col :sm="24" :md="12">
|
||||
<a-card hoverable :class="siderDrawer.isDarkTheme ? darkClass : ''">
|
||||
x-ui: <a-tag color="green">{{ .cur_ver }}</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="openLogs(20)">Logs</a-tag>
|
||||
{{ i18n "pages.index.operationHours" }}:
|
||||
<a-tag color="green">[[ formatSecond(status.uptime) ]]</a-tag>
|
||||
<a-tooltip>
|
||||
@@ -104,6 +92,29 @@
|
||||
</a-tooltip>
|
||||
</a-card>
|
||||
</a-col>
|
||||
<a-col :sm="24" :md="12">
|
||||
<a-card hoverable :class="siderDrawer.isDarkTheme ? darkClass : ''">
|
||||
{{ i18n "pages.index.xrayStatus" }}:
|
||||
<a-tag :color="status.xray.color">[[ status.xray.state ]]</a-tag>
|
||||
<a-tooltip v-if="status.xray.state === State.Error">
|
||||
<template slot="title">
|
||||
<p v-for="line in status.xray.errorMsg.split('\n')">[[ line ]]</p>
|
||||
</template>
|
||||
<a-icon type="question-circle" theme="filled"></a-icon>
|
||||
</a-tooltip>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="stopXrayService">{{ i18n "pages.index.stopXray" }}</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="restartXrayService">{{ i18n "pages.index.restartXray" }}</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="openSelectV2rayVersion">{{ i18n "pages.index.xraySwitch" }}</a-tag>
|
||||
</a-card>
|
||||
</a-col>
|
||||
<a-col :sm="24" :md="12">
|
||||
<a-card hoverable :class="siderDrawer.isDarkTheme ? darkClass : ''">
|
||||
{{ i18n "menu.link" }}:
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="openLogs(20)">Logs</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="openConfig">Config</a-tag>
|
||||
<a-tag color="blue" style="cursor: pointer;" @click="getBackup">Backup</a-tag>
|
||||
</a-card>
|
||||
</a-col>
|
||||
<a-col :sm="24" :md="12">
|
||||
<a-card hoverable :class="siderDrawer.isDarkTheme ? darkClass : ''">
|
||||
{{ i18n "pages.index.systemLoad" }}: [[ status.loads[0] ]] | [[ status.loads[1] ]] | [[ status.loads[2] ]]
|
||||
@@ -221,6 +232,7 @@
|
||||
</a-modal>
|
||||
</a-layout>
|
||||
{{template "js" .}}
|
||||
{{template "textModal"}}
|
||||
<script>
|
||||
|
||||
const State = {
|
||||
@@ -401,6 +413,18 @@
|
||||
return;
|
||||
}
|
||||
logModal.show(msg.obj,rows);
|
||||
},
|
||||
async openConfig(){
|
||||
this.loading(true);
|
||||
const msg = await HttpUtil.post('server/getConfigJson');
|
||||
this.loading(false);
|
||||
if (!msg.success) {
|
||||
return;
|
||||
}
|
||||
txtModal.show('config.json',JSON.stringify(msg.obj, null, 2),'config.json');
|
||||
},
|
||||
getBackup(){
|
||||
window.location = '/server/getDb';
|
||||
}
|
||||
},
|
||||
async mounted() {
|
||||
|
||||
@@ -13,6 +13,7 @@ import (
|
||||
"runtime"
|
||||
"strings"
|
||||
"time"
|
||||
"x-ui/config"
|
||||
"x-ui/logger"
|
||||
"x-ui/util/sys"
|
||||
"x-ui/xray"
|
||||
@@ -349,3 +350,43 @@ func (s *ServerService) GetLogs(count string) ([]string, error) {
|
||||
|
||||
return lines, nil
|
||||
}
|
||||
|
||||
func (s *ServerService) GetConfigJson() (interface{}, error) {
|
||||
// Open the file for reading
|
||||
file, err := os.Open(xray.GetConfigPath())
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
defer file.Close()
|
||||
|
||||
// Read the file contents
|
||||
fileContents, err := io.ReadAll(file)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
var jsonData interface{}
|
||||
err = json.Unmarshal(fileContents, &jsonData)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return jsonData, nil
|
||||
}
|
||||
|
||||
func (s *ServerService) GetDb() ([]byte, error) {
|
||||
// Open the file for reading
|
||||
file, err := os.Open(config.GetDBPath())
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
defer file.Close()
|
||||
|
||||
// Read the file contents
|
||||
fileContents, err := io.ReadAll(file)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return fileContents, nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user