From 82da2a1a04209e9ad00c6a3ca377518fac89f8ad Mon Sep 17 00:00:00 2001 From: hurole <1192163814@qq.com> Date: Thu, 8 Jan 2026 21:39:52 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E4=BC=98=E5=8C=96=E6=97=A5=E5=BF=97?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- apps/server/libs/gitea.ts | 4 +- apps/server/libs/pipeline-template.ts | 10 +- apps/server/prisma/data/dev.db | Bin 53248 -> 53248 bytes apps/server/runners/pipeline-runner.ts | 110 ++++++------------ apps/web/src/pages/project/detail/index.tsx | 1 - apps/web/src/pages/project/detail/service.ts | 5 +- .../list/components/CreateProjectModal.tsx | 8 +- 7 files changed, 49 insertions(+), 89 deletions(-) diff --git a/apps/server/libs/gitea.ts b/apps/server/libs/gitea.ts index e214638..f56152c 100644 --- a/apps/server/libs/gitea.ts +++ b/apps/server/libs/gitea.ts @@ -60,9 +60,7 @@ class Gitea { }), }); if (!response.ok) { - const payload = await response - .json() - .catch(() => null as unknown); + const payload = await response.json().catch(() => null as unknown); log.error( TAG, 'Gitea token request failed: status=%d payload=%o', diff --git a/apps/server/libs/pipeline-template.ts b/apps/server/libs/pipeline-template.ts index 590a2ce..7df9621 100644 --- a/apps/server/libs/pipeline-template.ts +++ b/apps/server/libs/pipeline-template.ts @@ -103,7 +103,10 @@ export async function initializePipelineTemplates(): Promise { log.info(TAG, `Created template: ${template.name}`); } } else { - log.info(TAG, 'Pipeline templates already exist, skipping initialization'); + log.info( + TAG, + 'Pipeline templates already exist, skipping initialization', + ); } log.info(TAG, 'Pipeline templates initialization completed'); @@ -208,7 +211,10 @@ export async function createPipelineFromTemplate( }); } - log.info(TAG, `Created pipeline from template ${templateId}: ${newPipeline.name}`); + log.info( + TAG, + `Created pipeline from template ${templateId}: ${newPipeline.name}`, + ); return newPipeline.id; } catch (error) { log.error(TAG, 'Failed to create pipeline from template:', error); diff --git a/apps/server/prisma/data/dev.db b/apps/server/prisma/data/dev.db index fec9b847aca3fd53e0113884d740c553a866e9d0..2dc1782d35592b65ef3e0ccb7bc2d9ff27e3b130 100644 GIT binary patch literal 53248 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 delta 467 zcmZozz}&Ead4e?WItB&?ULfWHV&;h&=8Wq$CM>h(JIu&`oBt*MXZ}n4hxs>b7F3wS zKY4?{kYNcg8?z#(OKL$*er0ZIUI{x3vnXe1acU6{BeN`HKxRQ|PG(*z3kMUkC}VI* zY617=&;B3yxecsLOsz}|^bAZaHouD(6OiKOP+;J@%@@pjpErs71h+lcDJ~z*aE>+( zh0THjOdRql+}sS>9KxLL?vj#>PxnrK+S&VTTKkjT+nz4jSx}xb*}g(;@`HS~$$k}l zlb0{&-P~4D$Iiycb(ewbF3^C>Tyk9sj3Nx8!qTxF`5mFW?(SfdI2m&jGxJhX%QpW$ z#mc&9f&drD>x^6v7`Pq)wO!-d{NR)Vs{l|81ekyrB+t27V8cqri4z(X+oZVI#Wgh< zyYovDlX6n?Qp@8JK>^}Tj%Si&0WmgLF!k_qF>?kp@I2-z;0y+u?#fA;{vc+qHYpBv uaYaSO?)u3AOp=V8le3sgH$P^2!^p3ol$uu-mRMA*q!8j75i { let logs = ''; - const timestamp = new Date().toISOString(); try { - logs += `[${timestamp}] 检查工作目录状态: ${this.projectDir}\n`; + logs += this.addTimestamp(`检查工作目录状态: ${this.projectDir}`); // 检查工作目录状态 const status = await GitManager.checkWorkspaceStatus(this.projectDir); - logs += `[${new Date().toISOString()}] 工作目录状态: ${status.status}\n`; + logs += this.addTimestamp(`工作目录状态: ${status.status}`); if ( status.status === WorkspaceDirStatus.NOT_CREATED || status.status === WorkspaceDirStatus.EMPTY ) { // 目录不存在或为空,需要克隆 - logs += `[${new Date().toISOString()}] 工作目录不存在或为空,开始克隆仓库\n`; + logs += this.addTimestamp('工作目录不存在或为空,开始克隆仓库'); // 确保父目录存在 await GitManager.ensureDirectory(this.projectDir); @@ -168,7 +165,7 @@ export class PipelineRunner { // TODO: 添加 token 支持 ); - logs += `[${new Date().toISOString()}] 仓库克隆成功\n`; + logs += this.addTimestamp('仓库克隆成功'); } else if (status.status === WorkspaceDirStatus.NO_GIT) { // 目录存在但不是 Git 仓库 throw new Error( @@ -176,14 +173,16 @@ export class PipelineRunner { ); } else if (status.status === WorkspaceDirStatus.READY) { // 已存在 Git 仓库,更新代码 - logs += `[${new Date().toISOString()}] 工作目录已存在 Git 仓库,开始更新代码\n`; + logs += this.addTimestamp('工作目录已存在 Git 仓库,开始更新代码'); await GitManager.updateRepository(this.projectDir, branch); - logs += `[${new Date().toISOString()}] 代码更新成功\n`; + logs += this.addTimestamp('代码更新成功'); } return logs; } catch (error) { - const errorLog = `[${new Date().toISOString()}] 准备工作目录失败: ${(error as Error).message}\n`; + const errorLog = this.addTimestamp( + `准备工作目录失败: ${(error as Error).message}`, + ); logs += errorLog; log.error( this.TAG, @@ -237,28 +236,9 @@ export class PipelineRunner { * @param isError 是否为错误日志 * @returns 带时间戳的日志消息 */ - private addTimestamp(message: string, isError = false): string { + private addTimestamp(message: string): string { const timestamp = new Date().toISOString(); - if (isError) { - return `[${timestamp}] [ERROR] ${message}`; - } - return `[${timestamp}] ${message}`; - } - - /** - * 为多行日志添加时间戳前缀 - * @param content 多行日志内容 - * @param isError 是否为错误日志 - * @returns 带时间戳的多行日志消息 - */ - private addTimestampToLines(content: string, isError = false): string { - if (!content) return ''; - - return `${content - .split('\n') - .filter((line) => line.trim() !== '') - .map((line) => this.addTimestamp(line, isError)) - .join('\n')}\n`; + return `[${timestamp}] [ERROR] ${message}\n`; } /** @@ -272,35 +252,21 @@ export class PipelineRunner { ): Promise { let logs = ''; - try { - // 添加步骤开始执行的时间戳 - logs += `${this.addTimestamp(`执行脚本: ${step.script}`)}\n`; + // 使用zx执行脚本,设置项目目录为工作目录和环境变量 + const script = step.script; - // 使用zx执行脚本,设置项目目录为工作目录和环境变量 - const script = step.script; + // bash -c 执行脚本,确保环境变量能被正确解析 + const result = await $({ + cwd: this.projectDir, + env: { ...process.env, ...envVars }, + })`bash -c ${script}`; - // 通过bash -c执行脚本,确保环境变量能被正确解析 - const result = await $({ - cwd: this.projectDir, - env: { ...process.env, ...envVars }, - })`bash -c ${script}`; + if (result.stdout) { + logs += this.addTimestamp(`\n${result.stdout}`); + } - if (result.stdout) { - // 为stdout中的每一行添加时间戳 - logs += this.addTimestampToLines(result.stdout); - } - - if (result.stderr) { - // 为stderr中的每一行添加时间戳和错误标记 - logs += this.addTimestampToLines(result.stderr, true); - } - - logs += `${this.addTimestamp(`步骤执行完成`)}\n`; - } catch (error) { - const errorMsg = `Error executing step "${step.name}": ${(error as Error).message}`; - logs += `${this.addTimestamp(errorMsg, true)}\n`; - log.error(this.TAG, errorMsg); - throw error; + if (result.stderr) { + logs += this.addTimestamp(`\n${result.stderr}`); } return logs; diff --git a/apps/web/src/pages/project/detail/index.tsx b/apps/web/src/pages/project/detail/index.tsx index 922764c..d2d2dc6 100644 --- a/apps/web/src/pages/project/detail/index.tsx +++ b/apps/web/src/pages/project/detail/index.tsx @@ -725,7 +725,6 @@ function ProjectDetailPage() { item={item} isSelected={selectedRecordId === item.id} onSelect={setSelectedRecordId} - onRetry={handleRetryDeployment} // 传递重新执行函数 /> ); diff --git a/apps/web/src/pages/project/detail/service.ts b/apps/web/src/pages/project/detail/service.ts index d2e2922..15b60d0 100644 --- a/apps/web/src/pages/project/detail/service.ts +++ b/apps/web/src/pages/project/detail/service.ts @@ -212,10 +212,7 @@ class DetailService { } // 更新项目 - async updateProject( - id: number, - project: Partial, - ) { + async updateProject(id: number, project: Partial) { const { data } = await net.request>({ url: `/api/projects/${id}`, method: 'PUT', diff --git a/apps/web/src/pages/project/list/components/CreateProjectModal.tsx b/apps/web/src/pages/project/list/components/CreateProjectModal.tsx index b0631e8..fe1a979 100644 --- a/apps/web/src/pages/project/list/components/CreateProjectModal.tsx +++ b/apps/web/src/pages/project/list/components/CreateProjectModal.tsx @@ -1,10 +1,4 @@ -import { - Button, - Form, - Input, - Message, - Modal, -} from '@arco-design/web-react'; +import { Button, Form, Input, Message, Modal } from '@arco-design/web-react'; import { useState } from 'react'; import type { Project } from '../../types'; import { projectService } from '../service';