chore: Flyway 도입 — DB 스키마 버전 관리 체계 구축#87
Conversation
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
📝 WalkthroughWalkthroughFlyway 마이그레이션 프레임워크를 도입하고 관련 설정을 추가한다. 프로덕션과 테스트 환경의 ChangesFlyway 마이그레이션 설정 도입
Estimated code review effort🎯 2 (Simple) | ⏱️ ~10 minutes 🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 4
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@FLYWAY_MIGRATION.md`:
- Line 5: Markdown headers in FLYWAY_MIGRATION.md are triggering markdownlint
MD022 because there are no blank lines before/after the headers (notably the
"### Existing DB (production / development server)" header and the headers at
the other flagged spots). Fix by adding a single blank line above and below each
header (lines referenced in the comment: the header at "### Existing DB
(production / development server)" and the other headers flagged at the same
file) so each header is separated from surrounding content; follow the MD022
convention consistently throughout the file.
In `@src/main/resources/db/migration/V1__init_schema.sql`:
- Line 11: The migration contains a PostgreSQL‑17‑only directive "SET
transaction_timeout = 0;" in V1__init_schema.sql which will fail on PG <17;
remove that hard failure by either deleting that SET line or wrapping it with a
runtime guard that checks for the parameter's existence (e.g., via
current_setting(..., true)) and only applies the SET when present; update the
migration file V1__init_schema.sql (the SET transaction_timeout statement)
accordingly and consider adding/ documenting a Postgres version pin
(POSTGRES_VERSION or image tag) in CI/deployment configs to avoid environment
drift.
In
`@src/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sql`:
- Around line 8-13: The migration currently adds
workspace_reasons.workspace_request_id and a FK (fk_workspace_reasons_request)
but leaves the column nullable, which conflicts with the WorkspaceReason
entity's `@JoinColumn`(name = "workspace_request_id", nullable = false); update
the migration to (1) backfill workspace_request_id for existing rows (using a
safe SELECT/UPDATE strategy appropriate to your schema), (2) then ALTER TABLE
workspace_reasons ALTER COLUMN workspace_request_id SET NOT NULL, and (3) ensure
the FK constraint fk_workspace_reasons_request remains valid after backfill;
reference the workspace_reasons table, workspace_request_id column, and
fk_workspace_reasons_request when making changes.
In `@src/test/resources/application.yml`:
- Around line 20-25: The global test config disables Flyway via the line
"enabled: false", which will hide SQL migration regressions; add a CI-specific
path that runs Flyway migrations against a real Postgres (e.g., create a CI
profile or application-ci.yml that sets spring.flyway.enabled: true and points
to a Testcontainers Postgres using the same "locations:
classpath:db/migration"), and add a migration smoke test job that boots the app
(or directly invokes Flyway.migrate() in a test) against that Testcontainers
instance to fail CI on broken SQL; keep the default test profile unchanged and
scope the change to the CI/profile that runs in your pipeline.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro
Run ID: 68e97bce-e37e-420e-b759-67ac0bc54530
📒 Files selected for processing (8)
.gitignoreFLYWAY_MIGRATION.mdbuild.gradlesrc/main/resources/application.ymlsrc/main/resources/db/migration/V1__add_substitute_reputation_consent_columns.sqlsrc/main/resources/db/migration/V1__init_schema.sqlsrc/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sqlsrc/test/resources/application.yml
💤 Files with no reviewable changes (1)
- src/main/resources/db/migration/V1__add_substitute_reputation_consent_columns.sql
There was a problem hiding this comment.
Actionable comments posted: 2
♻️ Duplicate comments (3)
FLYWAY_MIGRATION.md (1)
37-37:⚠️ Potential issue | 🟡 Minor | ⚡ Quick win오타 수정: 한글 문자가 혼입된 환경변수 설명을 정정하세요.
라인 37의
applica일tion.yml에 한글 문자 "일"이 잘못 끼어있습니다.application.yml로 정정이 필요합니다.✏️ 제안 수정
-| Variable | Default in applica일tion.yml | Description | +| Variable | Default in application.yml | Description |🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@FLYWAY_MIGRATION.md` at line 37, The table header in the FLYWAY_MIGRATION.md file contains a typo where the Korean character "일" is incorrectly inserted in the text. In the table header row, replace "applica일tion.yml" with the correct spelling "application.yml" to fix the mixed language character issue..gitignore (1)
62-62:⚠️ Potential issue | 🟡 Minor | ⚡ Quick win이 항목은 Flyway PR의 범위 밖입니다. 별도 PR로 분리하세요.
라인 62의
src/main/resources/META-INF/additional-spring-configuration-metadata.json은 IntelliJ가 자동 완성을 위해 생성하는 IDE 산물로, Flyway 도입과는 직접 관련이 없습니다.이전 리뷰어 ysw789의 의견에 따르면, IDE 산물 ignore 정책이 필요하다면 별도 PR로 분리하여 처리하는 것이 PR 응집성 측면에서 바람직합니다. 본 라인을 제거해 주세요.
✏️ 제안 수정
---- unchanged lines 1-60 not shown ---- - -src/main/resources/META-INF/additional-spring-configuration-metadata.json🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In @.gitignore at line 62, The line containing `src/main/resources/META-INF/additional-spring-configuration-metadata.json` in the .gitignore file is an IDE artifact unrelated to the Flyway adoption that is the focus of this PR. Remove this line from the .gitignore file as IDE-specific ignore policies should be handled in a separate PR to maintain PR cohesion and focus.src/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sql (1)
8-13:⚠️ Potential issue | 🟠 Major | 🏗️ Heavy lift
workspace_request_id백필 없이 V3에서 NOT NULL로 전환되어 기존 데이터에서 마이그레이션이 실패합니다.Line 8-13은 컬럼/FK만 추가하고
workspace_reasons.workspace_request_id에 대한 백필이 없습니다. 이 상태에서 V3의SET NOT NULL이 실행되면 기존 행에NULL이 남아 실패합니다(다운스트림 영향: V3 적용 중단).수정 방향 예시
ALTER TABLE workspace_reasons ADD COLUMN IF NOT EXISTS workspace_request_id BIGINT; +-- 도메인 규칙에 맞는 백필이 반드시 선행되어야 합니다. +-- UPDATE workspace_reasons wr +-- SET workspace_request_id = ... +-- WHERE workspace_request_id IS NULL; + ALTER TABLE workspace_reasons ADD CONSTRAINT fk_workspace_reasons_request FOREIGN KEY (workspace_request_id) REFERENCES workspace_requests(id);#!/bin/bash set -euo pipefail echo "== V2/V3에서 workspace_request_id 처리 흐름 확인 ==" nl -ba src/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sql | sed -n '1,120p' echo nl -ba src/main/resources/db/migration/V3__set_workspace_request_id_not_null.sql | sed -n '1,80p' echo echo "== 백필(UPDATE workspace_reasons) 유무 확인 ==" rg -n "UPDATE\\s+workspace_reasons|workspace_request_id|SET NOT NULL" \ src/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sql \ src/main/resources/db/migration/V3__set_workspace_request_id_not_null.sql🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@src/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sql` around lines 8 - 13, The V2 migration adds the workspace_request_id column and foreign key constraint to workspace_reasons table but lacks a backfill UPDATE statement for existing rows. Add an UPDATE statement in the V2 migration file (after adding the column but before or after the foreign key constraint) to populate workspace_request_id with appropriate values for all existing workspace_reasons records. This backfill must be completed in V2 so that when V3 executes the SET NOT NULL constraint, there are no NULL values remaining in the workspace_request_id column for existing rows.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In @.github/workflows/cicd.yml:
- Around line 139-141: The direct injection of GitHub secrets template
expressions (like `${{ secrets.FLYWAY_ENABLED }}`, `${{
secrets.FLYWAY_BASELINE_ON_MIGRATE }}`, and `${{ secrets.FLYWAY_BASELINE_VERSION
}}`) into the inline script body creates a remote command injection
vulnerability, as special characters or delimiters in secret values could break
out of the heredoc syntax. Instead, move these secret references to the step's
`env` configuration as environment variables, and then reference them as shell
variables (using `$VARIABLE_NAME` syntax) within the script itself. This ensures
secrets are properly escaped and cannot break script syntax boundaries.
In
`@src/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sql`:
- Around line 11-13: The foreign key constraint fk_workspace_reasons_request on
the workspace_reasons table is being added with immediate validation, which can
cause extended table locking during migration and impact production
availability. Split this into two separate steps: first add the constraint with
the NOT VALID clause to avoid locking, then add a second ALTER TABLE statement
to validate the constraint separately using VALIDATE CONSTRAINT
fk_workspace_reasons_request. This allows the constraint to be applied without
blocking the table for an extended period.
---
Duplicate comments:
In @.gitignore:
- Line 62: The line containing
`src/main/resources/META-INF/additional-spring-configuration-metadata.json` in
the .gitignore file is an IDE artifact unrelated to the Flyway adoption that is
the focus of this PR. Remove this line from the .gitignore file as IDE-specific
ignore policies should be handled in a separate PR to maintain PR cohesion and
focus.
In `@FLYWAY_MIGRATION.md`:
- Line 37: The table header in the FLYWAY_MIGRATION.md file contains a typo
where the Korean character "일" is incorrectly inserted in the text. In the table
header row, replace "applica일tion.yml" with the correct spelling
"application.yml" to fix the mixed language character issue.
In
`@src/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sql`:
- Around line 8-13: The V2 migration adds the workspace_request_id column and
foreign key constraint to workspace_reasons table but lacks a backfill UPDATE
statement for existing rows. Add an UPDATE statement in the V2 migration file
(after adding the column but before or after the foreign key constraint) to
populate workspace_request_id with appropriate values for all existing
workspace_reasons records. This backfill must be completed in V2 so that when V3
executes the SET NOT NULL constraint, there are no NULL values remaining in the
workspace_request_id column for existing rows.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro
Run ID: 01b3dd2b-49be-48ff-a6ea-f74c820bc805
📒 Files selected for processing (10)
.github/workflows/cicd.yml.gitignoreFLYWAY_MIGRATION.mdbuild.gradlesrc/main/resources/application.ymlsrc/main/resources/db/migration/V1__add_substitute_reputation_consent_columns.sqlsrc/main/resources/db/migration/V1__init_schema.sqlsrc/main/resources/db/migration/V2__add_user_id_and_comment_owner_to_workspace_reason_comments.sqlsrc/main/resources/db/migration/V3__set_workspace_request_id_not_null.sqlsrc/test/resources/application.yml
💤 Files with no reviewable changes (1)
- src/main/resources/db/migration/V1__add_substitute_reputation_consent_columns.sql
There was a problem hiding this comment.
Actionable comments posted: 3
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@FLYWAY_MIGRATION.md`:
- Around line 22-24: Update the FLYWAY_MIGRATION.md documentation to remove
references to `./env` file and clarify how environment variables are set in
different deployment scenarios. Replace the three numbered steps with clearer
instructions that distinguish between local development (where you can use
docker-compose .env file or set variables directly) and production environment
(where FLYWAY_BASELINE_ON_MIGRATE should be set through container runtime like
Kubernetes or Docker). This will prevent confusion since the application is
Docker-containerized and environment variables are injected at runtime rather
than read from a local ./env file.
In `@src/test/java/com/dreamteam/alter/migration/FlywayMigrationTest.java`:
- Line 19: The test class FlywayMigrationTest does not follow the project's
naming convention for test classes. According to the coding guidelines, all test
classes in src/test/** should follow the naming pattern [ClassName]Tests (plural
form). Rename the class from FlywayMigrationTest to FlywayMigrationTests and
rename the file from FlywayMigrationTest.java to FlywayMigrationTests.java to
match the required convention.
- Around line 25-40: The test method migrationsApplyCleanlyOnFreshDatabase does
not follow the required action_condition_expectedResult naming pattern and lacks
explicit Given-When-Then structure comments. Rename the method to follow the
naming convention where it describes the action (what is being tested), the
condition (the state or prerequisites), and the expected result (what should
happen). Additionally, add comment blocks to clearly delineate the Given phase
(where Flyway is configured), the When phase (where migrate() is called), and
the Then phase (where assertions are made).
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro
Run ID: 42efed53-82ba-4ac2-80eb-b1e3cdb86ad1
📒 Files selected for processing (8)
.github/workflows/cicd.yml.gitignoreFLYWAY_MIGRATION.mdbuild.gradlesrc/main/resources/application.ymlsrc/main/resources/db/migration/V1__init_schema.sqlsrc/main/resources/db/migration/V2__add_is_read_column_to_notifications.sqlsrc/test/java/com/dreamteam/alter/migration/FlywayMigrationTest.java
💤 Files with no reviewable changes (2)
- src/main/resources/db/migration/V2__add_is_read_column_to_notifications.sql
- .github/workflows/cicd.yml
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@FLYWAY_MIGRATION.md`:
- Line 12: The ddl-auto entry in FLYWAY_MIGRATION.md does not match the actual
configuration source. Update the documentation for spring.jpa.hibernate.ddl-auto
to reflect that application.yml uses the DDL_AUTO environment variable
placeholder rather than a hardcoded validate value, and keep the description
aligned with Flyway-managed schema behavior.
In `@src/main/resources/application.yml`:
- Around line 26-27: `baseline-version` is currently aligned with the same
version as the first real migration, which can cause
`V1__add_substitute_reputation_consent_columns.sql` to be skipped when
`baseline-on-migrate` is enabled. Update the Flyway baseline strategy in
`application.yml` so `baseline-version` does not overlap with executable
migrations, or redefine `V1__add_substitute_reputation_consent_columns.sql` as a
true baseline snapshot; keep the cutover flow in sync so actual schema-changing
migrations are never marked as already applied.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: ASSERTIVE
Plan: Pro
Run ID: 73ab1052-1df9-4702-ba8c-9bba8fba2a03
📒 Files selected for processing (4)
FLYWAY_MIGRATION.mdbuild.gradlesrc/main/resources/application.ymlsrc/test/resources/application.yml
Flyway 구성 제안기존 스키마와 데이터는 그대로 유지하고, 앞으로의 스키마 변경만 마이그레이션 스크립트로 누적하는 방식으로 가면 좋겠습니다.
cutover 절차 (기존 DB)
|
- Flyway 의존성 추가 및 application.yml 설정
(enabled: true, baseline-version: 1, baseline-on-migrate 환경변수,
ddl-auto: ${DDL_AUTO:validate})
- 베이스라인 전략: 기존 dev DB를 version 1로 마킹만 하고 스키마 덤프는
리포에 커밋하지 않음 (DB 구조 노출 방지). 실제 변경은 V2부터 누적.
- 기존 add_substitute/add_is_read 마이그레이션 제거 (해당 컬럼은 이미 dev DB에 반영됨)
관련 문서
https://www.notion.so/BE-DB-36086553162880308932e28abb3179af?v=3288655316288071b53d000c67f996d3&source=copy_link
Summary by CodeRabbit