mirror of
https://github.com/1Panel-dev/1Panel.git
synced 2026-10-11 00:00:30 +00:00
Compare commits
14
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
1c826525e3 | ||
|
|
3f0fd48cf3 | ||
|
|
211dbfdead | ||
|
|
aafec142cc | ||
|
|
384ff57df7 | ||
|
|
01ddd203ea | ||
|
|
29aed616ac | ||
|
|
83f0df9d84 | ||
|
|
7aa16c8142 | ||
|
|
3bd505954f | ||
|
|
275c0522a3 | ||
|
|
85dec6815b | ||
|
|
5e4e9f762e | ||
|
|
7ae3722997 |
@@ -61,7 +61,7 @@ func (b *BaseApi) LoadDaemonJson(c *gin.Context) {
|
|||||||
// @Success 200
|
// @Success 200
|
||||||
// @Security ApiKeyAuth
|
// @Security ApiKeyAuth
|
||||||
// @Router /containers/daemonjson/update [post]
|
// @Router /containers/daemonjson/update [post]
|
||||||
// @x-panel-log {"bodyKeys":["key", "value"],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新 docker daemon.json 配置 [key]=>[value]","formatEN":"Updated the docker daemon.json configuration [key]=>[value]"}
|
// @x-panel-log {"bodyKeys":["key", "value"],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新配置 [key]","formatEN":"Updated configuration [key]"}
|
||||||
func (b *BaseApi) UpdateDaemonJson(c *gin.Context) {
|
func (b *BaseApi) UpdateDaemonJson(c *gin.Context) {
|
||||||
var req dto.SettingUpdate
|
var req dto.SettingUpdate
|
||||||
if err := helper.CheckBindAndValidate(&req, c); err != nil {
|
if err := helper.CheckBindAndValidate(&req, c); err != nil {
|
||||||
@@ -84,7 +84,7 @@ func (b *BaseApi) UpdateDaemonJson(c *gin.Context) {
|
|||||||
// @Success 200
|
// @Success 200
|
||||||
// @Security ApiKeyAuth
|
// @Security ApiKeyAuth
|
||||||
// @Router /containers/logoption/update [post]
|
// @Router /containers/logoption/update [post]
|
||||||
// @x-panel-log {"bodyKeys":[],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新 docker daemon.json 日志配置","formatEN":"Updated the docker daemon.json log option"}
|
// @x-panel-log {"bodyKeys":[],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新日志配置","formatEN":"Updated the log option"}
|
||||||
func (b *BaseApi) UpdateLogOption(c *gin.Context) {
|
func (b *BaseApi) UpdateLogOption(c *gin.Context) {
|
||||||
var req dto.LogOption
|
var req dto.LogOption
|
||||||
if err := helper.CheckBind(&req, c); err != nil {
|
if err := helper.CheckBind(&req, c); err != nil {
|
||||||
@@ -107,7 +107,7 @@ func (b *BaseApi) UpdateLogOption(c *gin.Context) {
|
|||||||
// @Success 200
|
// @Success 200
|
||||||
// @Security ApiKeyAuth
|
// @Security ApiKeyAuth
|
||||||
// @Router /containers/ipv6option/update [post]
|
// @Router /containers/ipv6option/update [post]
|
||||||
// @x-panel-log {"bodyKeys":[],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新 docker daemon.json ipv6 配置","formatEN":"Updated the docker daemon.json ipv6 option"}
|
// @x-panel-log {"bodyKeys":[],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新 ipv6 配置","formatEN":"Updated the ipv6 option"}
|
||||||
func (b *BaseApi) UpdateIpv6Option(c *gin.Context) {
|
func (b *BaseApi) UpdateIpv6Option(c *gin.Context) {
|
||||||
var req dto.Ipv6Option
|
var req dto.Ipv6Option
|
||||||
if err := helper.CheckBind(&req, c); err != nil {
|
if err := helper.CheckBind(&req, c); err != nil {
|
||||||
@@ -130,7 +130,7 @@ func (b *BaseApi) UpdateIpv6Option(c *gin.Context) {
|
|||||||
// @Success 200
|
// @Success 200
|
||||||
// @Security ApiKeyAuth
|
// @Security ApiKeyAuth
|
||||||
// @Router /containers/daemonjson/update/byfile [post]
|
// @Router /containers/daemonjson/update/byfile [post]
|
||||||
// @x-panel-log {"bodyKeys":[],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新 docker daemon.json 配置","formatEN":"Updated the docker daemon.json configuration"}
|
// @x-panel-log {"bodyKeys":[],"paramKeys":[],"BeforeFunctions":[],"formatZH":"更新配置文件","formatEN":"Updated configuration file"}
|
||||||
func (b *BaseApi) UpdateDaemonJsonByFile(c *gin.Context) {
|
func (b *BaseApi) UpdateDaemonJsonByFile(c *gin.Context) {
|
||||||
var req dto.DaemonJsonUpdateByFile
|
var req dto.DaemonJsonUpdateByFile
|
||||||
if err := helper.CheckBindAndValidate(&req, c); err != nil {
|
if err := helper.CheckBindAndValidate(&req, c); err != nil {
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ type SearchCommandWithPage struct {
|
|||||||
Order string `json:"order"`
|
Order string `json:"order"`
|
||||||
GroupID uint `json:"groupID"`
|
GroupID uint `json:"groupID"`
|
||||||
Info string `json:"info"`
|
Info string `json:"info"`
|
||||||
|
Name string `json:"name"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type CommandOperate struct {
|
type CommandOperate struct {
|
||||||
|
|||||||
@@ -178,7 +178,7 @@ type WebsiteProxyConfig struct {
|
|||||||
CacheTime int `json:"cacheTime" `
|
CacheTime int `json:"cacheTime" `
|
||||||
CacheUnit string `json:"cacheUnit"`
|
CacheUnit string `json:"cacheUnit"`
|
||||||
Name string `json:"name" validate:"required"`
|
Name string `json:"name" validate:"required"`
|
||||||
Modifier string `json:"modifier" validate:"required"`
|
Modifier string `json:"modifier"`
|
||||||
Match string `json:"match" validate:"required"`
|
Match string `json:"match" validate:"required"`
|
||||||
ProxyPass string `json:"proxyPass" validate:"required"`
|
ProxyPass string `json:"proxyPass" validate:"required"`
|
||||||
ProxyHost string `json:"proxyHost" validate:"required"`
|
ProxyHost string `json:"proxyHost" validate:"required"`
|
||||||
|
|||||||
@@ -16,6 +16,7 @@ type ICommandRepo interface {
|
|||||||
Update(id uint, vars map[string]interface{}) error
|
Update(id uint, vars map[string]interface{}) error
|
||||||
Delete(opts ...DBOption) error
|
Delete(opts ...DBOption) error
|
||||||
Get(opts ...DBOption) (model.Command, error)
|
Get(opts ...DBOption) (model.Command, error)
|
||||||
|
WithLikeName(name string) DBOption
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewICommandRepo() ICommandRepo {
|
func NewICommandRepo() ICommandRepo {
|
||||||
@@ -79,3 +80,12 @@ func (u *CommandRepo) Delete(opts ...DBOption) error {
|
|||||||
}
|
}
|
||||||
return db.Delete(&model.Command{}).Error
|
return db.Delete(&model.Command{}).Error
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (a CommandRepo) WithLikeName(name string) DBOption {
|
||||||
|
return func(g *gorm.DB) *gorm.DB {
|
||||||
|
if len(name) == 0 {
|
||||||
|
return g
|
||||||
|
}
|
||||||
|
return g.Where("name like ? or command like ?", "%"+name+"%", "%"+name+"%")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -65,7 +65,7 @@ func (u *CommandService) SearchForTree() ([]dto.CommandTree, error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (u *CommandService) SearchWithPage(search dto.SearchCommandWithPage) (int64, interface{}, error) {
|
func (u *CommandService) SearchWithPage(search dto.SearchCommandWithPage) (int64, interface{}, error) {
|
||||||
total, commands, err := commandRepo.Page(search.Page, search.PageSize, commonRepo.WithLikeName(search.Info), commonRepo.WithByGroupID(search.GroupID), commonRepo.WithOrderRuleBy(search.OrderBy, search.Order))
|
total, commands, err := commandRepo.Page(search.Page, search.PageSize, commandRepo.WithLikeName(search.Name), commonRepo.WithLikeName(search.Info), commonRepo.WithByGroupID(search.GroupID), commonRepo.WithOrderRuleBy(search.OrderBy, search.Order))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, nil, err
|
return 0, nil, err
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,7 +2,6 @@ package service
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"encoding/json"
|
|
||||||
"fmt"
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
"path"
|
"path"
|
||||||
@@ -276,21 +275,6 @@ func loadClientMap(backupAccounts string) (map[string]cronjobUploadHelper, error
|
|||||||
if account.BackupPath != "/" {
|
if account.BackupPath != "/" {
|
||||||
pathItem = strings.TrimPrefix(account.BackupPath, "/")
|
pathItem = strings.TrimPrefix(account.BackupPath, "/")
|
||||||
}
|
}
|
||||||
if target == constant.Local {
|
|
||||||
varMap := make(map[string]interface{})
|
|
||||||
if err := json.Unmarshal([]byte(account.Vars), &varMap); err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
if _, ok := varMap["dir"]; !ok {
|
|
||||||
return nil, errors.New("load local backup dir failed")
|
|
||||||
}
|
|
||||||
baseDir, ok := varMap["dir"].(string)
|
|
||||||
if ok {
|
|
||||||
pathItem = baseDir
|
|
||||||
} else {
|
|
||||||
return nil, fmt.Errorf("error type dir: %T", varMap["dir"])
|
|
||||||
}
|
|
||||||
}
|
|
||||||
clients[target] = cronjobUploadHelper{
|
clients[target] = cronjobUploadHelper{
|
||||||
client: client,
|
client: client,
|
||||||
backupPath: pathItem,
|
backupPath: pathItem,
|
||||||
|
|||||||
@@ -288,6 +288,10 @@ func createWafConfig(website *model.Website, domains []model.WebsiteDomain) erro
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if !common.CompareVersion(nginxInstall.Version, "1.21.4.3-2-0") {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
wafDataPath := path.Join(nginxInstall.GetPath(), "1pwaf", "data")
|
wafDataPath := path.Join(nginxInstall.GetPath(), "1pwaf", "data")
|
||||||
fileOp := files.NewFileOp()
|
fileOp := files.NewFileOp()
|
||||||
if !fileOp.Stat(wafDataPath) {
|
if !fileOp.Stat(wafDataPath) {
|
||||||
@@ -419,6 +423,9 @@ func delWafConfig(website model.Website, force bool) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
if !common.CompareVersion(nginxInstall.Version, "1.21.4.3-2-0") {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
wafDataPath := path.Join(nginxInstall.GetPath(), "1pwaf", "data")
|
wafDataPath := path.Join(nginxInstall.GetPath(), "1pwaf", "data")
|
||||||
fileOp := files.NewFileOp()
|
fileOp := files.NewFileOp()
|
||||||
if !fileOp.Stat(wafDataPath) {
|
if !fileOp.Stat(wafDataPath) {
|
||||||
|
|||||||
@@ -54,7 +54,7 @@ func (c localClient) Upload(src, target string) (bool, error) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := common.CopyFile(src, target); err != nil {
|
if err := common.CopyFile(src, targetFilePath); err != nil {
|
||||||
return false, fmt.Errorf("cp file failed, err: %v", err)
|
return false, fmt.Errorf("cp file failed, err: %v", err)
|
||||||
}
|
}
|
||||||
return true, nil
|
return true, nil
|
||||||
|
|||||||
@@ -314,6 +314,7 @@ func (f FileOp) DownloadFile(url, dst string) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
defer resp.Body.Close()
|
||||||
|
|
||||||
out, err := os.Create(dst)
|
out, err := os.Create(dst)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@@ -324,8 +325,6 @@ func (f FileOp) DownloadFile(url, dst string) error {
|
|||||||
if _, err = io.Copy(out, resp.Body); err != nil {
|
if _, err = io.Copy(out, resp.Body); err != nil {
|
||||||
return fmt.Errorf("save download file [%s] error, err %s", dst, err.Error())
|
return fmt.Errorf("save download file [%s] error, err %s", dst, err.Error())
|
||||||
}
|
}
|
||||||
out.Close()
|
|
||||||
resp.Body.Close()
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -3,7 +3,6 @@ package files
|
|||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/spf13/afero"
|
|
||||||
"io"
|
"io"
|
||||||
"net/http"
|
"net/http"
|
||||||
"os"
|
"os"
|
||||||
@@ -12,6 +11,8 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
"sync"
|
"sync"
|
||||||
|
|
||||||
|
"github.com/spf13/afero"
|
||||||
)
|
)
|
||||||
|
|
||||||
func IsSymlink(mode os.FileMode) bool {
|
func IsSymlink(mode os.FileMode) bool {
|
||||||
@@ -144,8 +145,5 @@ func GetParentMode(path string) (os.FileMode, error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func IsInvalidChar(name string) bool {
|
func IsInvalidChar(name string) bool {
|
||||||
if strings.Contains(name, "&") {
|
return strings.Contains(name, "&")
|
||||||
return true
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1444,8 +1444,8 @@ const docTemplate = `{
|
|||||||
"key",
|
"key",
|
||||||
"value"
|
"value"
|
||||||
],
|
],
|
||||||
"formatEN": "Updated the docker daemon.json configuration [key]=\u003e[value]",
|
"formatEN": "Updated configuration [key]",
|
||||||
"formatZH": "更新 docker daemon.json 配置 [key]=\u003e[value]",
|
"formatZH": "更新配置 [key]",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1484,8 +1484,8 @@ const docTemplate = `{
|
|||||||
"x-panel-log": {
|
"x-panel-log": {
|
||||||
"BeforeFunctions": [],
|
"BeforeFunctions": [],
|
||||||
"bodyKeys": [],
|
"bodyKeys": [],
|
||||||
"formatEN": "Updated the docker daemon.json configuration",
|
"formatEN": "Updated configuration file",
|
||||||
"formatZH": "更新 docker daemon.json 配置",
|
"formatZH": "更新配置文件",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2094,8 +2094,8 @@ const docTemplate = `{
|
|||||||
"x-panel-log": {
|
"x-panel-log": {
|
||||||
"BeforeFunctions": [],
|
"BeforeFunctions": [],
|
||||||
"bodyKeys": [],
|
"bodyKeys": [],
|
||||||
"formatEN": "Updated the docker daemon.json ipv6 option",
|
"formatEN": "Updated the ipv6 option",
|
||||||
"formatZH": "更新 docker daemon.json ipv6 配置",
|
"formatZH": "更新 ipv6 配置",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2233,8 +2233,8 @@ const docTemplate = `{
|
|||||||
"x-panel-log": {
|
"x-panel-log": {
|
||||||
"BeforeFunctions": [],
|
"BeforeFunctions": [],
|
||||||
"bodyKeys": [],
|
"bodyKeys": [],
|
||||||
"formatEN": "Updated the docker daemon.json log option",
|
"formatEN": "Updated the log option",
|
||||||
"formatZH": "更新 docker daemon.json 日志配置",
|
"formatZH": "更新日志配置",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1437,8 +1437,8 @@
|
|||||||
"key",
|
"key",
|
||||||
"value"
|
"value"
|
||||||
],
|
],
|
||||||
"formatEN": "Updated the docker daemon.json configuration [key]=\u003e[value]",
|
"formatEN": "Updated configuration [key]",
|
||||||
"formatZH": "更新 docker daemon.json 配置 [key]=\u003e[value]",
|
"formatZH": "更新配置 [key]",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1477,8 +1477,8 @@
|
|||||||
"x-panel-log": {
|
"x-panel-log": {
|
||||||
"BeforeFunctions": [],
|
"BeforeFunctions": [],
|
||||||
"bodyKeys": [],
|
"bodyKeys": [],
|
||||||
"formatEN": "Updated the docker daemon.json configuration",
|
"formatEN": "Updated configuration file",
|
||||||
"formatZH": "更新 docker daemon.json 配置",
|
"formatZH": "更新配置文件",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2087,8 +2087,8 @@
|
|||||||
"x-panel-log": {
|
"x-panel-log": {
|
||||||
"BeforeFunctions": [],
|
"BeforeFunctions": [],
|
||||||
"bodyKeys": [],
|
"bodyKeys": [],
|
||||||
"formatEN": "Updated the docker daemon.json ipv6 option",
|
"formatEN": "Updated the ipv6 option",
|
||||||
"formatZH": "更新 docker daemon.json ipv6 配置",
|
"formatZH": "更新 ipv6 配置",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -2226,8 +2226,8 @@
|
|||||||
"x-panel-log": {
|
"x-panel-log": {
|
||||||
"BeforeFunctions": [],
|
"BeforeFunctions": [],
|
||||||
"bodyKeys": [],
|
"bodyKeys": [],
|
||||||
"formatEN": "Updated the docker daemon.json log option",
|
"formatEN": "Updated the log option",
|
||||||
"formatZH": "更新 docker daemon.json 日志配置",
|
"formatZH": "更新日志配置",
|
||||||
"paramKeys": []
|
"paramKeys": []
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5938,8 +5938,8 @@ paths:
|
|||||||
bodyKeys:
|
bodyKeys:
|
||||||
- key
|
- key
|
||||||
- value
|
- value
|
||||||
formatEN: Updated the docker daemon.json configuration [key]=>[value]
|
formatEN: Updated configuration [key]
|
||||||
formatZH: 更新 docker daemon.json 配置 [key]=>[value]
|
formatZH: 更新配置 [key]
|
||||||
paramKeys: []
|
paramKeys: []
|
||||||
/containers/daemonjson/update/byfile:
|
/containers/daemonjson/update/byfile:
|
||||||
post:
|
post:
|
||||||
@@ -5964,8 +5964,8 @@ paths:
|
|||||||
x-panel-log:
|
x-panel-log:
|
||||||
BeforeFunctions: []
|
BeforeFunctions: []
|
||||||
bodyKeys: []
|
bodyKeys: []
|
||||||
formatEN: Updated the docker daemon.json configuration
|
formatEN: Updated configuration file
|
||||||
formatZH: 更新 docker daemon.json 配置
|
formatZH: 更新配置文件
|
||||||
paramKeys: []
|
paramKeys: []
|
||||||
/containers/docker/operate:
|
/containers/docker/operate:
|
||||||
post:
|
post:
|
||||||
@@ -6353,8 +6353,8 @@ paths:
|
|||||||
x-panel-log:
|
x-panel-log:
|
||||||
BeforeFunctions: []
|
BeforeFunctions: []
|
||||||
bodyKeys: []
|
bodyKeys: []
|
||||||
formatEN: Updated the docker daemon.json ipv6 option
|
formatEN: Updated the ipv6 option
|
||||||
formatZH: 更新 docker daemon.json ipv6 配置
|
formatZH: 更新 ipv6 配置
|
||||||
paramKeys: []
|
paramKeys: []
|
||||||
/containers/limit:
|
/containers/limit:
|
||||||
get:
|
get:
|
||||||
@@ -6438,8 +6438,8 @@ paths:
|
|||||||
x-panel-log:
|
x-panel-log:
|
||||||
BeforeFunctions: []
|
BeforeFunctions: []
|
||||||
bodyKeys: []
|
bodyKeys: []
|
||||||
formatEN: Updated the docker daemon.json log option
|
formatEN: Updated the log option
|
||||||
formatZH: 更新 docker daemon.json 日志配置
|
formatZH: 更新日志配置
|
||||||
paramKeys: []
|
paramKeys: []
|
||||||
/containers/network:
|
/containers/network:
|
||||||
get:
|
get:
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ export interface SearchWithPage {
|
|||||||
pageSize: number;
|
pageSize: number;
|
||||||
orderBy?: string;
|
orderBy?: string;
|
||||||
order?: string;
|
order?: string;
|
||||||
|
name?: string;
|
||||||
}
|
}
|
||||||
export interface CommonModel {
|
export interface CommonModel {
|
||||||
id: number;
|
id: number;
|
||||||
|
|||||||
@@ -139,6 +139,7 @@ export namespace Setting {
|
|||||||
upload: string;
|
upload: string;
|
||||||
}
|
}
|
||||||
export interface UpgradeInfo {
|
export interface UpgradeInfo {
|
||||||
|
testVersion: string;
|
||||||
newVersion: string;
|
newVersion: string;
|
||||||
latestVersion: string;
|
latestVersion: string;
|
||||||
releaseNote: string;
|
releaseNote: string;
|
||||||
|
|||||||
+34
-1643
File diff suppressed because it is too large
Load Diff
@@ -83,7 +83,8 @@ const seriesStyle = [
|
|||||||
|
|
||||||
function initChart() {
|
function initChart() {
|
||||||
let itemChart = echarts?.getInstanceByDom(document.getElementById(props.id) as HTMLElement);
|
let itemChart = echarts?.getInstanceByDom(document.getElementById(props.id) as HTMLElement);
|
||||||
// 如果不存在,就进行初始化
|
const optionItem = itemChart?.getOption();
|
||||||
|
const itemSelect = optionItem?.legend;
|
||||||
if (itemChart == null) {
|
if (itemChart == null) {
|
||||||
itemChart = echarts.init(document.getElementById(props.id) as HTMLElement);
|
itemChart = echarts.init(document.getElementById(props.id) as HTMLElement);
|
||||||
}
|
}
|
||||||
@@ -109,10 +110,9 @@ function initChart() {
|
|||||||
yAxis.push({
|
yAxis.push({
|
||||||
splitLine: {
|
splitLine: {
|
||||||
show: true,
|
show: true,
|
||||||
//分隔辅助线
|
|
||||||
lineStyle: {
|
lineStyle: {
|
||||||
type: 'dashed', //线的类型 虚线0
|
type: 'dashed',
|
||||||
opacity: theme === 'dark' ? 0.1 : 1, //透明度
|
opacity: theme === 'dark' ? 0.1 : 1,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
...item,
|
...item,
|
||||||
@@ -120,7 +120,6 @@ function initChart() {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// 把配置和数据放这里
|
|
||||||
const option = {
|
const option = {
|
||||||
title: [
|
title: [
|
||||||
{
|
{
|
||||||
@@ -168,7 +167,7 @@ function initChart() {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
grid: props.option.grid || { left: '7%', right: '7%', bottom: '20%' },
|
grid: props.option.grid || { left: '7%', right: '7%', bottom: '20%' },
|
||||||
legend: {
|
legend: itemSelect || {
|
||||||
right: 10,
|
right: 10,
|
||||||
itemWidth: 8,
|
itemWidth: 8,
|
||||||
textStyle: {
|
textStyle: {
|
||||||
|
|||||||
@@ -58,6 +58,8 @@ const message = {
|
|||||||
fullscreen: 'Fullscreen',
|
fullscreen: 'Fullscreen',
|
||||||
quitFullscreen: 'Quit Fullscreen',
|
quitFullscreen: 'Quit Fullscreen',
|
||||||
update: 'Edit',
|
update: 'Edit',
|
||||||
|
showAll: 'Show All',
|
||||||
|
hideSome: 'Hide Some',
|
||||||
},
|
},
|
||||||
search: {
|
search: {
|
||||||
timeStart: 'Time start',
|
timeStart: 'Time start',
|
||||||
@@ -1934,6 +1936,9 @@ const message = {
|
|||||||
acmeAccountType: 'Account Type',
|
acmeAccountType: 'Account Type',
|
||||||
keyType: 'Key algorithm',
|
keyType: 'Key algorithm',
|
||||||
tencentCloud: 'Tencent Cloud',
|
tencentCloud: 'Tencent Cloud',
|
||||||
|
containWarn: 'The domain name contains the main domain, please re-enter',
|
||||||
|
rewriteHelper2:
|
||||||
|
'Applications such as WordPress installed from the app store have pseudo-static configuration by default. Repeated configuration may result in errors',
|
||||||
},
|
},
|
||||||
php: {
|
php: {
|
||||||
short_open_tag: 'Short tag support',
|
short_open_tag: 'Short tag support',
|
||||||
|
|||||||
@@ -58,6 +58,8 @@ const message = {
|
|||||||
fullscreen: '全屏',
|
fullscreen: '全屏',
|
||||||
quitFullscreen: '退出全屏',
|
quitFullscreen: '退出全屏',
|
||||||
update: '編輯',
|
update: '編輯',
|
||||||
|
showAll: '顯示所有',
|
||||||
|
hideSome: '隱藏部分',
|
||||||
},
|
},
|
||||||
search: {
|
search: {
|
||||||
timeStart: '開始時間',
|
timeStart: '開始時間',
|
||||||
@@ -1810,6 +1812,8 @@ const message = {
|
|||||||
acmeAccountType: '賬號類型',
|
acmeAccountType: '賬號類型',
|
||||||
keyType: '密鑰演算法',
|
keyType: '密鑰演算法',
|
||||||
tencentCloud: '騰訊雲',
|
tencentCloud: '騰訊雲',
|
||||||
|
containWarn: '其他域名中包含主域名,请重新輸入',
|
||||||
|
rewriteHelper2: '從應用程式商店安裝的 WordPress 等應用,預設已經配置好偽靜態,重複配置可能會報錯',
|
||||||
},
|
},
|
||||||
php: {
|
php: {
|
||||||
short_open_tag: '短標簽支持',
|
short_open_tag: '短標簽支持',
|
||||||
|
|||||||
@@ -58,6 +58,8 @@ const message = {
|
|||||||
fullscreen: '全屏',
|
fullscreen: '全屏',
|
||||||
quitFullscreen: '退出全屏',
|
quitFullscreen: '退出全屏',
|
||||||
update: '编辑',
|
update: '编辑',
|
||||||
|
showAll: '显示所有',
|
||||||
|
hideSome: '隐藏部分',
|
||||||
},
|
},
|
||||||
search: {
|
search: {
|
||||||
timeStart: '开始时间',
|
timeStart: '开始时间',
|
||||||
@@ -1810,6 +1812,8 @@ const message = {
|
|||||||
acmeAccountType: '账号类型',
|
acmeAccountType: '账号类型',
|
||||||
keyType: '密钥算法',
|
keyType: '密钥算法',
|
||||||
tencentCloud: '腾讯云',
|
tencentCloud: '腾讯云',
|
||||||
|
containWarn: '其他域名中包含主域名,请重新输入',
|
||||||
|
rewriteHelper2: '从应用商店安装的 WordPress 等应用,默认已经配置好伪静态,重复配置可能会报错',
|
||||||
},
|
},
|
||||||
php: {
|
php: {
|
||||||
short_open_tag: '短标签支持',
|
short_open_tag: '短标签支持',
|
||||||
|
|||||||
@@ -518,3 +518,14 @@ export function getAction(action: string) {
|
|||||||
export function getLanguage() {
|
export function getLanguage() {
|
||||||
return localStorage.getItem('lang') || 'zh';
|
return localStorage.getItem('lang') || 'zh';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function emptyLineFilter(str: string, spilt: string) {
|
||||||
|
let list = str.split(spilt);
|
||||||
|
let results = [];
|
||||||
|
for (let i = 0; i < list.length; i++) {
|
||||||
|
if (list[i].trim() !== '') {
|
||||||
|
results.push(list[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return results.join(spilt);
|
||||||
|
}
|
||||||
|
|||||||
@@ -46,6 +46,7 @@ import ConfirmDialog from '@/components/confirm-dialog/index.vue';
|
|||||||
import { updateDaemonJson } from '@/api/modules/container';
|
import { updateDaemonJson } from '@/api/modules/container';
|
||||||
import DrawerHeader from '@/components/drawer-header/index.vue';
|
import DrawerHeader from '@/components/drawer-header/index.vue';
|
||||||
import { FormInstance } from 'element-plus';
|
import { FormInstance } from 'element-plus';
|
||||||
|
import { emptyLineFilter } from '@/utils/util';
|
||||||
|
|
||||||
const emit = defineEmits<{ (e: 'search'): void }>();
|
const emit = defineEmits<{ (e: 'search'): void }>();
|
||||||
|
|
||||||
@@ -101,7 +102,7 @@ const onSave = async (formEl: FormInstance | undefined) => {
|
|||||||
|
|
||||||
const onSubmit = async () => {
|
const onSubmit = async () => {
|
||||||
loading.value = true;
|
loading.value = true;
|
||||||
await updateDaemonJson('Mirrors', form.mirrors.replaceAll('\n', ','))
|
await updateDaemonJson('Mirrors', emptyLineFilter(form.mirrors, '\n').replaceAll('\n', ','))
|
||||||
.then(() => {
|
.then(() => {
|
||||||
loading.value = false;
|
loading.value = false;
|
||||||
emit('search');
|
emit('search');
|
||||||
|
|||||||
@@ -46,6 +46,7 @@ import ConfirmDialog from '@/components/confirm-dialog/index.vue';
|
|||||||
import { updateDaemonJson } from '@/api/modules/container';
|
import { updateDaemonJson } from '@/api/modules/container';
|
||||||
import DrawerHeader from '@/components/drawer-header/index.vue';
|
import DrawerHeader from '@/components/drawer-header/index.vue';
|
||||||
import { FormInstance } from 'element-plus';
|
import { FormInstance } from 'element-plus';
|
||||||
|
import { emptyLineFilter } from '@/utils/util';
|
||||||
|
|
||||||
const emit = defineEmits<{ (e: 'search'): void }>();
|
const emit = defineEmits<{ (e: 'search'): void }>();
|
||||||
|
|
||||||
@@ -97,7 +98,7 @@ const onSave = async () => {
|
|||||||
|
|
||||||
const onSubmit = async () => {
|
const onSubmit = async () => {
|
||||||
loading.value = true;
|
loading.value = true;
|
||||||
await updateDaemonJson('Registries', form.registries.replaceAll('\n', ','))
|
await updateDaemonJson('Registries', emptyLineFilter(form.registries, '\n').replaceAll('\n', ','))
|
||||||
.then(() => {
|
.then(() => {
|
||||||
loading.value = false;
|
loading.value = false;
|
||||||
handleClose();
|
handleClose();
|
||||||
|
|||||||
@@ -1,12 +1,7 @@
|
|||||||
<template>
|
<template>
|
||||||
<el-row :gutter="10">
|
<el-row :gutter="10">
|
||||||
<el-col :xs="12" :sm="12" :md="6" :lg="6" :xl="6" align="center">
|
<el-col :xs="12" :sm="12" :md="6" :lg="6" :xl="6" align="center">
|
||||||
<el-popover
|
<el-popover placement="bottom" :width="loadWidth()" trigger="hover" v-if="chartsOption['cpu']">
|
||||||
placement="bottom"
|
|
||||||
:width="currentInfo.cpuPercent.length < 36 ? 300 : (currentInfo.cpuPercent.length / 12) * 150"
|
|
||||||
trigger="hover"
|
|
||||||
v-if="chartsOption['cpu']"
|
|
||||||
>
|
|
||||||
<div>
|
<div>
|
||||||
<el-tooltip
|
<el-tooltip
|
||||||
effect="dark"
|
effect="dark"
|
||||||
@@ -14,7 +9,7 @@
|
|||||||
v-if="baseInfo.cpuModelName.length > 40"
|
v-if="baseInfo.cpuModelName.length > 40"
|
||||||
placement="top"
|
placement="top"
|
||||||
>
|
>
|
||||||
<el-tag>
|
<el-tag class="cpuModeTag">
|
||||||
{{ baseInfo.cpuModelName.substring(0, 40) + '...' }}
|
{{ baseInfo.cpuModelName.substring(0, 40) + '...' }}
|
||||||
</el-tag>
|
</el-tag>
|
||||||
</el-tooltip>
|
</el-tooltip>
|
||||||
@@ -22,14 +17,24 @@
|
|||||||
{{ baseInfo.cpuModelName }}
|
{{ baseInfo.cpuModelName }}
|
||||||
</el-tag>
|
</el-tag>
|
||||||
</div>
|
</div>
|
||||||
<el-tag class="tagClass">
|
<el-tag class="cpuDetailTag">{{ $t('home.core') }} *{{ baseInfo.cpuCores }}</el-tag>
|
||||||
{{ $t('home.core') }} *{{ baseInfo.cpuCores }} {{ $t('home.logicCore') }} *{{
|
<el-tag class="cpuDetailTag">{{ $t('home.logicCore') }} *{{ baseInfo.cpuLogicalCores }}</el-tag>
|
||||||
baseInfo.cpuLogicalCores
|
|
||||||
}}
|
|
||||||
</el-tag>
|
|
||||||
<br />
|
<br />
|
||||||
<div v-for="(item, index) of currentInfo.cpuPercent" :key="index">
|
<div v-for="(item, index) of currentInfo.cpuPercent" :key="index">
|
||||||
<el-tag class="tagCPUClass">CPU-{{ index }}: {{ formatNumber(item) }}%</el-tag>
|
<el-tag v-if="cpuShowAll || (!cpuShowAll && index < 32)" class="tagCPUClass">
|
||||||
|
CPU-{{ index }}: {{ formatNumber(item) }}%
|
||||||
|
</el-tag>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div v-if="currentInfo.cpuPercent.length > 32" class="mt-1 float-right">
|
||||||
|
<el-button v-if="!cpuShowAll" @click="cpuShowAll = true" link type="primary" size="small">
|
||||||
|
{{ $t('commons.button.showAll') }}
|
||||||
|
<el-icon><DArrowRight /></el-icon>
|
||||||
|
</el-button>
|
||||||
|
<el-button v-if="cpuShowAll" @click="cpuShowAll = false" link type="primary" size="small">
|
||||||
|
{{ $t('commons.button.hideSome') }}
|
||||||
|
<el-icon><DArrowLeft /></el-icon>
|
||||||
|
</el-button>
|
||||||
</div>
|
</div>
|
||||||
<template #reference>
|
<template #reference>
|
||||||
<v-charts
|
<v-charts
|
||||||
@@ -302,6 +307,8 @@ const currentInfo = ref<Dashboard.CurrentInfo>({
|
|||||||
shotTime: new Date(),
|
shotTime: new Date(),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const cpuShowAll = ref();
|
||||||
|
|
||||||
const chartsOption = ref({ cpu: null, memory: null, load: null });
|
const chartsOption = ref({ cpu: null, memory: null, load: null });
|
||||||
|
|
||||||
const acceptParams = (current: Dashboard.CurrentInfo, base: Dashboard.BaseInfo, isInit: boolean): void => {
|
const acceptParams = (current: Dashboard.CurrentInfo, base: Dashboard.BaseInfo, isInit: boolean): void => {
|
||||||
@@ -359,6 +366,14 @@ const goGPU = () => {
|
|||||||
router.push({ name: 'GPU' });
|
router.push({ name: 'GPU' });
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const loadWidth = () => {
|
||||||
|
if (!cpuShowAll.value || currentInfo.value.cpuPercent.length < 32) {
|
||||||
|
return 310;
|
||||||
|
}
|
||||||
|
let line = Math.floor(currentInfo.value.cpuPercent.length / 16);
|
||||||
|
return line * 141 + 28;
|
||||||
|
};
|
||||||
|
|
||||||
function formatNumber(val: number) {
|
function formatNumber(val: number) {
|
||||||
return Number(val.toFixed(2));
|
return Number(val.toFixed(2));
|
||||||
}
|
}
|
||||||
@@ -369,6 +384,18 @@ defineExpose({
|
|||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style scoped lang="scss">
|
<style scoped lang="scss">
|
||||||
|
.cpuModeTag {
|
||||||
|
justify-content: flex-start !important;
|
||||||
|
text-align: left !important;
|
||||||
|
width: 280px;
|
||||||
|
}
|
||||||
|
.cpuDetailTag {
|
||||||
|
justify-content: flex-start !important;
|
||||||
|
text-align: left !important;
|
||||||
|
width: 140px;
|
||||||
|
margin-top: 3px;
|
||||||
|
margin-left: 1px;
|
||||||
|
}
|
||||||
.tagClass {
|
.tagClass {
|
||||||
margin-top: 3px;
|
margin-top: 3px;
|
||||||
}
|
}
|
||||||
@@ -378,8 +405,8 @@ defineExpose({
|
|||||||
text-align: left !important;
|
text-align: left !important;
|
||||||
float: left;
|
float: left;
|
||||||
margin-top: 3px;
|
margin-top: 3px;
|
||||||
margin-left: 4px;
|
margin-left: 1px;
|
||||||
width: 100px;
|
width: 140px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.buttonClass {
|
.buttonClass {
|
||||||
|
|||||||
@@ -111,27 +111,24 @@ let uploadHelper = ref('');
|
|||||||
const em = defineEmits(['close']);
|
const em = defineEmits(['close']);
|
||||||
const handleClose = () => {
|
const handleClose = () => {
|
||||||
open.value = false;
|
open.value = false;
|
||||||
uploadRef.value!.clearFiles();
|
clearFiles();
|
||||||
em('close', false);
|
em('close', false);
|
||||||
};
|
};
|
||||||
const state = reactive({
|
const state = reactive({
|
||||||
uploadEle: null,
|
uploadEle: null,
|
||||||
});
|
});
|
||||||
const uploaderFiles = ref<UploadFiles>([]);
|
const uploaderFiles = ref<UploadFiles>([]);
|
||||||
const isUploadFolder = ref(false);
|
|
||||||
const hoverIndex = ref(null);
|
const hoverIndex = ref(null);
|
||||||
const uploadType = ref('file');
|
|
||||||
const tmpFiles = ref<UploadFiles>([]);
|
const tmpFiles = ref<UploadFiles>([]);
|
||||||
const breakFlag = ref(false);
|
const breakFlag = ref(false);
|
||||||
|
|
||||||
const upload = (command: string) => {
|
const upload = (command: string) => {
|
||||||
uploadType.value = command;
|
|
||||||
if (command == 'dir') {
|
if (command == 'dir') {
|
||||||
state.uploadEle.webkitdirectory = true;
|
state.uploadEle.webkitdirectory = true;
|
||||||
} else {
|
} else {
|
||||||
state.uploadEle.webkitdirectory = false;
|
state.uploadEle.webkitdirectory = false;
|
||||||
}
|
}
|
||||||
isUploadFolder.value = true;
|
uploadRef.value.$el.querySelector('input').value = '';
|
||||||
uploadRef.value.$el.querySelector('input').click();
|
uploadRef.value.$el.querySelector('input').click();
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -253,10 +250,11 @@ const fileOnChange = (_uploadFile: UploadFile, uploadFiles: UploadFiles) => {
|
|||||||
|
|
||||||
const clearFiles = () => {
|
const clearFiles = () => {
|
||||||
uploadRef.value!.clearFiles();
|
uploadRef.value!.clearFiles();
|
||||||
|
uploaderFiles.value = [];
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleExceed: UploadProps['onExceed'] = () => {
|
const handleExceed: UploadProps['onExceed'] = () => {
|
||||||
uploadRef.value!.clearFiles();
|
clearFiles();
|
||||||
MsgWarning(i18n.global.t('file.uploadOverLimit'));
|
MsgWarning(i18n.global.t('file.uploadOverLimit'));
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -339,8 +337,7 @@ const submit = async () => {
|
|||||||
loading.value = false;
|
loading.value = false;
|
||||||
uploadHelper.value = '';
|
uploadHelper.value = '';
|
||||||
if (success == files.length) {
|
if (success == files.length) {
|
||||||
uploadRef.value!.clearFiles();
|
clearFiles();
|
||||||
uploaderFiles.value = [];
|
|
||||||
MsgSuccess(i18n.global.t('file.uploadSuccess'));
|
MsgSuccess(i18n.global.t('file.uploadSuccess'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,13 +16,20 @@
|
|||||||
</el-button>
|
</el-button>
|
||||||
</template>
|
</template>
|
||||||
<template #search>
|
<template #search>
|
||||||
<el-select v-model="group" @change="search()" clearable class="p-w-200">
|
<el-row :gutter="5">
|
||||||
<template #prefix>{{ $t('terminal.group') }}</template>
|
<el-col :xs="24" :sm="20" :md="20" :lg="20" :xl="20">
|
||||||
<el-option :label="$t('commons.table.all')" value=""></el-option>
|
<el-select v-model="group" @change="search()" clearable class="p-w-200">
|
||||||
<div v-for="item in groupList" :key="item.name">
|
<template #prefix>{{ $t('terminal.group') }}</template>
|
||||||
<el-option :value="item.id" :label="item.name" />
|
<el-option :label="$t('commons.table.all')" value=""></el-option>
|
||||||
</div>
|
<div v-for="item in groupList" :key="item.name">
|
||||||
</el-select>
|
<el-option :value="item.id" :label="item.name" />
|
||||||
|
</div>
|
||||||
|
</el-select>
|
||||||
|
</el-col>
|
||||||
|
<el-col :xs="24" :sm="4" :md="4" :lg="4" :xl="4">
|
||||||
|
<TableSearch @search="search()" v-model:searchName="commandReq.name" />
|
||||||
|
</el-col>
|
||||||
|
</el-row>
|
||||||
</template>
|
</template>
|
||||||
<template #main>
|
<template #main>
|
||||||
<ComplexTable
|
<ComplexTable
|
||||||
@@ -160,6 +167,10 @@ let commandInfo = reactive<Command.CommandOperate>({
|
|||||||
command: '',
|
command: '',
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const commandReq = reactive({
|
||||||
|
name: '',
|
||||||
|
});
|
||||||
|
|
||||||
const cmdVisible = ref<boolean>(false);
|
const cmdVisible = ref<boolean>(false);
|
||||||
|
|
||||||
const loadGroups = async () => {
|
const loadGroups = async () => {
|
||||||
@@ -274,6 +285,7 @@ const search = async (column?: any) => {
|
|||||||
info: info.value,
|
info: info.value,
|
||||||
orderBy: paginationConfig.orderBy,
|
orderBy: paginationConfig.orderBy,
|
||||||
order: paginationConfig.order,
|
order: paginationConfig.order,
|
||||||
|
name: commandReq.name,
|
||||||
};
|
};
|
||||||
loading.value = true;
|
loading.value = true;
|
||||||
await getCommandPage(params)
|
await getCommandPage(params)
|
||||||
|
|||||||
@@ -105,7 +105,7 @@
|
|||||||
<span v-if="node.label.length <= 25">
|
<span v-if="node.label.length <= 25">
|
||||||
<a @click="onClickConn(node, data)">{{ node.label }}</a>
|
<a @click="onClickConn(node, data)">{{ node.label }}</a>
|
||||||
</span>
|
</span>
|
||||||
<el-tooltip v-else :content="node.label" placement="top-start">
|
<el-tooltip v-else :content="node.label" placement="right">
|
||||||
<span>
|
<span>
|
||||||
<a @click="onClickConn(node, data)">
|
<a @click="onClickConn(node, data)">
|
||||||
{{ node.label.substring(0, 22) }}...
|
{{ node.label.substring(0, 22) }}...
|
||||||
|
|||||||
@@ -126,7 +126,6 @@ const proxyForm = ref<FormInstance>();
|
|||||||
const rules = ref({
|
const rules = ref({
|
||||||
name: [Rules.requiredInput, Rules.appName],
|
name: [Rules.requiredInput, Rules.appName],
|
||||||
match: [Rules.requiredInput],
|
match: [Rules.requiredInput],
|
||||||
modifier: [Rules.requiredInput],
|
|
||||||
cacheTime: [Rules.requiredInput, checkNumberRange(1, 65535)],
|
cacheTime: [Rules.requiredInput, checkNumberRange(1, 65535)],
|
||||||
proxyPass: [Rules.requiredInput],
|
proxyPass: [Rules.requiredInput],
|
||||||
proxyHost: [Rules.requiredInput],
|
proxyHost: [Rules.requiredInput],
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
<template>
|
<template>
|
||||||
<div>
|
<div>
|
||||||
<el-form-item :label="$t('website.rewriteMode')">
|
<el-form-item :label="$t('website.rewriteMode')">
|
||||||
<el-select v-model="req.name" filterable @change="getRewriteConfig(req.name)">
|
<el-select v-model="req.name" filterable @change="getRewriteConfig(req.name)" class="p-w-200">
|
||||||
<el-option :label="$t('website.current')" :value="'current'"></el-option>
|
<el-option :label="$t('website.current')" :value="'current'"></el-option>
|
||||||
<el-option
|
<el-option
|
||||||
v-for="(rewrite, index) in Rewrites"
|
v-for="(rewrite, index) in Rewrites"
|
||||||
@@ -11,6 +11,7 @@
|
|||||||
></el-option>
|
></el-option>
|
||||||
</el-select>
|
</el-select>
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
|
<el-text type="warning">{{ $t('website.rewriteHelper2') }}</el-text>
|
||||||
<Codemirror
|
<Codemirror
|
||||||
ref="codeRef"
|
ref="codeRef"
|
||||||
v-loading="loading"
|
v-loading="loading"
|
||||||
@@ -26,7 +27,7 @@
|
|||||||
:extensions="extensions"
|
:extensions="extensions"
|
||||||
v-model="content"
|
v-model="content"
|
||||||
/>
|
/>
|
||||||
<div style="margin-top: 10px">
|
<div class="mt-2">
|
||||||
<el-form-item>
|
<el-form-item>
|
||||||
<el-alert :title="$t('website.rewriteHelper')" type="info" :closable="false" />
|
<el-alert :title="$t('website.rewriteHelper')" type="info" :closable="false" />
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
|
|||||||
@@ -349,7 +349,7 @@ import { ElForm, FormInstance } from 'element-plus';
|
|||||||
import { reactive, ref } from 'vue';
|
import { reactive, ref } from 'vue';
|
||||||
import Params from '@/views/app-store/detail/params/index.vue';
|
import Params from '@/views/app-store/detail/params/index.vue';
|
||||||
import Check from '../check/index.vue';
|
import Check from '../check/index.vue';
|
||||||
import { MsgSuccess } from '@/utils/message';
|
import { MsgError, MsgSuccess } from '@/utils/message';
|
||||||
import { GetGroupList } from '@/api/modules/group';
|
import { GetGroupList } from '@/api/modules/group';
|
||||||
import { Group } from '@/api/interface/group';
|
import { Group } from '@/api/interface/group';
|
||||||
import { SearchRuntimes } from '@/api/modules/runtime';
|
import { SearchRuntimes } from '@/api/modules/runtime';
|
||||||
@@ -582,6 +582,16 @@ const changeAppType = (type: string) => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
function isSubsetOfStrArray(primaryDomain: string, otherDomains: string): boolean {
|
||||||
|
const arr: string[] = otherDomains.split('\n');
|
||||||
|
for (const item of arr) {
|
||||||
|
if (primaryDomain === item) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
const submit = async (formEl: FormInstance | undefined) => {
|
const submit = async (formEl: FormInstance | undefined) => {
|
||||||
if (!formEl) return;
|
if (!formEl) return;
|
||||||
await formEl.validate((valid) => {
|
await formEl.validate((valid) => {
|
||||||
@@ -589,6 +599,12 @@ const submit = async (formEl: FormInstance | undefined) => {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
loading.value = true;
|
loading.value = true;
|
||||||
|
const flag = isSubsetOfStrArray(website.value.primaryDomain, website.value.otherDomains);
|
||||||
|
if (!flag) {
|
||||||
|
MsgError(i18n.global.t('website.containWarn'));
|
||||||
|
loading.value = false;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
PreCheck({})
|
PreCheck({})
|
||||||
.then((res) => {
|
.then((res) => {
|
||||||
if (res.data) {
|
if (res.data) {
|
||||||
|
|||||||
@@ -111,11 +111,12 @@
|
|||||||
</el-button>
|
</el-button>
|
||||||
</template>
|
</template>
|
||||||
</el-table-column>
|
</el-table-column>
|
||||||
<el-table-column :label="$t('website.remark')" prop="remark" min-width="120px">
|
<el-table-column
|
||||||
<template #default="{ row }">
|
:label="$t('website.remark')"
|
||||||
<MsgInfo :info="row.remark" />
|
prop="remark"
|
||||||
</template>
|
show-overflow-tooltip
|
||||||
</el-table-column>
|
min-width="120px"
|
||||||
|
></el-table-column>
|
||||||
<el-table-column
|
<el-table-column
|
||||||
:label="$t('commons.table.protocol')"
|
:label="$t('commons.table.protocol')"
|
||||||
prop="protocol"
|
prop="protocol"
|
||||||
@@ -194,7 +195,6 @@ import { dateFormatSimple } from '@/utils/util';
|
|||||||
import { MsgSuccess } from '@/utils/message';
|
import { MsgSuccess } from '@/utils/message';
|
||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import { VideoPlay, VideoPause } from '@element-plus/icons-vue';
|
import { VideoPlay, VideoPause } from '@element-plus/icons-vue';
|
||||||
import MsgInfo from '@/components/msg-info/index.vue';
|
|
||||||
import { GetGroupList } from '@/api/modules/group';
|
import { GetGroupList } from '@/api/modules/group';
|
||||||
import { Group } from '@/api/interface/group';
|
import { Group } from '@/api/interface/group';
|
||||||
import { GlobalStore } from '@/store';
|
import { GlobalStore } from '@/store';
|
||||||
|
|||||||
Reference in New Issue
Block a user