Skip to content

Commit e350172

Browse files
committed
refactor: pr body tnwjd
1 parent 54b7063 commit e350172

2 files changed

Lines changed: 51 additions & 13 deletions

File tree

.github/scripts/dependency-update.mjs

Lines changed: 36 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,15 @@ const OPENAI_REASONING_EFFORT = "medium"
88
const MAX_RELEASE_NOTE_LENGTH = 16_000
99
const STABLE_VERSION_PATTERN = /^v?(\d+)\.(\d+)\.(\d+)$/
1010
const DIRECT_PACKAGE_PATTERN = /\.package\(\s*url:\s*"(?<url>[^"]+)"\s*,\s*(?<requirement>\.exact\("(?<exact>[^"]+)"\)|\.upToNextMinor\(from:\s*"(?<upToNextMinor>[^"]+)"\))\s*\)/gs
11+
const SEOUL_DATE_TIME_FORMATTER = new Intl.DateTimeFormat("en-CA", {
12+
timeZone: "Asia/Seoul",
13+
year: "numeric",
14+
month: "2-digit",
15+
day: "2-digit",
16+
hour: "2-digit",
17+
minute: "2-digit",
18+
hourCycle: "h23",
19+
})
1120

1221
// ThirdParty에 직접 선언한 외부 라이브러리 요구 조건 읽기
1322
export function parsePackages(manifest) {
@@ -137,15 +146,19 @@ export async function decideCandidates({
137146
export function renderPrBodySection({ runId, packages, now = new Date() }) {
138147
const applied = packages.filter(packageInfo => packageInfo.action === "apply")
139148
const manual = packages.filter(packageInfo => packageInfo.action === "manual_review")
140-
const date = now.toISOString().replace("T", " ").replace(/\.\d{3}Z$/, " UTC")
141149
const lines = [
142150
`<!-- dependency-update:${runId} -->`,
143-
`### ${date} 의존성 갱신 실행`,
151+
"### 실행 시간",
152+
"",
153+
seoulDateTime(now),
154+
"",
155+
"### 반영 후보",
144156
"",
145157
]
146158

147-
if (applied.length !== 0) {
148-
lines.push("#### 반영 후보", "")
159+
if (applied.length === 0) {
160+
lines.push("없음", "")
161+
} else {
149162
lines.push("| package | 이전 | 이후 | 근거 |")
150163
lines.push("| --- | --- | --- | --- |")
151164
lines.push(...applied.map(packageInfo => [
@@ -157,20 +170,31 @@ export function renderPrBodySection({ runId, packages, now = new Date() }) {
157170
lines.push("")
158171
}
159172

160-
if (manual.length !== 0) {
161-
lines.push("#### 수동 확인 필요", "")
162-
lines.push(...manual.map(packageInfo => [
173+
lines.push("### 수동 확인 필요", "")
174+
if (manual.length === 0) {
175+
lines.push("없음")
176+
} else {
177+
lines.push(...manual.flatMap(packageInfo => [
163178
`- ${packageInfo.repository}`,
164-
`${packageInfo.currentVersion}${packageInfo.candidateVersion}`,
165-
packageInfo.manualReviewReason,
166-
packageInfo.releaseNotes?.url,
167-
].filter(Boolean).join(" — ")))
168-
lines.push("")
179+
` - ${packageInfo.currentVersion}${packageInfo.candidateVersion}`,
180+
` - ${packageInfo.manualReviewReason || "변경 이력 확인 필요"}`,
181+
...(packageInfo.releaseNotes?.url ? [` - ${packageInfo.releaseNotes.url}`] : []),
182+
]))
169183
}
170184

171185
return `${lines.join("\n").trimEnd()}\n`
172186
}
173187

188+
// 서울 시간대로 실행 시간을 표기
189+
function seoulDateTime(now) {
190+
const values = Object.fromEntries(
191+
SEOUL_DATE_TIME_FORMATTER.formatToParts(now)
192+
.map(part => [part.type, part.value])
193+
)
194+
195+
return `${values.year}-${values.month}-${values.day} ${values.hour}:${values.minute} KST`
196+
}
197+
174198
// 직접 선언한 외부 라이브러리의 동일 메이저 후보와 변경 이력 수집
175199
export async function discoverCandidates({
176200
manifest,

.github/scripts/dependency-update.test.mjs

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -350,7 +350,7 @@ test("removes a v tag prefix before applying the candidate to the manifest", asy
350350
)
351351
})
352352

353-
test("renders an append-only PR section for approved and manual-review results", () => {
353+
test("renders an automatic PR section with Seoul time", () => {
354354
const section = renderPrBodySection({
355355
runId: "123",
356356
packages: [
@@ -372,10 +372,24 @@ test("renders an append-only PR section for approved and manual-review results",
372372
})
373373

374374
assert.match(section, /<!-- dependency-update:123 -->/)
375+
assert.match(section, /### \n\n2026-08-20 09:00 KST/)
376+
assert.match(section, /### /)
375377
assert.match(section, /opficdev\/Nexa.*1\.1\.1.*1\.2\.0/)
378+
assert.match(section, /### /)
376379
assert.match(section, / /)
377380
})
378381

382+
test("renders empty automatic PR sections", () => {
383+
const section = renderPrBodySection({
384+
runId: "123",
385+
packages: [],
386+
now: new Date("2026-08-20T00:00:00Z"),
387+
})
388+
389+
assert.match(section, /### \n\n/)
390+
assert.match(section, /### \n\n/)
391+
})
392+
379393
function candidatePackage() {
380394
return {
381395
repository: "opficdev/Nexa",

0 commit comments

Comments
 (0)