[Spring] Formatter

이연우·2025년 8월 18일

TIL

목록 보기
80/100

🎯 Formatter란?

  • 문자열 ↔ 객체 변환을 하되,
    표시 형식(포맷팅)을 세밀하게 제어하는 데 특화된 컴포넌트
  • ConversionService와 목적은 비슷하지만,
    사람이 읽는 형태로 출력/입력되는 값을 다룰 때 특히 유용함

📚 핵심 포인트

  • 객체 → 문자열: 사람이 읽기 좋은 포맷으로 출력
  • 문자열 → 객체: 포맷된 문자열을 역으로 해석
    → 즉, Converter보다 표현 형식 제어에 더 초점이 있음

🌐 Locale (지역/언어)

  • 지역 및 언어 정보를 담는 객체
    • 언어 코드: en, ko
    • 국가 코드: US, KR
  • 국제화(i18n) 시 어떤 언어/표기 관습을 쓸지 결정하는 기준
  • 예: Locale.KOREA면 숫자/날짜 등에 한국식 포맷 적용

🧩 Formatter 인터페이스 구조

  • Printer ✍️: Object → String

    • 객체를 문자열로 출력 (포맷팅)
  • Parser 🔎: String → Object

    • 문자열을 객체로 해석 (파싱)
  • Formatter는 내부적으로 Printer + Parser를 상속하여
    하나의 타입에 대해 양방향 변환을 제공함


💡 Formatter 적용

  • 적용 예시: 숫자 ↔ 금액 문자열
    → 목표: 숫자 10000 ↔ 문자열 "10,000" (로케일에 맞는 금액 표기)

🛠️ PriceFormatter 구현

@Slf4j
public class PriceFormatter implements Formatter<Number> {

  @Override
  public Number parse(String text, Locale locale) throws ParseException {
    log.info("text = {}, locale={}", text, locale);
    NumberFormat format = NumberFormat.getInstance(locale);
    // "10,000" -> 10000L
    return format.parse(text);
  }

  @Override
  public String print(Number object, Locale locale) {
    log.info("object = {}, locale = {}", object, locale);
    // 10000L -> "10,000"
    return NumberFormat.getInstance(locale).format(object);
  }
}
  • 🧮 Number
    • Integer, Long, Double부모 타입
    • parse 결과는 Long으로 반환됨 (테스트에서 확인)

✅ 테스트 코드

class PriceFormatterTest {

  PriceFormatter formatter = new PriceFormatter();

  @Test
  void parse() throws ParseException {
    Number result = formatter.parse("1,000", Locale.KOREA);
    // parse 결과는 Long
    Assertions.assertThat(result).isEqualTo(1000L);
  }

  @Test
  void print() {
    String result = formatter.print(1000, Locale.KOREA);
    Assertions.assertThat(result).isEqualTo("1,000");
  }
}
  • Locale.KOREA 기준으로
    • "1,000"1000L
    • 1000"1,000"

📑 흐름 한눈 정리

  • 입력 문자열 수신 → parse(text, locale)객체(Number)
  • 객체(Number)print(object, locale)출력 문자열
  • Locale에 따라 구분자/표시 방식이 자동 반영됨

🧠 요약 정리

구분역할핵심 메서드특징/비고
Formatter문자열 ↔
객체 변환
(포맷 초점)
print(Object, Locale), parse(String, Locale)포맷 제어에 특화
✍️ Printer객체 → 문자열print(Object, Locale)표시 형식(, . 등) 적용
🔎 Parser문자열 → 객체parse(String, Locale)포맷 해석
(구분자 제거 등)
🌐 Locale지역/언어 정보국제화에 따른
표기 방식 결정
예시(PriceFormatter)금액 문자열 ↔ 숫자NumberFormat.getInstance(locale)"1,000"1000L
Number숫자 부모 타입Integer/Long/Double의 상위

0개의 댓글