깃 플로우: 브랜치로 읽는 코드의 현재 상태

Git Flow라는 개념은 오래전부터 들어왔지만, 실제로 구조를 이해하고 사용해본 경험은 거의 없었다. 그동안은 Git의 기본적인 사용법(commit, push, branch)만 알고 있으면 충분하다고 생각했다. 필요하면 그때그때 찾아보면 된다고 판단했고,
개인 개발 환경에서는 그 선택이 크게 틀리지도 않았다.

하지만 협업 환경에서는 이야기가 달라진다. 브랜치의 목적이 불분명해지고, 배포 코드와 개발 코드의 경계가 흐려지는 순간
Git은 협업을 돕는 도구가 아니라 혼란을 증폭시키는 요소가 된다.

특히 이직을 준비하며 여러 팀의 개발 문화를 살펴보면서, Git Flow는 단순한 브랜치 전략이 아니라
배포 안정성과 협업 비용을 관리하기 위한 규칙이라는 점을 뒤늦게 체감하게 되었다.

이 글에서는 Git Flow를 "외워야 할 규칙"이 아닌, 왜 이런 구조가 필요했고,
어떤 문제를 해결하려는 설계였는지를 중심으로 정리해보려 한다.

git flow란 무엇일까?

소프트웨어의 '배포 상태'를 기준으로 코드 변경을 단계별로 분리하고 관리하기 위한 브랜치 기반 협업 워크플로우입니다.
일반적으로 브랜치를 다음과 같은 이름으로 작성이 되어집니다.

브랜치 의미하는 상태
main 현재 운영 중인 코드
develop 다음 배포 후보
feature 변경 중인 코드
release 배포 직전 안정화 상태
hotfix 운영 장애 수정 상태

여기서 브랜치 이름은 무엇을 뜻하는 걸까요? 현재 운영중인 코드의 브랜치명이 main인게 중요한걸까요?
결론부터 말하자면, 그 자체는 크게 중요하지 않습니다. (이름은 회사마다 조금씩 달라질 수 있겠죠)
Git은 브랜치 이름에 아무런 의미를 부여하지 않습니다. 중요한 것은 해당 브랜치가 어떤 상태의 코드를 가리키고 있는 것이 중요한 부분입니다. 즉, Git Flow에서 브랜치 이름은 코드가 현재 어떤 단계에 있는지를 팀원들에게 전달하기 위한 의사 소통수단에 가깝습니다.
간단히 생각해서, 브랜치 이름은 단순한 규칙이 아니라 현재 코드의 상태를 설명하는 라벨이라고 이해하시면 됩니다.

기본 파이프라인

feature → develop → release → main

각 상태에 대해 자세히 알아봅시다. 

feature - 변경이 격리된 상태

기능 개발이 진행 중인 상태로 아직 완성되지 않았고, 깨져도 되는 코드
이 상태의 코드들은 배포 책임을 지지 않는것이 가장 중요한 특징입니다.

특징

  • 새로운 기능 개발
  • 리팩토링
  • 실험적인 변경 가능
  • 테스트 실패 허용

jira같은 이슈 및 프로젝트 관리 도구를 통해 티켓으로 발행되어 관리가 되어질수도 있다고 합니다.

실무에서는 feature 브랜치를 Jira와 같은 이슈 및 프로젝트 관리 도구에서 발행된 티켓 단위로 생성하여 관리하는 경우도 많습니다.
이를 통해 작업의 상태와 코드 변경을 함께 추적할 수 있다.

develop - 다음 배포 후보 상태

다음 배포에 포함될 코드들이 통합된 상태
feature에서 작업한 코드들이 처음으로 함께 동작하는 상태가 되어집니다.

특징

  • 여러 feature가 병합됨
  • 통합 테스트 시작
  • 기능 추가는 계속 가능
  • 운영에는 아직 나가지 않음

그렇다면, feature에서 develop으로 어떻게 통합을 시킬까요?
feature 브랜치는 PR을 통해 리뷰와 CI를 거친뒤 develop으로 병합하게 되어집니다.

PR이 생성이 되어지면, CI가 동작하게 되어집니다. 만약 리뷰가 반려가 되거나 CI가 실패하게 된다면, develop 브랜치로 머지가 되지 않습니다.

release - 배포 안정화 단계

이번 배포에 포함될 코드가 확정된 상태
develop에서 release로 코드를 통합한다고 하면, feature에서 develop으로 병합하는 과정과무엇이 다른지 의문이 생길 수 있습니다.
이 차이를 이해하기 위해서는 release 단계의 목적을 먼저 이해해야 합니다.

목적
이번 배포의 범위를 확정하는 것

release 단계의 의미
release 단계는 기능을 계속 추가하는 개발 단계가 아니라,
개발이 종료되었음을 선언하고 배포를 준비하는 단계라고 볼 수 있습니다.
이 시점 이후에는 기능 추가는 중단되고, 배포를 위한 안정화와 검증만 수행되어집니다.

