Skip to content

Commit eba867b

Browse files
committed
perf(ci): 테스트 샤딩으로 CI 실행 시간 단축
- Backend/E2E 테스트에 4개 샤드 병렬 실행 적용 - Playwright blob 리포터로 분산 테스트 결과 병합 - justfile에 shard 파라미터 전달 지원 추가
1 parent 12dc638 commit eba867b

File tree

4 files changed

+70
-18
lines changed

4 files changed

+70
-18
lines changed

.github/workflows/backend-tests.yml

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,13 @@ on:
2222

2323
jobs:
2424
backend-tests:
25-
name: Run Backend tests
25+
name: Backend Tests (Shard ${{ matrix.shardIndex }}/${{ matrix.shardTotal }})
2626
runs-on: ubuntu-latest
27+
strategy:
28+
fail-fast: false
29+
matrix:
30+
shardIndex: [1, 2, 3, 4]
31+
shardTotal: [4]
2732
steps:
2833
- name: Checkout
2934
uses: actions/checkout@master
@@ -64,10 +69,10 @@ jobs:
6469
wait-on tcp:5432
6570
6671
- name: Run tests
67-
run: just test backend
72+
run: just test backend --shard=${{ matrix.shardIndex }}/${{ matrix.shardTotal }}
6873

6974
- name: Run e2e tests
70-
run: just test e2e
75+
run: just test e2e --shard=${{ matrix.shardIndex }}/${{ matrix.shardTotal }}
7176
env:
7277
GOOGLE_CLIENT_ID: ${{ secrets.GOOGLE_CLIENT_ID }}
7378
GOOGLE_CLIENT_SECRET: ${{ secrets.GOOGLE_CLIENT_SECRET }}

.github/workflows/e2e-ui-tests.yml

Lines changed: 47 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,13 @@ on:
2828

2929
jobs:
3030
e2e-ui-tests:
31-
name: Run E2E UI tests
31+
name: E2E UI Tests (Shard ${{ matrix.shardIndex }}/${{ matrix.shardTotal }})
3232
runs-on: ubuntu-latest
33+
strategy:
34+
fail-fast: false
35+
matrix:
36+
shardIndex: [1, 2, 3, 4]
37+
shardTotal: [4]
3338

3439
services:
3540
postgres:
@@ -72,12 +77,51 @@ jobs:
7277
run: just deps-playwright
7378

7479
- name: Run E2E UI tests
75-
run: just test e2e-ui
80+
run: just test e2e-ui --shard=${{ matrix.shardIndex }}/${{ matrix.shardTotal }}
7681
env:
7782
VITE_DISCORD_SERVER_LINK: https://discord.gg/kZApcdSEJ4
7883

79-
- name: Upload test report
84+
- name: Upload blob report
8085
if: always()
86+
uses: actions/upload-artifact@v4
87+
with:
88+
name: blob-report-${{ matrix.shardIndex }}
89+
path: blob-report/
90+
retention-days: 1
91+
92+
e2e-report-merge:
93+
name: Merge E2E Reports
94+
needs: e2e-ui-tests
95+
if: always()
96+
runs-on: ubuntu-latest
97+
steps:
98+
- name: Checkout
99+
uses: actions/checkout@master
100+
101+
- name: Setup Node 22
102+
uses: actions/setup-node@v6
103+
with:
104+
node-version: "22.18.0"
105+
106+
- name: Setup pnpm
107+
uses: pnpm/action-setup@v4
108+
with:
109+
version: 9.15.0
110+
111+
- name: Install dependencies
112+
run: pnpm install
113+
114+
- name: Download blob reports
115+
uses: actions/download-artifact@v4
116+
with:
117+
pattern: blob-report-*
118+
path: all-blob-reports
119+
merge-multiple: true
120+
121+
- name: Merge reports
122+
run: pnpm exec playwright merge-reports --reporter html ./all-blob-reports
123+
124+
- name: Upload merged report
81125
uses: actions/upload-artifact@v4
82126
with:
83127
name: playwright-report

justfile

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -287,15 +287,15 @@ test target="all" *args:
287287

288288
just setup-testdb
289289
cd "{{ backend_dir }}"
290-
DATABASE_URL="postgres://postgres:postgres@localhost:5432/test?pool_timeout=60" NODE_OPTIONS="--max_old_space_size=8192" PRISMA_CLIENT_ENGINE_TYPE={{ prisma_engine }} pnpm exec jest --runInBand --logHeapUsage --no-compilation-cache --silent=false {{ args }}
290+
DATABASE_URL="postgres://postgres:postgres@localhost:5432/test?pool_timeout=60" NODE_OPTIONS="--max_old_space_size=8192" PRISMA_CLIENT_ENGINE_TYPE={{ prisma_engine }} pnpm exec jest --runInBand --logHeapUsage --no-compilation-cache --silent=false --passWithNoTests {{ args }}
291291
;;
292292
e2e)
293293
echo "NodeJS:" $(node -v)
294294
echo "Prisma Engine:" {{ prisma_engine }}
295295

