~/yeinkeem
Career Statement

김예인

Backend / Platform Engineer

백엔드 6년차입니다. Java/Spring 기반으로 공공 업무 시스템과 세무 SaaS 신규 플랫폼을 개발해왔고, 복잡한 도메인 요구사항을 API와 운영 가능한 구조로 풀어내는 일을 해왔습니다.

현재는 더존테크윌에서 도메인 API, API Gateway 인증/권한 구조, 사내 공통 Spring Boot Starter, Kubernetes GitOps 파이프라인을 담당하고 있습니다. 이전에는 국세청 NTIS 송달 시스템에서 대규모 발송 배치, 외부 채널 연동, 운영 이슈 대응을 경험했습니다.

빠른 구현뿐 아니라 서비스가 안정적으로 운영되고, 이후 팀원이 같은 기준으로 확장할 수 있는 구조를 남기는 데 관심이 많습니다.

2023.04 — 재직 중 · 3년 2개월

주식회사 더존테크윌

주임 / 서비스개발본부 · 개발1팀

세무사·회계법인 대상 SaaS를 제공하는 회사. 기존 레거시 세무 정보 서비스를 신규 SaaS 플랫폼으로 재구축하고 있고, 그중 백엔드·플랫폼 영역을 담당하고 있습니다.

신규 SaaS 플랫폼 백엔드

2023.04 — 현재
Overview

프로젝트 초기 단계부터 참여해, 레거시 PHP 기반 세무 정보 서비스를 Spring Boot 3.3과 Spring Cloud 기반 마이크로서비스로 재구축하고 있습니다. 현재 도메인·플랫폼 책임 단위로 분리된 다수의 마이크로서비스가 구축되어 상용 오픈을 준비 중인 단계입니다. API Gateway, 사내 공통 라이브러리, Kubernetes GitOps 파이프라인, 관측성·로깅처럼 여러 서비스가 함께 쓰는 기반을 다루면서, 세법 도메인 API도 같이 담당하고 있습니다. 도메인 콘텐츠는 법령·판례·예규와 그에 연결된 세무자료로 구성되어 시점 기준 조회와 변경 이력 추적이 핵심 요구사항이고, 레거시 Oracle DB는 다년간 누적된 테이블이 많아 도메인 진입 비용 자체가 컸습니다.

Role

프로젝트 합류 시점에 공통 플랫폼 영역과 도메인 API를 동시에 맡게 됐습니다. 사내 공통 Spring Boot Starter, API Gateway 인증/인가 책임 경계 재설계, Kubernetes GitOps 파이프라인, 관측성·로깅 등 여러 서비스가 함께 쓰는 기반을 설계·구현했고, 세법 영역의 도메인 API도 함께 개발했습니다.

Scale
  • 도메인·플랫폼 책임 단위로 분리한 다수의 마이크로서비스 (Spring Boot 3.3)
  • 상용 오픈 준비 중인 SaaS 플랫폼
  • 기존 서비스의 운영 고객 전체 전환을 고려한 구조 설계
  • 도메인 콘텐츠: 법령·판례·예규 + 연결된 세무자료 (시점 기준 조회·변경 이력 추적 필요)
  • 레거시 Oracle DB: 다년간 누적된 다수의 테이블 (DB 동결 + API 재설계 전략 채택)
Stack
Backend
Java 21, Spring Boot 3.3, Spring Cloud Gateway, JPA, QueryDSL, OpenFeign, Resilience4j
Database
Oracle (legacy), PostgreSQL (pg_trgm), Caffeine
Infra
Kubernetes, Jenkins, ArgoCD, Jib, Kustomize, Nexus, Harbor
Observability
Elasticsearch, Filebeat, Elastic APM, log4j2 JSON
Identity / Auth
JWT (RS256), OAuth2, LDAP
주요 책임

레거시 Oracle 스키마 분석 · 도메인 문서화

