DBMS 2

DA, SQL, DB보안 등 실무자를 위한 위한 DB기술 바이블!

MySQL 지역화 (Localization)와 국제적인 사용

DBMS 2
MySQL 가이드
데이터 베이스 관리
MySQL 지역화 (Localization)와 국제적인 사용
작성자
admin
작성일
2021-02-19 10:52
조회
861

MySQL 지역화 (Localization)와 국제적인 사용

데이터와 정렬을 위한 문자 셋
에러 메시지 언어 설정
새로운 문자 셋 추가
문자 정의 배열
스트링 콜레팅(collating)지원
. 멀티-바이트문자 지원
문자 셋 문제
MySQL 서버 타임존 지원

이 섹션은 다른 문자 셋을 서버가 사용할 수 있도록 구성하는 방법을 설명한다. 또한, 서버의 타임 존 설정 방법과 접속 별 타임 존 지원 활성화 방법에 대해서도 함께 설명을 한다.


데이터와 정렬을 위한 문자 셋

디폴트로는, MySQL 은 latin1 (cp1252 서유럽) 문자 셋과 latin1_swedish_ci 콜레션 (collation)을 사용하고 있다. 이 디폴트 값은 대부분의 서유럽과 미국 사용자들이 사용할 수 있는 문자 셋이다.

모든 MySQL 바이너리 배포판은 --with-extra-charsets=complex를 사용해서 컴파일 되어 있다. 이것은 모든 표준 배포판에 코드를 추가해서 배포판이 latin1과 바이너리에 포함되어 있는 모든 멀티-바이트문자 셋을 처리할 수 있도록 해준다. 다른 문자 셋은 필요할 경우에 문자-셋 정의문에서 읽어올 수가 있다.

문자 셋은 아이덴티파이어 (identifier)에서 사용할 수 있는 문자가 어떤 것인지를 판단한다. 콜레션 (collation)은 SELECT 명령문의 ORDER BY 와 GROUP BY 구문이 스트링을 어떻게 정렬하는지를 결정한다.

여러분은 서버가 시작될 때 서버의 디폴트 문자 셋과 콜레션을 --character-set-server 와 --collation-server 옵션을 사용해서 변경 시킬 수가 있다. 콜레션은 반드시 디폴트 문자 셋에 대해 리걸 콜레션이 되어야 한다. (SHOW COLLATION 명령문을 사용해서 각 문자 셋에서 사용할 수 있는 콜레션이 무엇인지를 알아본다.) Section 5.2.1, “mysqld 명령어 옵션”을 참조할 것.

사용 가능한 문자 셋은 configure에 대한 --with-charset=charset_name 및 --with-extra-charsets=list-of-charsets | complex | all | none 옵션과, SHAREDIR/charsets/Index에 있는 문자 셋 구성 파일에 결정된다. Section 2.8.2, “전형적인 configure 옵션”을 참조.

MySQL을 구동하는 동안에 문자 셋을 변경 하고자 한다면, 정렬 순서도 함께 바꾸어야 한다. 따라서, 여러분은 반드시 모든 테이블에서 myisamchk -r -q --set-collation=collation_name 를 구동 시켜야 하는데, 그렇지 않으면 올바르게 순서가 지켜지지 않을 수도 있다.

클라이언트가 MySQL 서버에 접속을 할 때, 서버는 클라이언트에게 자신의 디폴트 문자 셋이 어떤 것인지를 알려 주며, 클라이언트는 서버가 알려주는 문자 셋으로 전환을 한다.

SQL 쿼리에 대한 스트링을 빠져 나올 때에는 mysql_real_escape_string()을 사용해야 한다. mysql_real_escape_string()은 이전 버전의 mysql_escape_string() 함수와 동일한 것이지만, 이것은 처음의 MYSQL 접속 핸들을 처음의 파라미터로 가져와서 문자에서 빠져 나올 때 적절한 문자 셋이 계정 안으로 들어갈 수 있도록 해주는 차이가 있다..

만약에 클라이언트가 서버가 설치된 것과는 다른 경로를 가지고 컴파일 되었고, MySQL 서버를 구성한 사용자가 MySQL 바이너리에 있는 모든 문자 셋을 포함 시키지 않았다면, 서버가 클라이언트와 다른 문자 셋을 사용할 경우에 클라이언트가 찾아야 하는 추가 문자 셋이 어디에 있는지를 반드시 클라이언트에게 알려 주어야 한다.

