[EXT-016][실무] 사용자에게 맞는 표시 언어 고르기 > IT 기술 공유

본문 바로가기

사이트 내 전체검색

뒤로가기 IT 기술 공유

[EXT-016][실무] 사용자에게 맞는 표시 언어 고르기

페이지 정보

작성자 기술팀장 작성일 26-09-08 06:39 조회 12 댓글 0

본문

[이번 수업]

여러 언어를 지원하려면 표시할 문구 묶음을 골라야 합니다. 이번에는 언어 태그(language tag, 언어와 지역 등을 나타내는 표준 표기)를 확인하고 저장된 선택과 실행 환경의 선호 언어를 순서대로 적용합니다.

[선수지식]

JavaScript 객체·함수와 Node.js 실행 방법을 알아야 합니다. 지역별 숫자 표시는 EXT-015에서 연습할 수 있습니다.

[학습목표]

1. BCP 47 언어 태그를 설명한다.
2. 사용자 선택, 환경 선호, 기본값의 우선순위를 구현한다.
3. 선택 결과를 허용 목록과 HTML lang 속성에 연결한다.

[핵심개념]

ko, en-US, zh-Hant-TW는 BCP 47 언어 태그입니다. 하이픈으로 나뉜 하위 태그가 언어, 문자 체계, 지역 등을 구체화합니다. en_US처럼 밑줄을 쓴 값을 임의로 만들지 마세요. Intl.Locale은 태그를 검사하고 language 같은 요소를 읽습니다. 잘못된 태그에는 RangeError가 날 수 있어 외부 입력은 예외 처리해야 합니다.

선택 정책은 표준이 대신 정하지 않습니다. 이 수업에서는 사용자가 저장한 선택, 브라우저 선호 목록, 서비스 기본값 순으로 적용합니다. HTTP Accept-Language에는 여러 언어 범위와 q 가중치가 들어갈 수 있으므로 첫 쉼표 앞만 잘라 쓰지 마세요. 서버에서는 검증된 파서를 쓰고, 지원 태그 하나를 고를 때는 RFC 4647의 lookup 방식을 적용할 수 있습니다.

[따라하기]

language_picker.js 파일에 다음 코드를 저장합니다. 지역별 번역이 따로 없는 서비스의 예입니다.

```javascript
const messages = {
  ko: { hello: "안녕하세요" },
  en: { hello: "Hello" },
  ja: { hello: "こんにちは" },
};

function baseLanguage(tag) {
  if (!tag) return null;
  try {
    return new Intl.Locale(tag).language;
  } catch {
    return null;
  }
}

function chooseLanguage(saved, requested, fallback = "ko") {
  for (const tag of [saved, ...requested]) {
    const language = baseLanguage(tag);
    if (language && Object.hasOwn(messages, language)) return language;
  }
  return fallback;
}

const browserChoice = chooseLanguage(null, ["ja-JP", "en-US"]);
const savedChoice = chooseLanguage("ko-KR", ["ja-JP"]);
console.log(browserChoice);
console.log(savedChoice);
console.log(messages[savedChoice].hello);
```

Windows PowerShell·명령 프롬프트, macOS 터미널, Linux 셸에서 같은 명령을 실행합니다.

```text
node language_picker.js
```

예상 결과입니다.

```text
ja
ko
안녕하세요
```

웹에서는 결과를 실제 문서 언어와 맞춰 `<html lang="ko">`처럼 설정하세요. 보조기술과 검색 도구가 콘텐츠 언어를 판단할 때 사용합니다. 지역별 문구가 따로 있다면 기본 언어만 꺼내지 말고, 전체 태그를 포함한 RFC 4647 lookup이나 검증된 국제화 라이브러리를 사용하세요.

[흔한 실수]

첫째, IP 주소나 시간대로 언어를 확정합니다. 위치와 읽는 언어는 같지 않습니다. 둘째, 번역이 없는 태그를 선택해 빈 화면을 만듭니다. 지원 목록과 기본값이 필요합니다. 셋째, 문구는 한국어인데 lang을 en으로 둡니다. 넷째, 외부 태그를 검증 없이 파일 이름에 붙입니다.

[보안 주의]

언어 태그는 인증·권한·국적을 뜻하지 않습니다. 외부 태그를 파일 경로로 조합하지 말고 코드의 허용 목록에서 번역을 찾으세요. Accept-Language는 사용자 선호를 포함하므로 필요 이상으로 보관하지 않습니다. 번역 문자열을 HTML로 출력할 때도 이스케이프가 필요합니다. 실습은 본인 소유의 로컬 파일에서만 진행합니다.

[직접 해볼 과제]

messages에서 ja를 제거하고 요청 목록이 ["ja-JP", "en-GB"]일 때 en이 선택되는지 확인하세요. 잘못된 태그 bad_tag를 saved에 넣어도 중단되지 않는지 확인하고, 기본값이 선택되는 사례도 만드세요.

[확인문제]

1. 저장된 사용자 선택을 환경 선호보다 먼저 적용하는 이유는 무엇인가요?
2. Accept-Language를 첫 쉼표 기준으로만 자르면 왜 잘못될 수 있나요?
3. 외부 언어 태그를 번역 파일 경로에 바로 붙이면 어떤 위험이 있나요?

[다음 학습]

다음에는 언어마다 달라지는 단수·복수 규칙을 Intl.PluralRules로 처리합니다.

[공식 참고 자료]

IETF BCP 47 언어 태그(RFC 5646)
https://www.rfc-editor.org/rfc/rfc5646.html

IETF 언어 태그 매칭(RFC 4647)
https://www.rfc-editor.org/rfc/rfc4647.html

HTTP Accept-Language(RFC 9110)
https://www.rfc-editor.org/rfc/rfc9110.html#section-12.5.4

ECMA-402 Locale 객체
https://tc39.es/ecma402/#locale-objects

WHATWG HTML lang 속성
https://html.spec.whatwg.org/multipage/dom.html#the-lang-and-xml:lang-attributes

댓글목록 0

등록된 댓글이 없습니다.

Copyright © 소유하신 도메인. All rights reserved.

사이트 정보

회사명 : 회사명 / 대표 : 대표자명
주소 : OO도 OO시 OO구 OO동 123-45
사업자 등록번호 : 123-45-67890
전화 : 02-123-4567 팩스 : 02-123-4568
통신판매업신고번호 : 제 OO구 - 123호
개인정보관리책임자 : 정보책임자명

PC 버전으로 보기