담당 범위: 분석 및 문서화
  • 레거시 Oracle DB에 다년간 누적된 테이블이 많고, 컬럼 의미와 관계에 대한 사내 문서가 정리돼 있지 않은 상태였습니다.
  • 신규 API 코드 작성에 들어가기 전에, 핵심 도메인 영역(법령·판례·예규·세무자료 등)의 테이블 구조와 실제 데이터 패턴을 분석해 사내 문서로 정리했습니다. 코드만 빨리 짜고 넘어가지 않고, 다른 팀원이 도메인을 따라 들어올 수 있는 진입점을 만들고 싶었습니다.
  • 이후 합류하는 백엔드·기획·세무사가 도메인을 파악할 때 같은 문서를 참고하게 됐고, "이 컬럼이 뭐였더라"를 사람에게 매번 물어보지 않아도 되는 상태가 됐습니다.

사내 공통 Spring Boot Starter 설계·구현

ADR-0001 담당 범위: 설계·구현 주도 (사내 채택 이후 일부 모듈은 협업)
  • 신규 마이크로서비스를 만들 때마다 응답 포맷, 예외 처리, BaseEntity, 권한 enum 등을 반복 구현하고 있었고, 사람마다 패턴이 조금씩 달라지면서 같은 종류의 버그가 여러 서비스에서 반복되는 상태였습니다.
  • 공통 기능을 사내 Spring Boot Starter 형태로 제공하기로 했습니다. core / data / web / starter 4개 모듈로 나눠 Auto-Configuration 기반으로 의존성 한 줄만 추가하면 표준 구성이 따라오게 했고, 사내 Nexus에 SemVer 기반으로 자동 배포되도록 정리했습니다.
  • 권한 enum을 core 모듈에 한 번 정의해, 권한 추가나 변경이 라이브러리 한 곳에서만 일어나도록 정리했습니다.
  • 신규 서비스의 보일러플레이트가 크게 줄었고, 권한·응답·예외처럼 서비스마다 달라지면 문제가 생기는 기준들이 한 곳에서 관리되는 상태가 됐습니다.

점진적 MSA 이관 — 레거시 DB 유지 + API 재설계

담당 범위: 이관 전략 주도 · 도메인별 API는 다른 백엔드와 분담
  • 레거시 PHP 모놀리스의 Oracle DB는 수년 치 운영 데이터가 명확한 PK, 외래키, 코멘트 없이 운영되어서 DB까지 한 번에 재설계하면 마이그레이션 리스크와 운영 중단 시간이 너무 컸습니다.
  • DB는 그대로 두고 API만 점진적으로 분리하는 Strangler Fig 패턴을 선택했습니다. 신규 API는 Spring Boot로 새로 만들되 같은 Oracle DB를 바라보게 두고, 화면이 신규 API를 호출하도록 하나씩 옮기는 방식으로 진행하고 있습니다.
  • 검색이나 동기화처럼 트랜잭션 성격이 다른 워크로드는 PostgreSQL(pg_trgm)로 분리해 듀얼 DataSource 구조로 가져갔습니다. Spring AbstractRoutingDataSource로 워크로드에 따라 분기하도록 했고, 각 도메인 API는 JPA + QueryDSL + MyBatis(복잡 쿼리·집계) 조합으로 재설계했습니다.
  • 검색성 조회는 PostgreSQL 쪽으로 분리해 기존 Oracle에 걸리는 부담을 줄였고, 화면 단위로 점진 교체할 수 있는 흐름이 자리잡았습니다.

도메인 API 설계·구현 (법령·판례 콘텐츠)

담당 범위: 세법 영역 설계·구현
  • 변경 이력이 있는 콘텐츠와 연관 자료를 다루는 영역이라, 시점 기준 조회와 연관 콘텐츠 조회를 API 설계의 기본 축으로 잡았습니다.
  • 레거시 Oracle의 법령·판례·세무자료 데이터를 화면 요구사항에 맞는 응답 구조로 재구성했고, 시점 기준 메타 조회와 조문 단위 연관 매핑 조회를 책임 단위로 분리해 엔드포인트를 정리했습니다.
  • Spring REST Docs를 적용해 컨트롤러 테스트에서 API 문서가 함께 생성되도록 했고, 문서가 코드 변경을 따라오지 못하는 문제를 줄였습니다.
  • 이 패턴(시점 + 참조)이 자리잡은 이후, 다른 백엔드가 자기 도메인을 만들 때도 같은 흐름을 따라가게 됐습니다.