여러분은 이것을 동적 MySQL 문자 셋이 저장되어 있는 디렉토리 경로를 가리켜 주는 --character-sets-dir 옵션 지정을 통해 구현 할 수가 있다. 예를 들면, 아래의 내용을 옵션 파일에 넣을 수가 있다:



[client]
character-sets-dir=/usr/local/mysql/share/mysql/charsets


여러분은 클라이언트가 아래와 같은 문자 셋을 사용하도록 만들 수가 있다:



[client]
default-character-set=charset_name


하지만, 이것은 일반적으로는 불필요한 행동이 된다.


에러 메시지 언어 설정

mysqld는 에러 메시지를 영어로 보여 주는 것이 디폴트이지만, 다른 언어로 이 메시지를 나타나도록 할 수도 있다: Czech, Danish, Dutch, Estonian, French, German, Greek, Hungarian, Italian, Japanese, Korean, Norwegian, Norwegian-ny, Polish, Portuguese, Romanian, Russian, Slovak, Spanish, 또는 Swedish.

mysqld는특정 언어로 에러 메시지를 보여 주게끔 mysqld를 시작하기 위해서는, --language 또는 -L 옵션을 사용한다. 이 옵션 값은 언어 이름 또는 에러 메시지 파일의 경로가 될 수 있다. 예를 들면:



shell> mysqld --language=swedish
또는:

shell> mysqld --language=/usr/local/share/swedish


언어 이름은 소문자로 지정되어야 한다.

디폴트로는, 언어 파일은 MySQL의 베이스 디렉토리 밑에 있는 share/LANGUAGE 디렉토리에 있다.

서버가 만들어 내는 에러 메시지 내용 변경도 가능하다. 자세한 것은 http://dev.mysql.com/doc/를 참조할 것. 만약에 에러 메시지를 변경한 후에 MySQL을 새로운 버전으로 업그레이드 한다면, 에러 메시지 변경 작업을 다시 하도록 한다.


새로운 문자 셋 추가

이 섹션에서는 MySQL에 새로운 문자 셋을 추가하는 과정을 설명하고 있다. 이 과정을 진행하기 위해서는 반드시 MySQL 소스 배포판을 사용해야 한다. 올바른 과정을 선택하기 위해서는, 문자 셋이 단순한 것인지 아니면 복잡한 것인지를 알아야 한다:


  • 만약에 문자 셋이 특수 스트링 콜레션 루틴을 사용해서 정렬을 하지 않고 멀티-바이트문자 지원이 필요 없는 것이라면, 그 문자 셋은 단순한 것이다.
  • 만약에 위의 특성 중에 하나라도 필요하게 되면, 그 문자 셋은 복잡한 문자 셋이다.

예를 들면, latin1 과 danish는 단순 문자 셋이며, 반면에 big5 와의 지침에서 보면, 문자 셋 이름은 MYSET로 표현 되어 있다.

단순 문자 셋의 경우, 아래의 과정을 진행한다:


  1. MYSET 을 sql/share/charsets/Index 파일의 끝에 추가한다. 이 파일에 고유의 번호를 부여한다.
  2. sql/share/charsets/MYSET.conf를 생성한다. (이 파일은 sql/share/charsets/latin1.conf 복사본을 사용해서 만들 수 있다.) 파일에 대한 신텍스는 매우 간단하다:
    • ‘#’ 문자를 사용해서 코멘트를 입력한다.
    • 단어는 화이트 스페이스를 사용해서 구분한다.
    • 문자 셋을 정의할 때, 모든 단어는 반드시 16진수 포맷 숫자로 되어야 한다.
    • ctype 배열은 처음 257 단어를 가져온다. to_lower[], to_upper[] 그리고 sort_order[] 배열은 그 다음 256 단어를 각각 가져온다.
  3. 문자 셋 이름을 configure.in에 있는 CHARSETS_AVAILABLE 과 COMPILED_CHARSETS 리스트에 추가한다.
  4. 재 구성하고, 재 컴파일 한 후에, 테스트를 한다.