release에서 발생하는 모든 변경

  • 왜 수정했는지
  • 어떤 이슈 때문인지
  • 배포에 어떤 영향을 주는지

명확히 기록되어야 합니다.

만약에, release 단계에서 버그를 발견한다면 어떻게 처리가 되어질까?
결론부터 말하면, release 단계에서 발견된 버그는 develop으로 되돌아가지 않습니다.
해당 버그는 release 브랜치에서 직접 수정되어집니다.
이는 release가 이미 이번 배포에 포함될 코드에 대한 책임을 지는 상태이기 때문입니다.
다만, release에서 수정된 내용은 반드시 develop에도 다시 병합한다고 합니다.
이를 누락할 경우, 다음 배포에서 동일한 버그가 다시 발생하는 문제가 생길 수 있습니다.

 

초기 개발 단계에서는 사용자와 운영 부담이 크지 않기 때문에 git flow의 모든 단계를 그대로 적용하지 않는 경우가 많습니다.
특히 release 단계는 배포 리스크를 관리하기 위한 구조이므로, 초기에는 생략되거나 develop 브랜치가 그 역할을 대신하기도 합니다.


main - 운영상태

실제 서비스에 배포된 코드의 상태

QA 검증이 종료되고, 해당 버전에 대해 운영 배포가 가능하다는 판단이 내려지면
release 브랜치는 main 브랜치로 병합되어집니다.이는 해당 코드가 운영 환경에 대한 책임을 공식적으로 가지게 되었음을 의미합니다.

다음과 같은 흐름으로 main브랜치를 관리한다고 합니다.

  • release 브랜치 QA 완료
  • release → main PR 생성
  • CI 실행 (운영 기준)
  • 승인
  • merge
  • tag 생성 (v1.2.0)
  • 프로덕션 배포 트리거

tag의 역할은 무엇일까요? 이걸로 배포를 진행하는 걸까요?

 

tag는 배포를 수행하기 위한 수단이라기보다는, 배포가 완료된 결과를 고정해서 기록하는 역할을 합니다.
실제 배포는 main 브랜치의 커밋을 기준으로 이루어지며, tag는 해당 커밋이 어떤 버전으로 운영에 배포되었는지를
명확히 남기기 위해 사용되어집니다. 

그렇다면, main브랜치에서 버그가 발생하는 경우는 어떻게 해야 할까요?
develop이나 release에서 버그가 발생하게 되면 해당 브랜치에서 작업을 하지만 main은 hotfix라는 브랜치를 새로만들어 관리가 되어집니다.

hotfix - 운영 이슈

hotfix는 정상적인 개발 흐름이 아니라 비정상 상황을 수습하기 위한 예외 경로이기 때문에 기본 브랜치 전략이 아닙니다.
그렇다면, main은 어째서 hotfix로 브랜치를 따로 만든걸까요?
main에서 바로 수정하지 않고 hotfix 브랜치를 따로 만드는 이유는 운영 기준선(main)을 보호하기 위해서입니다.

버전 관리

버전 관리는 코드를 관리하는 것이 아니라, 배포된 사실을 관리합니다. 그래서 git flow에서는 태그로 버전을 관리합니다.

MAJOR.MINOR.PATCH

MAJOR: 하위 호환이 깨지는 변경
MINOR: 기능 추가 (하위 호환 유지)
PATCH: 버그 수정

Git Flow와 연결하면 이렇게 해석할 수 있습니다. release 단계에서 이번 배포는 버전 1.2.0으로 나갈 준비를 하게 됩니다.
그렇게 main에 병합되고 배포가 끝나면 v1.2.0 태그로 확정이 되어집니다.

브랜치코드  상태주요  역할책임  담당자
feature 변경 중 기능 개발, 실험, 리팩토링 개발자 (개인)
develop 다음 배포 후보 기능 통합, 통합 테스트 개발팀
release 배포 직전 안정화 배포 범위 확정, QA, 버그 수정 개발팀 + QA
main 운영 중 실제 서비스 운영 코드 기준 개발팀 + 운영
hotfix 운영 장애 대응 긴급 버그 수정, 즉시 배포 개발팀 (운영 책임자 포함)
tag 배포 완료 기록 배포 버전 고정, 롤백 기준 개발팀

 

Git Flow는 이미 알고 있다고 생각했지만, 실제로는 왜 이렇게 사용되는지까지는 깊이 생각해보지 않았던 것 같습니다/
이번 정리를 통해 브랜치가 단순한 작업 단위가 아니라 코드의 상태와 책임을 표현하는 수단이라는 점을 이해하게 되었습니다.
특히 각 단계의 통합마다 CI가 동작한다는 점은, Git Flow가 단순한 규칙이 아니라
검증을 전제로 한 협업 모델이라는 사실을 잘 보여준다고 느꼈습니다.

'개발' 카테고리의 다른 글

RDB vs Nosql  (0) 2025.12.12
스프링 시큐리티에는 보안 6요소를 어떻게 사용할까?  (0) 2025.11.12

댓글

Designed by JB FACTORY