From e81040a39cdff3317e72fe160f5cfefcfff8c721 Mon Sep 17 00:00:00 2001 From: zhengkunwang223 <1paneldev@sina.com> Date: Mon, 30 Mar 2026 11:12:39 +0800 Subject: [PATCH] feat: support remark for openclaw --- agent/app/api/v2/agents.go | 20 +++++++++++++++++++ agent/app/dto/agents.go | 7 +++++++ agent/app/model/agent.go | 1 + agent/app/service/agents.go | 11 ++++++++++ agent/app/service/agents_utils.go | 1 + agent/init/migration/migrate.go | 1 + agent/init/migration/migrations/init.go | 7 +++++++ agent/router/ro_ai.go | 1 + frontend/src/api/interface/ai.ts | 7 +++++++ frontend/src/api/modules/ai.ts | 4 ++++ .../src/views/ai/agents/agent/add/index.vue | 6 ++++++ frontend/src/views/ai/agents/agent/index.vue | 20 ++++++++++++++++++- 12 files changed, 85 insertions(+), 1 deletion(-) diff --git a/agent/app/api/v2/agents.go b/agent/app/api/v2/agents.go index a06e849223af..fc2cc117c786 100644 --- a/agent/app/api/v2/agents.go +++ b/agent/app/api/v2/agents.go @@ -91,6 +91,26 @@ func (b *BaseApi) ResetAgentToken(c *gin.Context) { helper.Success(c) } +// @Tags AI +// @Summary Update Agent remark +// @Accept json +// @Param request body dto.AgentRemarkUpdateReq true "request" +// @Success 200 +// @Security ApiKeyAuth +// @Security Timestamp +// @Router /ai/agents/remark [post] +func (b *BaseApi) UpdateAgentRemark(c *gin.Context) { + var req dto.AgentRemarkUpdateReq + if err := helper.CheckBindAndValidate(&req, c); err != nil { + return + } + if err := agentService.UpdateRemark(req); err != nil { + helper.BadRequest(c, err) + return + } + helper.Success(c) +} + // @Tags AI // @Summary Update Agent model config // @Accept json diff --git a/agent/app/dto/agents.go b/agent/app/dto/agents.go index 4a6b3bb4835f..e23522723275 100644 --- a/agent/app/dto/agents.go +++ b/agent/app/dto/agents.go @@ -4,6 +4,7 @@ import "time" type AgentCreateReq struct { Name string `json:"name" validate:"required"` + Remark string `json:"remark"` AppVersion string `json:"appVersion" validate:"required"` WebUIPort int `json:"webUIPort" validate:"required"` BridgePort int `json:"bridgePort"` @@ -29,6 +30,7 @@ type AgentCreateReq struct { type AgentItem struct { ID uint `json:"id"` Name string `json:"name"` + Remark string `json:"remark"` AgentType string `json:"agentType"` Provider string `json:"provider"` ProviderName string `json:"providerName"` @@ -63,6 +65,11 @@ type AgentTokenResetReq struct { ID uint `json:"id" validate:"required"` } +type AgentRemarkUpdateReq struct { + ID uint `json:"id" validate:"required"` + Remark string `json:"remark"` +} + type AgentModelConfigUpdateReq struct { AgentID uint `json:"agentId" validate:"required"` AccountID uint `json:"accountId" validate:"required"` diff --git a/agent/app/model/agent.go b/agent/app/model/agent.go index fa382e7084d9..f0aa923c1a40 100644 --- a/agent/app/model/agent.go +++ b/agent/app/model/agent.go @@ -3,6 +3,7 @@ package model type Agent struct { BaseModel Name string `json:"name" gorm:"not null;unique"` + Remark string `json:"remark"` AgentType string `json:"agentType" gorm:"default:openclaw"` Provider string `json:"provider"` Model string `json:"model"` diff --git a/agent/app/service/agents.go b/agent/app/service/agents.go index 2aa2273258f1..3164ee550d4c 100644 --- a/agent/app/service/agents.go +++ b/agent/app/service/agents.go @@ -29,6 +29,7 @@ type IAgentService interface { Page(req dto.SearchWithPage) (int64, []dto.AgentItem, error) Delete(req dto.AgentDeleteReq) error ResetToken(req dto.AgentTokenResetReq) error + UpdateRemark(req dto.AgentRemarkUpdateReq) error UpdateModelConfig(req dto.AgentModelConfigUpdateReq) error GetOverview(req dto.AgentOverviewReq) (*dto.AgentOverview, error) GetProviders() ([]dto.ProviderInfo, error) @@ -234,6 +235,7 @@ func (a AgentService) Create(req dto.AgentCreateReq) (*dto.AgentItem, error) { } agent := &model.Agent{ Name: req.Name, + Remark: req.Remark, AgentType: agentType, Provider: provider, Model: storedModel, @@ -323,6 +325,15 @@ func (a AgentService) ResetToken(req dto.AgentTokenResetReq) error { return agentRepo.Save(agent) } +func (a AgentService) UpdateRemark(req dto.AgentRemarkUpdateReq) error { + agent, err := agentRepo.GetFirst(repo.WithByID(req.ID)) + if err != nil { + return err + } + agent.Remark = req.Remark + return agentRepo.Save(agent) +} + func (a AgentService) UpdateModelConfig(req dto.AgentModelConfigUpdateReq) error { agent, err := loadOpenclawAgentByID(req.AgentID) if err != nil { diff --git a/agent/app/service/agents_utils.go b/agent/app/service/agents_utils.go index 7d5c2f5635ce..6a13fa82400e 100644 --- a/agent/app/service/agents_utils.go +++ b/agent/app/service/agents_utils.go @@ -340,6 +340,7 @@ func buildAgentItem(agent *model.Agent, appInstall *model.AppInstall, envMap map item := dto.AgentItem{ ID: agent.ID, Name: agent.Name, + Remark: agent.Remark, AgentType: agentType, Provider: agent.Provider, ProviderName: providercatalog.DisplayName(agent.Provider), diff --git a/agent/init/migration/migrate.go b/agent/init/migration/migrate.go index 5dc97f3f4145..920f58a9ca0b 100644 --- a/agent/init/migration/migrate.go +++ b/agent/init/migration/migrate.go @@ -77,6 +77,7 @@ func InitAgentDB() { migrations.AddAITerminalSettings, migrations.UpdateAgentQuickJumpTitle, migrations.FixOpenclaw20260323HTTPPort, + migrations.AddAgentRemarkColumn, }) if err := m.Migrate(); err != nil { global.LOG.Error(err) diff --git a/agent/init/migration/migrations/init.go b/agent/init/migration/migrations/init.go index 0cbfed26faba..4ee55a676540 100644 --- a/agent/init/migration/migrations/init.go +++ b/agent/init/migration/migrations/init.go @@ -1151,3 +1151,10 @@ WHERE version = ? ).Error }, } + +var AddAgentRemarkColumn = &gormigrate.Migration{ + ID: "20260330-add-agent-remark-column", + Migrate: func(tx *gorm.DB) error { + return tx.AutoMigrate(&model.Agent{}) + }, +} diff --git a/agent/router/ro_ai.go b/agent/router/ro_ai.go index 5aade3056e3a..0230b51fc599 100644 --- a/agent/router/ro_ai.go +++ b/agent/router/ro_ai.go @@ -44,6 +44,7 @@ func (a *AIToolsRouter) InitRouter(Router *gin.RouterGroup) { aiToolsRouter.POST("/agents/search", baseApi.PageAgents) aiToolsRouter.POST("/agents/delete", baseApi.DeleteAgent) aiToolsRouter.POST("/agents/token/reset", baseApi.ResetAgentToken) + aiToolsRouter.POST("/agents/remark", baseApi.UpdateAgentRemark) aiToolsRouter.POST("/agents/model/update", baseApi.UpdateAgentModelConfig) aiToolsRouter.POST("/agents/overview", baseApi.GetAgentOverview) aiToolsRouter.GET("/agents/providers", baseApi.GetAgentProviders) diff --git a/frontend/src/api/interface/ai.ts b/frontend/src/api/interface/ai.ts index aafaf4bc8028..70ec1459233b 100644 --- a/frontend/src/api/interface/ai.ts +++ b/frontend/src/api/interface/ai.ts @@ -238,6 +238,7 @@ export namespace AI { export interface AgentCreateReq { name: string; + remark: string; appVersion: string; webUIPort: number; bridgePort?: number; @@ -263,6 +264,7 @@ export namespace AI { export interface AgentItem { id: number; name: string; + remark: string; agentType: 'openclaw' | 'copaw'; provider: string; providerName: string; @@ -297,6 +299,11 @@ export namespace AI { id: number; } + export interface AgentRemarkUpdateReq { + id: number; + remark: string; + } + export interface AgentModelConfigUpdateReq { agentId: number; accountId: number; diff --git a/frontend/src/api/modules/ai.ts b/frontend/src/api/modules/ai.ts index 5c8c37125eb8..fdd6d50daf40 100644 --- a/frontend/src/api/modules/ai.ts +++ b/frontend/src/api/modules/ai.ts @@ -109,6 +109,10 @@ export const resetAgentToken = (req: AI.AgentTokenResetReq) => { return http.post(`/ai/agents/token/reset`, req); }; +export const updateAgentRemark = (req: AI.AgentRemarkUpdateReq) => { + return http.post(`/ai/agents/remark`, req); +}; + export const updateAgentModelConfig = (req: AI.AgentModelConfigUpdateReq) => { return http.post(`/ai/agents/model/update`, req); }; diff --git a/frontend/src/views/ai/agents/agent/add/index.vue b/frontend/src/views/ai/agents/agent/add/index.vue index cb86fef34661..3cf09d6e19be 100644 --- a/frontend/src/views/ai/agents/agent/add/index.vue +++ b/frontend/src/views/ai/agents/agent/add/index.vue @@ -5,6 +5,9 @@ + + + @@ -136,6 +139,7 @@ const { isIntl } = useGlobalStore(); const form = reactive({ name: '', + remark: '', agentType: 'openclaw' as 'openclaw' | 'copaw', appVersion: '', webUIPort: 18789, @@ -382,6 +386,7 @@ const submit = async () => { try { const res = await createAgent({ name: form.name, + remark: form.remark, appVersion: form.appVersion, webUIPort: form.webUIPort, allowedOrigins: form.agentType === 'openclaw' ? parseAllowedOriginsInput(form.allowedOrigins) : undefined, @@ -419,6 +424,7 @@ const submit = async () => { const handleClose = () => { formRef.value?.resetFields(); form.token = ''; + form.remark = ''; form.allowedOrigins = ''; form.dockerCompose = ''; lastAutoAllowedOrigins.value = ''; diff --git a/frontend/src/views/ai/agents/agent/index.vue b/frontend/src/views/ai/agents/agent/index.vue index 0ebceb5bdfdb..ea93bfcb0818 100644 --- a/frontend/src/views/ai/agents/agent/index.vue +++ b/frontend/src/views/ai/agents/agent/index.vue @@ -101,6 +101,18 @@ + + +