296296
just setup-testdb
297297
cd "{{ backend_dir }}"
298-
DATABASE_URL="postgres://postgres:postgres@localhost:5432/test?pool_timeout=60" NODE_OPTIONS="--max_old_space_size=8192" PRISMA_CLIENT_ENGINE_TYPE={{ prisma_engine }} pnpm exec jest --config ./jest-e2e.json --runInBand --no-compilation-cache --forceExit {{ args }}
298+
DATABASE_URL="postgres://postgres:postgres@localhost:5432/test?pool_timeout=60" NODE_OPTIONS="--max_old_space_size=8192" PRISMA_CLIENT_ENGINE_TYPE={{ prisma_engine }} pnpm exec jest --config ./jest-e2e.json --runInBand --no-compilation-cache --forceExit --passWithNoTests {{ args }}
299299
;;
300300
e2e-ui)
301301
set +x
@@ -315,7 +315,7 @@ test target="all" *args:
315315
cd "{{ backend_dir }}"
316316
DATABASE_URL="postgres://postgres:postgres@localhost:5432/test?pool_timeout=60" PRISMA_CLIENT_ENGINE_TYPE={{ prisma_engine }} pnpm prisma db seed
317317
cd "{{ root_dir }}"
318-
pnpm test:e2e-ui
318+
pnpm test:e2e-ui {{ args }}
319319
fi
320320
;;
321321
*)

playwright.config.ts

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3,20 +3,23 @@ import { defineConfig, devices } from "@playwright/test";
33
import { AUTH_FILE, BACKEND_URL, FRONTEND_URL } from "./e2e/constants";
44

55
const WEBSERVER_TIMEOUT_MS = 3 * 60 * 1000;
6+
const isCI = !!process.env.CI;
67

78
export default defineConfig({
89
testDir: "./e2e",
910
outputDir: "./test-results",
1011
fullyParallel: true,
11-
forbidOnly: !!process.env.CI,
12-
retries: process.env.CI ? 2 : 0,
13-
workers: 4,
14-
reporter: [["html", { open: "never", outputFolder: "playwright-report" }]],
12+
forbidOnly: isCI,
13+
retries: isCI ? 2 : 0,
14+
workers: isCI ? 2 : 4,
15+
reporter: isCI
16+
? [["blob"], ["html", { open: "never", outputFolder: "playwright-report" }]]
17+
: [["html", { open: "never", outputFolder: "playwright-report" }]],
1518
use: {
1619
baseURL: FRONTEND_URL,
17-
trace: process.env.CI ? "on-first-retry" : "on",
18-
screenshot: process.env.CI ? "only-on-failure" : "on",
19-
video: process.env.CI ? "retain-on-failure" : "on",
20+
trace: isCI ? "on-first-retry" : "on",
21+
screenshot: isCI ? "only-on-failure" : "on",
22+
video: isCI ? "retain-on-failure" : "on",
2023
},
2124
projects: [
2225
{
@@ -43,13 +46,13 @@ export default defineConfig({
4346
command:
4447
'cd src/backend && DATABASE_URL="postgres://postgres:postgres@localhost:5432/test?pool_timeout=60" PRISMA_CLIENT_ENGINE_TYPE=binary PORT=3001 NODE_ENV=development GOOGLE_CLIENT_ID=dummy GOOGLE_CLIENT_SECRET=dummy DISCORD_CLIENT_ID=dummy DISCORD_CLIENT_SECRET=dummy KAKAO_CLIENT_ID=dummy KAKAO_CLIENT_SECRET=dummy DISCORD_GOLD_EXCHANGE_RATE_WEBHOOK_URL=https://discord.com/api/webhooks/dummy pnpm start:dev',
4548
url: `${BACKEND_URL}/graphql`,
46-
reuseExistingServer: !process.env.CI,
49+
reuseExistingServer: !isCI,
4750
timeout: WEBSERVER_TIMEOUT_MS,
4851
},
4952
{
5053
command: "cd src/frontend && PLAYWRIGHT=1 pnpm dev",
5154
url: FRONTEND_URL,
52-
reuseExistingServer: !process.env.CI,
55+
reuseExistingServer: !isCI,
5356
timeout: WEBSERVER_TIMEOUT_MS,
5457
},
5558
],

0 commit comments

Comments
 (0)