API Gateway · 인증/인가 책임 경계 재설계

ADR-0004 · ADR-0005 · ADR-0006 담당 범위: 설계·구현 주도 (인프라·보안 영역 협업)
  • 초기 구조에서는 Gateway가 모든 자원의 권한 정책을 알고 있어야 했는데, 자원 서비스가 늘어날수록 Gateway 필터가 도메인 변경을 따라가야 하는 결합이 커지는 문제가 있었습니다. 필터 한두 곳을 보완하는 수준이 아니라, 책임 경계 자체를 다시 잡아야 한다고 판단했습니다.
  • Gateway는 인증만 책임지고 인가는 자원 서비스에서 판단하도록 책임을 나눴습니다. Gateway는 별도 IdP 서비스가 발급한 RS256 JWT를 검증하고 헤더로 사용자 컨텍스트를 넘기는 역할까지만 가지도록 정리했고, 권한 어휘는 사내 공통 라이브러리의 enum에서 단일 정의하도록 했습니다.
  • 운영자(백오피스) 인증은 외부 고객용 IdP와 분리해 LDAP 기반으로 처리했습니다. 외부 고객 인증 쪽 이슈가 운영자 채널까지 번지지 않도록 하기 위한 결정이었습니다.
  • 그 결과 자원 서비스의 권한 정책 변경이 Gateway 수정으로 이어지는 일을 줄였고, 서비스마다 권한명이 달라지는 문제도 공통 라이브러리 기준으로 정리할 수 있었습니다.

Kubernetes GitOps 파이프라인 구축

ADR-0007 담당 범위: 설계·구현 및 운영
  • 초기에는 Jenkins에서 SSH로 서버에 접속해 배포하는 방식이었습니다. 자동화는 되어 있었지만 롤백 기준이 약했고, 환경마다 같은 결과물이 배포된다는 보장도 부족했습니다. K8s 전환 시점에 맞춰 빌드와 배포 책임을 분리하는 방향으로 파이프라인을 다시 설계했습니다.
  • Jenkins는 빌드와 이미지 push까지만 담당하고, 클러스터 동기화는 ArgoCD가 매니페스트 repo를 pull 방식으로 감시하도록 구성했습니다. 앱 코드 repo와 매니페스트 repo를 분리했고, 환경별 차이는 Kustomize overlay에서만 표현하도록 정리했습니다.
  • 처음에는 환경별로 다시 빌드하는 구조였지만, staging/prod 파이프라인을 설계하는 과정에서 같은 소스가 같은 결과물로 배포된다는 보장이 약하다는 문제가 보였습니다. 이후 dev에서 한 번 빌드한 이미지를 staging/prod로 promote하는 방식으로 바꿨습니다.
  • ArgoCD는 App-of-Apps 패턴으로 구성해 신규 서비스 추가 시 정해진 매니페스트 묶음을 추가하면 배포 흐름에 올라오도록 했습니다. 관측성 같은 인프라성 컴포넌트도 같은 GitOps 흐름 위에서 관리했고, 배포 이력과 환경별 차이는 Git 기준으로 추적할 수 있게 됐습니다.

중앙 로그 수집 파이프라인 구축

