Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 1 addition & 5 deletions core/app/api/v2/command.go
Original file line number Diff line number Diff line change
Expand Up @@ -137,11 +137,7 @@ func (b *BaseApi) UpdateCommand(c *gin.Context) {
return
}

upMap := make(map[string]interface{})
upMap["name"] = req.Name
upMap["group_id"] = req.GroupID
upMap["command"] = req.Command
if err := commandService.Update(req.ID, upMap); err != nil {
if err := commandService.Update(req); err != nil {
helper.InternalServer(c, err)
return
}
Expand Down
7 changes: 4 additions & 3 deletions core/app/dto/logs.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@ import (
)

type OperationLog struct {
ID uint `json:"id"`
Source string `json:"source"`

ID uint `json:"id"`
Source string `json:"source"`
Node string `json:"node"`
IP string `json:"ip"`
Path string `json:"path"`
Method string `json:"method"`
Expand All @@ -26,6 +26,7 @@ type SearchOpLogWithPage struct {
PageInfo
Source string `json:"source"`
Status string `json:"status"`
Node string `json:"node"`
Operation string `json:"operation"`
}

Expand Down
1 change: 1 addition & 0 deletions core/app/model/logs.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ type OperationLog struct {
BaseModel
Source string `json:"source"`
IP string `json:"ip"`
Node string `json:"node"`
Path string `json:"path"`
Method string `json:"method"`
UserAgent string `json:"userAgent"`
Expand Down
5 changes: 5 additions & 0 deletions core/app/repo/common.go
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,11 @@ func WithByStatus(status string) global.DBOption {
return g.Where("status = ?", status)
}
}
func WithByNode(node string) global.DBOption {
return func(g *gorm.DB) *gorm.DB {
return g.Where("node = ?", node)
}
}
func WithByGroupBelong(group string) global.DBOption {
return func(g *gorm.DB) *gorm.DB {
return g.Where("group_belong = ?", group)
Expand Down
14 changes: 11 additions & 3 deletions core/app/service/command.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ type ICommandService interface {
SearchForTree(req dto.OperateByType) ([]dto.CommandTree, error)
SearchWithPage(search dto.SearchCommandWithPage) (int64, interface{}, error)
Create(req dto.CommandOperate) error
Update(id uint, upMap map[string]interface{}) error
Update(req dto.CommandOperate) error
Delete(ids []uint) error
}

Expand Down Expand Up @@ -123,6 +123,14 @@ func (u *CommandService) Delete(ids []uint) error {
return commandRepo.Delete(repo.WithByIDs(ids))
}

func (u *CommandService) Update(id uint, upMap map[string]interface{}) error {
return commandRepo.Update(id, upMap)
func (u *CommandService) Update(req dto.CommandOperate) error {
command, _ := commandRepo.Get(repo.WithByName(req.Name), repo.WithByType(req.Type))
if command.ID != req.ID {
return buserr.New("ErrRecordExist")
}
upMap := make(map[string]interface{})
upMap["name"] = req.Name
upMap["group_id"] = req.GroupID
upMap["command"] = req.Command
return commandRepo.Update(req.ID, upMap)
}
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The code seems to be correct with minor changes. The primary difference is that Update method now takes a req dto.CommandOperate instead of id uint, upMap map[string]interface{}. This change allows easier validation before updating the record using Get. However, it's important to ensure that this does not introduce security vulnerabilities by directly manipulating user input in query conditions without proper sanitization.

Additionally, there are redundant fields added while performing updates ("group_id", "command"), which might not always be needed depending on how your application handles these data. It would be cleaner if these were conditionally added based on whether the fields exist within the request.

Lastly, the use of _ = commandRepo.Get(...) ignores an optional error (from repo.WithByName or others), but this could potentially indicate a failure in retrieving records under certain scenarios. Depending on your needs, you might want to handle these errors.

Overall, despite these optimizations, the existing implementation appears to work correctly and maintainable with appropriate checks in place to reduce risk and improve robustness.

3 changes: 3 additions & 0 deletions core/app/service/logs.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,9 @@ func (u *LogService) PageOperationLog(req dto.SearchOpLogWithPage) (int64, inter
if len(req.Status) != 0 {
options = append(options, repo.WithByStatus(req.Status))
}
if len(req.Node) != 0 {
options = append(options, repo.WithByNode(req.Node))
}

total, ops, err := logRepo.PageOperationLog(
req.Page,
Expand Down
4 changes: 1 addition & 3 deletions core/i18n/i18n.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ package i18n

import (
"embed"
"fmt"
"strings"

"github.com/1Panel-dev/1Panel/core/global"
Expand Down Expand Up @@ -65,10 +64,9 @@ func GetErrMsg(key string, maps map[string]interface{}) string {
}

func GetMsgByKey(key string) string {
content, err := global.I18n.Localize(&i18n.LocalizeConfig{
content, _ := global.I18n.Localize(&i18n.LocalizeConfig{
MessageID: key,
})
fmt.Println(err)
return content
}

Expand Down
1 change: 1 addition & 0 deletions core/init/migration/migrate.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ func Init() {
migrations.UpdateXpackHideMemu,
migrations.AddSystemIP,
migrations.InitScriptLibrary,
migrations.AddOperationNode,
})
if err := m.Migrate(); err != nil {
global.LOG.Error(err)
Expand Down
10 changes: 10 additions & 0 deletions core/init/migration/migrations/init.go
Original file line number Diff line number Diff line change
Expand Up @@ -339,3 +339,13 @@ var InitScriptLibrary = &gormigrate.Migration{
return nil
},
}

var AddOperationNode = &gormigrate.Migration{
ID: "20250321-add-operation-node",
Migrate: func(tx *gorm.DB) error {
if err := tx.AutoMigrate(&model.OperationLog{}); err != nil {
return err
}
return nil
},
}
2 changes: 2 additions & 0 deletions core/middleware/operation.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,10 @@ func OperationLog() gin.HandlerFunc {
source := loadLogInfo(c.Request.URL.Path)
pathItem := strings.TrimPrefix(c.Request.URL.Path, "/api/v2")
pathItem = strings.TrimPrefix(pathItem, "/api/v2/core")
currentNode := c.Request.Header.Get("CurrentNode")
record := &model.OperationLog{
Source: source,
Node: currentNode,
IP: c.ClientIP(),
Method: strings.ToLower(c.Request.Method),
Path: pathItem,
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/components/log/custom-hightlight/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,7 @@ const systemRules: TokenRule[] = [
const taskRules: TokenRule[] = [
{
type: 'bracket-text',
pattern: /\[([^\]]+)\]/g,
pattern: /\[([^\,]]+)\]/g,
color: '#B87A2B',
},
];
Expand Down
3 changes: 2 additions & 1 deletion frontend/src/components/system-upgrade/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,12 @@
v-if="version !== 'Waiting' && !globalStore.hasNewVersion"
type="primary"
:underline="false"
class="ml-2"
@click="onLoadUpgradeInfo"
>
{{ $t('commons.button.update') }}
</el-link>
<el-tag v-if="version === 'Waiting'" round style="margin-left: 10px">
<el-tag v-if="version === 'Waiting'" round class="ml-2.5">
{{ $t('setting.upgrading') }}
</el-tag>
</div>
Expand Down
22 changes: 13 additions & 9 deletions frontend/src/layout/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -7,15 +7,19 @@
@mouseenter="collapseButtonShow = true"
@mouseleave="collapseButtonShow = false"
>
<el-affix v-if="collapseButtonShow" :offset="124" class="affix">
<el-button
size="small"
circle
:style="{ 'margin-left': menuStore.isCollapse ? '60px' : '165px', position: 'absolute' }"
:icon="menuStore.isCollapse ? 'ArrowRight' : 'ArrowLeft'"
plain
@click="handleCollapse()"
></el-button>
<el-affix v-if="collapseButtonShow" :offset="18" class="affix">
<el-tooltip
:content="menuStore.isCollapse ? $t('commons.button.expand') : $t('commons.button.collapse')"
>
<el-button
size="small"
circle
:style="{ 'margin-left': menuStore.isCollapse ? '60px' : '165px', position: 'absolute' }"
:icon="menuStore.isCollapse ? 'ArrowRight' : 'ArrowLeft'"
plain
@click="handleCollapse()"
></el-button>
</el-tooltip>
</el-affix>
<Sidebar @menu-click="handleMenuClick" :menu-router="!classObj.openMenuTabs" @open-task="openTask" />
</div>
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The provided patch contains several changes and optimizations:

  1. Tooltip Replacement: The button was replaced with an el-tooltip component to display a tooltip when hovering over the collapse/collapse icon.

  2. Content Translation: A translation string $t('commons.button.expand') and $t('commons.button.collapse') are used to dynamically set the tooltip text. This makes the code more internationalizable if needed.

  3. Minor Padding Adjustment: The margin on the left of the collapse/button has been adjusted from '165px' to '60px'. You might want to re-evaluate this based on your design requirements or layout needs.

Here is the updated snippet:

@@ -7,15 +7,19 @@
             @mouseenter="collapseButtonShow = true"
             @mouseleave="collapseButtonShow = false"
         >
-            <el-affix v-if="collapseButtonShow" :offset="124" class="affix">
-                <el-button
-                    size="small"
-                    circle
-                    :style="{ 'margin-left': menuStore.isCollapse ? '60px' : '165px', position: 'absolute' }"
-                    :icon="menuStore.isCollapse ? 'ArrowRight' : 'ArrowLeft'"
-                    plain
-                    @click="handleCollapse()"
-                ></el-button>
+            <el-affix v-if="collapseButtonShow" :offset="18" class="affix">
+                <el-tooltip
+                    :content="$t('commons.button.' + (menuStore.isCollapse ? 'expand' : 'collapse'))"
+                 >
+                     <el-button
+                         size="small"
+                         circle
+                         :style="{ 'margin-left': menuStore.isCollapse ? '60px' : '165px', position: 'absolute' }"
+                         :icon="menuStore.isCollapse ? 'ArrowRight' : 'ArrowLeft'"
+                         plain
+                         @click="handleCollapse()"
+                     ></el-button>
+                 </el-tooltip>
             </el-affix>
             <Sidebar @menu-click="handleMenuClick" :menu-router="!classObj.openMenuTabs" @open-task="openTask" />

Potential Issues:

  1. Hover Effect Conflicts: If there are other parts of your application that rely on mouse hover effects, ensure this change does not interfere with them.
  2. Accessibility: Ensure proper accessibility for users who may have trouble reading tooltips directly on icons.

Optimization Suggestions:

  • None significant changes were made in terms of performance optimization beyond minor adjustments and translations. However, ensure any globalizations or localization strategies are properly managed in your project.

Expand Down
1 change: 1 addition & 0 deletions frontend/src/views/cronjob/cronjob/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
@sort-change="search"
@search="search"
:data="data"
:heightDiff="300"
>
<el-table-column type="selection" fix />
<el-table-column
Expand Down
1 change: 0 additions & 1 deletion frontend/src/views/cronjob/cronjob/record/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -387,7 +387,6 @@ const forDetail = async (row: Cronjob.Record) => {
};
const loadRecord = async (row: Cronjob.Record) => {
currentRecord.value = row;
console.log(currentRecord.value);
if (row.records) {
const res = await getRecordLog(row.id);
let log = res.data.replace(/\x1B\[[0-?]*[ -/]*[@-~]/g, '');
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/views/cronjob/library/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@
:pagination-config="paginationConfig"
:data="data"
@search="search"
:heightDiff="370"
:heightDiff="300"
>
<el-table-column type="selection" fix />
<el-table-column :label="$t('commons.table.name')" show-overflow-tooltip prop="name" min-width="60">
Expand Down
1 change: 1 addition & 0 deletions frontend/src/views/cronjob/library/operate/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ const onSubmit = async (formEl: FormInstance | undefined) => {
formEl.validate(async (valid) => {
if (!valid) return;
loading.value = true;
dialogData.value.rowData.groupList = dialogData.value.rowData.groupList || [];
dialogData.value.rowData.groups = dialogData.value.rowData.groupList.join(',');
if (dialogData.value.title === 'create') {
await addScript(dialogData.value.rowData)
Expand Down
6 changes: 5 additions & 1 deletion frontend/src/views/database/postgresql/setting/index.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
<template>
<div v-loading="loading">
<LayoutContent :title="props.database + ' ' + $t('commons.button.set')" backName="PostgreSQL">
<LayoutContent backName="PostgreSQL">
<template #leftToolBar>
<el-text class="mx-1">
{{ props.database }}
</el-text>
<el-divider direction="vertical" />
<el-button type="primary" :plain="activeName !== 'conf'" @click="jumpToConf">
{{ $t('database.confChange') }}
</el-button>
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/views/database/redis/remote/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -156,7 +156,7 @@ const buttons = [
},
},
{
label: i18n.global.t('commons.button.delete'),
label: i18n.global.t('commons.button.unbind'),
click: (row: Database.DatabaseInfo) => {
onDelete(row);
},
Expand Down
6 changes: 5 additions & 1 deletion frontend/src/views/database/redis/setting/index.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
<template>
<div v-show="settingShow" v-loading="loading">
<LayoutContent :title="database + ' ' + $t('commons.button.set')" :reload="true">
<LayoutContent :reload="true">
<template #leftToolBar>
<el-text class="mx-1">
{{ database }}
</el-text>
<el-divider direction="vertical" />
<el-button type="primary" :plain="activeName !== 'conf'" @click="changeTab('conf')">
{{ $t('database.confChange') }}
</el-button>
Expand Down
42 changes: 38 additions & 4 deletions frontend/src/views/log/operation/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
</el-button>
</template>
<template #rightToolBar>
<el-select v-model="searchGroup" @change="search()" clearable class="p-w-200 mr-2.5">
<el-select v-model="searchGroup" @change="search()" clearable class="p-w-200">
<template #prefix>{{ $t('logs.resource') }}</template>
<el-option :label="$t('commons.table.all')" value=""></el-option>
<el-option :label="$t('logs.detail.apps')" value="apps"></el-option>
Expand All @@ -25,12 +25,18 @@
<el-option :label="$t('logs.detail.logs')" value="logs"></el-option>
<el-option :label="$t('logs.detail.settings')" value="settings"></el-option>
</el-select>
<el-select v-model="searchStatus" @change="search()" clearable class="p-w-200 mr-2.5">
<template #prefix>{{ $t('commons.table.status') }}</template>
<el-select v-model="searchStatus" @change="search()" clearable class="p-w-200">
<template #prefix>{{ $t('xpack.node.node') }}</template>
<el-option :label="$t('commons.table.all')" value=""></el-option>
<el-option :label="$t('commons.status.success')" value="Success"></el-option>
<el-option :label="$t('commons.status.failed')" value="Failed"></el-option>
</el-select>
<el-select v-model="searchNode" @change="search()" clearable class="p-w-200">
<template #prefix>{{ $t('xpack.node.node') }}</template>
<el-option :label="$t('commons.table.all')" value=""></el-option>
<el-option :label="$t('xpack.node.master')" value="local" />
<el-option v-for="(node, index) in nodes" :key="index" :label="node.name" :value="node.name" />
</el-select>
<TableSearch @search="search()" v-model:searchName="searchName" />
<TableRefresh @search="search()" />
<TableSetting title="operation-log-refresh" @search="search()" />
Expand All @@ -52,7 +58,11 @@
<span v-if="globalStore.language === 'en'">{{ row.detailEN }}</span>
</template>
</el-table-column>

<el-table-column v-if="globalStore.isMasterProductPro" :label="$t('xpack.node.node')" prop="node">
<template #default="{ row }">
<span>{{ row.node === 'local' ? $t('xpack.node.master') : row.node }}</span>
</template>
</el-table-column>
<el-table-column :label="$t('commons.table.status')" prop="status">
<template #default="{ row }">
<Status :status="row.status" :msg="row.message" />
Expand Down Expand Up @@ -81,6 +91,7 @@ import { onMounted, reactive, ref } from '@vue/runtime-core';
import i18n from '@/lang';
import { MsgSuccess } from '@/utils/message';
import { GlobalStore } from '@/store';
import { listNodeOptions } from '@/api/modules/setting';

const loading = ref();
const data = ref();
Expand All @@ -94,6 +105,8 @@ const paginationConfig = reactive({
const searchName = ref<string>('');
const searchGroup = ref<string>('');
const searchStatus = ref<string>('');
const searchNode = ref<string>('');
const nodes = ref();

const globalStore = GlobalStore();

Expand All @@ -104,6 +117,7 @@ const search = async () => {
pageSize: paginationConfig.pageSize,
status: searchStatus.value,
source: searchGroup.value,
node: searchNode.value,
};
loading.value = true;
await getOperationLogs(params)
Expand Down Expand Up @@ -140,6 +154,23 @@ const loadDetail = (log: string) => {
return log;
};

const loadNodes = async () => {
await listNodeOptions()
.then((res) => {
if (!res) {
nodes.value = [];
return;
}
nodes.value = res.data || [];
if (nodes.value.length === 0) {
globalStore.currentNode = 'local';
}
})
.catch(() => {
nodes.value = [];
});
};

const replacements = {
'[enable]': 'commons.button.enable',
'[Enable]': 'commons.button.enable',
Expand Down Expand Up @@ -172,6 +203,9 @@ const onSubmitClean = async () => {
};

onMounted(() => {
if (globalStore.isMasterProductPro) {
loadNodes();
}
search();
});
</script>
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The changes made to the code appear to be improving its functionality and localization support. Some key improvements include:

  1. Localization Enhancements: Added $t usages throughout the code for better internationalization. This aligns with best practices for Vue.js applications using Internationalization (i18n).

  2. Additional Column: Introduced a new column for showing which instance a log belongs to (xpack.node.node). This is likely relevant when dealing with multi-node environments.

  3. Fetching Node Options: Moved the logic to fetch node options into loadNodes, ensuring it only runs when necessary (only applicable in certain contexts). Also adjusted how selected_node is set based on response handling.

These modifications help make the component more modular, maintainable, and user-friendly by enhancing the user experience with localized strings and additional informative columns.

Expand Down
9 changes: 8 additions & 1 deletion frontend/src/views/log/system/index.vue
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,12 @@
{{ $t('commons.button.watch') }}
</el-checkbox>
</el-button>
<el-radio-group class="ml-2" @change="search()" v-model="itemType">
<el-radio-group
v-if="globalStore.currentNode === 'local'"
class="ml-2"
@change="search()"
v-model="itemType"
>
<el-radio-button :label="$t('logs.agent')" value="Agent" />
<el-radio-button :label="$t('logs.core')" value="Core" />
</el-radio-group>
Expand All @@ -39,6 +44,8 @@ import LogFile from '@/components/log/file/index.vue';
import LogRouter from '@/views/log/router/index.vue';
import { nextTick, onMounted, reactive, ref } from 'vue';
import { getSystemFiles } from '@/api/modules/log';
import { GlobalStore } from '@/store';
const globalStore = GlobalStore();

const loading = ref();
const isWatch = ref();
Expand Down
2 changes: 2 additions & 0 deletions frontend/src/views/login/components/login-form.vue
Original file line number Diff line number Diff line change
Expand Up @@ -297,6 +297,8 @@ const agreeWithLogin = () => {

const login = (formEl: FormInstance | undefined) => {
if (!formEl || isLoggingIn) return;
errAuthInfo.value = false;
errCaptcha.value = false;
formEl.validate(async (valid) => {
if (!valid) return;
if (isIntl.value) {
Expand Down
Loading