복잡 문자 셋의 경우, 아래의 과정을 진행한다:


    1. MySQL 배포판에 있는 strings/ctype-MYSET.c 파일을 생성한다.
    2. MYSET 을 sql/share/charsets/Index 파일 끝에 추가한다. 여기에 고유 번호를 부여한다.
    3. 무엇을 정의해야 하는지 알아보기 위해서 ctype-*.c 파일을 살펴 본다 (strings/ctype-big5.c와 같은 파일). 파일에 있는 배열은 ctype_MYSET, to_lower_MYSET와 같은 이름을 가져야 한다는 것을 명심한다.
    4. 파일의 맨 위 근처에, 아래와 같은 코멘트를 집어 넣는다:
      /*
      * This comment is parsed by configure to create ctype.c,
      * so don't change it unless you know what you are doing.
      *
      * .configure. number_MYSET=MYNUMBER
      * .configure. strxfrm_multiply_MYSET=N
      * .configure. mbmaxlen_MYSET=N
      */

      configure 프로그램은 이 코멘트를 사용해서 문자 셋을 MySQL 라이브러리에 자동으로 집어 넣는다.
      strxfrm_multiply 와 mbmaxlen 라인은 다음 섹션에서 설명하기로 한다. 이것들은 콜레션 함수가 필요하거나 또는 멀티-바이트문자 셋 함수가 필요할 경우에만 개별적으로 포함 시킬 필요가 있다.
    5. 그런 다음에는, 아래의 함수들을 생성한다
      • my_strncoll_MYSET()
      • my_strcoll_MYSET()
      • my_strxfrm_MYSET()
      • my_like_range_MYSET()
    6. 문자 셋 이름을 configure.in에 있는CHARSETS_AVAILABLE 과 COMPILED_CHARSETS 리스트에 추가한다.
    7. 재 구성하고, 재 컴파일하고, 테스트를 한다.

sql/share/charsets/README 파일에는 추가적인 설명이 들어 있다.


문자 정의 배열

to_lower[] 와 to_upper[]는 문자 셋의 각 멤버에 대응하는 소문자와 대문자를 가지고 있는 단순 배열이다. 예를 들면:



to_lower['A'] should contain 'a'
to_upper['a'] should contain 'A'


sort_order[]는 비교와 정렬을 위해 문자가 어떤 순서로 되어 있는지를 가리키는 맵 (map)이다. 대부분의 경우 (하지만 모든 문자에 해당하지는 않음) 이것은 to_upper[]과 동일하게 취급 되는데, to_upper[] 는 대소 문자 구분 없는 정렬을 의미한다. MySQL은 sort_order[] 값을 근거로 문자를 정렬한다. 좀더 복잡한 정렬 규칙에 대해서는, Section 5.11.5, “스트링 콜레팅 (collating) 지원”을 참조할 것.

ctype[]는 일종의 비트 값 배열이며, 문자 별로 하나의 요소를 가지고 있다. (to_lower[], to_upper[], 그리고 sort_order[]는 문자 값으로 인덱스 되어 있으나, ctype[]는 문자 값 + 1로 인덱스 되어 있다. 이것은 EOF를 다루기 위한 구형 레가시 방식이다)

m_ctype.h에서 아래와 같은 비트마스크 (bitmask)를 볼 수 있을 것이다:



#define _U      01      /* Uppercase */
#define _L 02 /* Lowercase */
#define _N 04 /* Numeral (digit) */
#define _S 010 /* Spacing character */
#define _P 020 /* Punctuation */
#define _C 040 /* Control character */
#define _B 0100 /* Blank */
#define _X 0200 /* heXadecimal digit */


각 문자에 대한 ctype[] 엔트리는 문자를 설명하는데 사용할 수 있는 비트 마스크 값의 합집합 (union)이 되어야 한다. 예를 들면, 'A'는 대문자일 뿐만 아니라 (_U) 16진수 숫자이기도 하기 때문에 (_X), ctype['A'+1]는 다음의 값을 가지게 된다:



_U + _X = 01 + 0200 = 0201


스트링 콜레팅(collating)지원

만약에 여러분이 사용하는 언어의 정렬 규칙이 너무 복잡해서 단순 sort_order[] 테이블을 가지고서는 처리할 수가 없다면, 스트링 콜레션 함수를 사용해야 할 것이다.

이에 대한 가장 좋은 설명서는 현존하는 문자 셋이 된다. big5, czech, gbk, sjis, 그리고 tis160 문자 셋을 참고 삼아 살펴 본다.