ADR-0008 담당 범위: 설계·구현 및 운영
  • K8s 전환 직후에는 ArgoCD UI에서 Pod 로그를 확인했지만, Pod가 재시작되면 로그가 사라지고 서비스 간 흐름을 이어서 보기 어려웠습니다. SSH 배포 시기부터 필요성을 이야기했던 중앙 로그 수집을 K8s 전환 이후 다시 추진했습니다.
  • 스택은 Elasticsearch 기반으로 잡았습니다. 사내에 다른 용도로 운영 중인 Elasticsearch가 있어 클러스터를 새로 띄우지 않고 인덱스를 추가하는 방식으로 시작할 수 있었고, 이 덕분에 초기 도입 비용을 줄일 수 있었습니다.
  • 초기 권고안은 Logstash + logback 조합이었지만, 프로젝트는 log4j2를 사용하고 있어 그대로 적용하기 어려웠습니다. 모든 서비스의 로깅 설정을 크게 바꾸기보다, 컨테이너 stdout 로그를 인프라 쪽에서 수집하는 방향으로 바꿔 Filebeat DaemonSet을 선택했습니다.
  • Filebeat가 노드별 컨테이너 로그를 수집해 Elasticsearch로 직접 전송하도록 구성했고, 서비스 네임스페이스만 수집하도록 필터를 적용했습니다. dev 환경에서 먼저 수집 구조를 검증했고, staging/prod 반영을 위해 ILM, 멀티라인 처리, 로그 보관 주기 같은 운영 정책을 함께 정리하고 있습니다.

마스터 코드 캐시 콜드스타트 개선

담당 범위: 분석·설계·구현
  • 공통 화면 진입 시 마스터 코드(세목·과세 구분 등) 조회가 사용자 체감 수준으로 느렸습니다. 캐시는 있었지만 첫 요청에서 DB로부터 채워지는 구조라 콜드스타트 페널티가 그대로 사용자에게 노출되고 있었습니다.
  • Caffeine 메모리 캐시를 쓰면서 기동 시 워밍업을 함께 가져가기로 했습니다. 처음에는 같은 빈 안에서 워밍업 메서드를 호출했는데 Spring AOP self-invocation 문제로 캐시가 채워지지 않았고, ApplicationReadyEvent 후크에서 워밍업을 수행하는 별도 빈으로 분리해 우회했습니다.
  • G1GC와 -XX:MaxRAMPercentage로 컨테이너 환경에 맞게 GC 튜닝도 같이 했습니다.
  • 마스터 코드 콜드스타트가 사용자가 체감하지 못할 수준으로 단축됐고, Full GC 빈도가 줄어 Pod 메모리가 cgroup 한계 안에서 안정적으로 유지됐습니다.
2022.01 — 2023.04 · 1년 4개월

국세청 NTIS 유지보수 - 업무공통(송달)

백엔드 개발 / 플랫폼팀 (대내 업무공통)
㈜아이티센글로벌 (2022.01–02) · ㈜더존테크윌 (2022.03–2023.04)

국세청 NTIS 유지보수 사업단에 백엔드 개발자로 참여했습니다. 세무공무원이 사용하는 대내 시스템 중 송달 영역을 담당했으며, 납세고지서·안내문을 우편, SMS, EMAIL, 카카오 알림톡으로 발송하는 배치와 API를 개발·운영했습니다. 같은 사업단에서 약 1년 4개월간 동일 업무를 이어서 수행했고, 사업단 변경에 따라 계약사만 변경되었습니다.

NTIS 송달 영역 — 요건 검토부터 운영까지

2022.01 — 2023.04
Overview

세무공무원의 업무 프로세스에 맞춰 납세자에게 고지서·안내문을 발송하는 송달 시스템입니다. 발송 채널은 우편·SMS·EMAIL·카카오 알림톡 4종이고, 시즌별(근로장려금, 종합소득세 등) 대량 발송 배치와 외부 발송 시스템 연동·결과 회신 처리가 핵심입니다. 잦은 송달 요건 변경에 대응하는 "요건 검토 → 구현 방향 제시 → 개발 → 결과 회신" 사이클을 담당했습니다.

Role

송달 영역의 배치와 API 개발·유지보수를 담당했습니다. 국세청 전산 공무원이 제기한 업무 개선안을 시스템 구조 안에서 구현 가능한 방식으로 검토하고, 영향 범위·일정·리스크를 정리해 회신했습니다. 발송 시즌에는 결과 데이터를 모니터링하며 누락·실패 건을 추적하고, 재발송·데이터 보정까지 이어지는 운영 대응을 함께 맡았습니다.

Scale
  • 시즌별 대량 발송: 근로장려금·종합소득세 등 대규모 배치
  • 발송 채널 4종 (우편 · SMS · EMAIL · 카카오 알림톡)
  • 전국 단위 운영 — 국세청 NTIS
Stack
Backend
Java, 전자정부프레임워크, MyBatis, Quartz
Database
MySQL
Frontend
WebSquare (화면 일부 연동)
주요 책임

고객 요건 기술 검토 · 개선 개발

  • 발송 대상자 산출 기준, 외부 채널 메시지 포맷, 결과 코드 처리 규칙 등 송달 요건 변경 요청을 검토했습니다. 현재 배치·API 구조에서 구현 가능한 방식을 제시하고, 영향 범위·일정·리스크를 정리해 회신했습니다.
  • 검토와 합의가 끝나면 배치·API 수정, 테스트, 운영 반영, 결과 데이터 회신까지 이어지는 과정을 담당했습니다. 고객사 운영팀과 직접 소통하면서, 단일 기능이 아니라 실제 행정 업무 흐름 기준으로 요구사항을 해석하고 개발 범위를 조정했습니다.

시즌별 대량 발송 배치 개발·유지보수

  • 근로장려금·연말정산 대상자 알림, 종합소득세 신고 안내, 부가가치세 신고 안내 등 시즌별 업무에 맞춰 대량의 고지서·안내문을 발송하는 배치를 개발·유지보수했습니다.
  • 발송 결과와 실패 코드를 기준으로 누락·실패 건을 분류하고, 사유별 재발송·데이터 보정·운영 회신까지 이어지는 처리 흐름을 담당했습니다.

외부 발송 채널 연동 기능 개선

  • 우편 발송 시스템(인쇄·발송 위탁) 연동 부분과 카카오 알림톡 API 연동 부분의 기능 개선·유지보수를 담당했습니다.
  • 외부 시스템 응답·실패 코드를 송달 결과 테이블에 일관된 포맷으로 적재해서, 운영자가 한 화면에서 채널별 결과를 확인할 수 있도록 정리했습니다.
2021.04 — 2022.01 · 10개월

국세청 학자금상환 시스템 고도화

백엔드 개발 / 대내 업무공통 파트
서림정보통신주식회사

국세청 학자금상환 시스템 고도화 프로젝트에 참여했습니다. 그중 대내 업무공통 파트에서 여러 서비스가 공통으로 호출해 쓰는 마스터 데이터 조회 API와 라이브러리를 담당했습니다.

학자금상환 시스템 — 대내 업무공통 파트

2021.04 — 2022.01
Overview

학자금상환 시스템 고도화 프로젝트 중 여러 화면·서비스에서 공통으로 호출하는 조회 영역을 담당했습니다. 주소·청사(조직)·납세자·내부 구성원 등 마스터 데이터를 단일 API로 제공하는 형태로 정리했습니다.

Role

공통 조회 API와 라이브러리 개발·유지보수를 담당했고, WebSquare 기반 화면 연동까지 함께 진행했습니다.

Stack
Backend
Java, 전자정부프레임워크, MyBatis
Database
Oracle
Frontend
WebSquare
주요 책임

공통 마스터 데이터 조회 API · 라이브러리 개발

  • 주소 조회, 청사(조직) 조회, 납세자 조회, 내부 구성원 조회 등 여러 서비스가 공통으로 호출하는 마스터 데이터 조회 API와 공통 라이브러리를 개발·유지보수했습니다.
  • 이전까지 화면·기능별로 흩어져 있던 조회 로직을 공통 영역으로 모아, 화면 단에서는 동일한 인터페이스로 데이터를 가져올 수 있도록 정리했습니다.

WebSquare 화면 — 백엔드 API 연동

  • WebSquare 기반 화면 컴포넌트와 백엔드 API 통신 부분을 구현했고, 화면 측 데이터 바인딩 포맷에 맞춰 응답 구조를 정리했습니다.

위 의사결정의 전체 배경과 검토했던 대안은 별도 ADR 저장소에 정리돼 있습니다 → github.com/yeinkeem/architecture-decisions