여러분은 파일의 맨 위 특별 코멘트에 있는 strxfrm_multiply_MYSET=N 값을 지정해야 한다. N 은 my_strxfrm_MYSET 을 실행하는 동안 스트링이 커질 수 있는 최대 비율로 설정한다 (이것은 양수이어야 한다).


. 멀티-바이트문자 지원

멀티-바이트 문자가 있는 새로운 문자 셋 지원을 추가 하고자 한다면, 멀티-바이트 문자 함수를 사용하도록 한다.

이에 대한 가장 좋은 설명서는 현존하는 문자 셋이 된다. euc_kr, gb2312, gbk, sjis, 그리고 ujis 문자 셋을 살펴 본다. 이것들은 strings 디렉토리에 있는 ctype-charset_name.c 파일에서 구현되었다.

여러분은 파일의 맨 위 특별 코멘트에 있는 mbmaxlen_MYSET=N 값을 지정해야 한다.

N 은 문자 셋에 있는 것 중에 가장 큰 문자 class=sub_title>문자 셋 문제

바이너리 배포판에 컴파일 되어 있지 않은 문자 셋을 사용하고자 한다면, 아래의 문제를 만날 수도 있다:


        • 여러분이 사용하는 프로그램은 문자 셋이 저장되어 있는 곳을 알아 내기 위한 경로를 잘못 사용하게 된다. (디폴트는 /usr/local/mysql/share/mysql/charsets). 이 문제는 의심스러운 프로그램을 구동 시킬 때 --character-sets-dir 옵션을 사용해서 수정할 수가 있다.
        • 문자 셋이 동적으로 로딩할 수 없는 멀티-바이트 문자 셋일 경우. 이와 같은 경우, 여러분은 반드시 문자 셋을 지원하도록 프로그램을 재 컴파일 해야 한다.
        • 문자 셋이 동적 문자 셋이지만, 이에 대한 구성 파일을 가지고 있지 않는 경우. 이와 같은 경우, 새로운 MySQL 배포판을 가지고 그 문자 셋에 대한 구성 파일을 설치해야 한다.
        • 만약에 Index 파일이 문자 셋에 대한 이름을 가지고 있지 않다면, 여러분의 프로그램은 아래와 같은 에러를 화면에 출력 한다:
        • ERROR 1105: File '/usr/local/share/mysql/charsets/?.conf'
          not found (Errcode: 2)

          이와 같은 경우, 여러분은 새로운 Index 파일을 가져오거나 또는 수동으로 누락된 문자 셋 이름을 현재 파일에 추가해야 한다.
        • MyISAM 테이블의 경우, myisamchk -dvv tbl_name을 사용해서 테이블 번호와 문자 셋을 검사할 수가 있다.
MySQL 서버 타임존 지원

MySQL 서버에는 여러 가지 타임 존 설정 방법이 있다:


        • 시스템 타임 존. 서버가 시작될 때에, 서버는 호스트 머신의 타임 존을 알아 내려고 시도하며 그것을 사용해서 system_time_zone 시스템 변수를 설정한다. 이 값은 설정 후에는 변경되지 않게 된다.
        • 서버의 현재 타임 존. 글로벌 time_zone 시스템 변수는 서버가 현재 동작하면서 사용하고 있는 타임 존을 나타낸다. time_zone의 초기 값은 'SYSTEM'이며, 이것은 서버의 타임 존이 시스템 타임 존과 동일하다는 것을 나타낸다.
          초기 값은 --default-time-zone=timezone 옵션을 사용해서 확정적으로 지정할 수가 있다. 여러분이 SUPER 권한을 가지고 있다면, 런타임 시에 아래의 명령문을 사용해서 글로벌 값을 설정할 수가 있다:
          mysql> SET GLOBAL time_zone = timezone;
        • 접속 별 타임 존. 접속하는 각 클라이언트는 자신만의 타임 존을 가지고 있는데, 이것은 세션 time_zone 변수에 의해 지정된다. 초기에는, 세션 변수는 그 값을 글로벌 time_zone 변수에서 가져 오지만, 클라이언트는 아래의 명령문을 사용해서 자신만의 고유 타임 존으로 변경할 수가 있다:
          mysql> SET time_zone = timezone; 

글로벌 및 클라이언트-특성 타임 존의 현재 값은 아래와 같이 얻을 수가 있다:






mysql> SELECT @@global.time_zone, @@session.time_zone;

timezone 값은 스트링으로 주어지며 '+10:00' 또는 '-6:00'와 같이 UTC오프셋을 가리키게 된다. 만약에 mysql 데이터 베이스에 타임 존 정보 테이블이 이미 존재한다면, 'Europe/Helsinki', 'US/Eastern', 또는 'MET'와 같은 네임드 타임 존 형태로도 값을 줄 수가 있다. 'SYSTEM'은 사용하는 타임 존이 시스템 타임 존과 동일한 것임을 가리킬 때 사용한다. 타임 존 이름은 대소 문자를 구분하지 않는다.

MySQL을 설치하면 mysql 데이터 베이스에 타임 존 테이블이 생성되지만, 그것을 읽어 오지는 않는다. 그것은 수동으로 읽어와야 한다. (만약에 여러분이 이전 버전을 4.1.3 또는 그 이후 버전으로 업그레이드 한다면, mysql 데이터 베이스를 업그레이드 해서 테이블이 생성되도록 만들어야 한다. Section 5.6.2, “mysql_upgrade -MySQL 업그레이드에 대한 테이블 검사”에 있는 방법을 따라 한다.)

만약에 여러분의 시스템이 자체 zoneinfo 데이터 베이스를 가지고 있다면 (타임 존을 설명하는 파일 셋), mysql_tzinfo_to_sql 프로그램을 사용해서 타임 존 테이블을 채우도록 한다. 만약에 여러분의 시스템이 zoneinfo 데이터 베이스를 가지고 있지 않다면, 이 섹션 후반에서 설명하는 다운 로드 패키지를 사용하도록 한다.

mysql_tzinfo_to_sql 은 타임 존 테이블을 읽어 오기 위해 사용하는 프로그램이다. 명령어 라인에서, zoneinfo 디렉토리의 경로 이름을 mysql_tzinfo_to_sql에 보내고 그 결과를 mysql 프로그램으로 보낸다. 예를 들면:

shell> mysql_tzinfo_to_sql /usr/share/zoneinfo | mysql -u root mysql

mysql_tzinfo_to_sql은 시스템 타임 존을 읽고 그것을 가지고 SQL명령문을 만든다. mysql 는 그 명령문이 타임 존 테이블을 읽어오도록 만든다.

mysql_tzinfo_to_sql를 사용하면 단일 타임 존 파일을 읽어오거나 또는 립 세컨드 (leap second) 정보를 만들어 낼 수도 있다:


        • 타임 존 이름 tz_name에 상응하는 단일 타임 존 파일 tz_file를 읽어오기 위해서는, mysql_tzinfo_to_sql 을 아래와 같이 호출한다:
          shell> mysql_tzinfo_to_sql tz_file tz_name | mysql -u root mysql
        • 만약에 타임 존에 립 세컨드용 계정이 필요하다면, 립 세컨드 정보를 아래와 같이 초기화 시킨다. 여기에서 tz_file는 여러분이 사용하는 타임 존 파일의 이름이 된다:
          shell> mysql_tzinfo_to_sql --leap tz_file | mysql -u root mysql

만약에 여러분의 시스템이 zoneinfo 데이터 베이스를 가지고 있지 않다면 (예를 들어, 윈도우 또는 HP-UX), http://dev.mysql.com/downloads/timezones.html에서 존 테이블을 다운 로드하여 사용한다. 이 패키지는 MyISAM 타임 존 테이블용 .frm, .MYD, 및 .MYI 파일을 가지고 있다. 이러한 테이블들은 mysql 데이터 베이스의 일 부분이기 때문에, 파일들을 MySQL 서버의 데이터 디렉토리의 mysql 서브디렉토리에 저장해야 한다. 이것을 수행하는 동안에는 서버를 종료해야 한다.

Warning: 여러분의 시스템이 zoneinfo 데이터 베이스를 가지고 있다면 다운 로드 패키지를 사용하지 말길 바란다. 대신에 mysql_tzinfo_to_sql 유틸리티를 사용한다. 그렇지 않으면, 시스템에서 다른 어플리케이션과 MySQL을 처리할 때 datetime의 차이가 발생하게 된다.

리플리케이션 설정에서의 타임 존 설정? 알려져 있는 문제점들”을 참조할 것.

출처 : MySQL 코리아