리눅스 태블로 서버에서 Oracle 'ORA-01861' 에러 해결하기

리눅스 태블로 서버에서 Oracle 데이터 원본 조회 시 발생하는 ORA-01861 에러의 원인(세션 로케일 차이)과 2가지 해결 방법(서비스 로케일 변경 및 명시적 날짜 변환)을 정리합니다.

리눅스 태블로 서버에서 Oracle 'ORA-01861' 에러 해결하기

리눅스 기반 태블로 서버(Tableau Server)에서 Oracle 데이터 원본을 사용할 때, 태블로 데스크탑에서는 정상적으로 조회되던 데이터가 서버에서만 다음 오류로 실패할 수 있습니다.

ORA-01861: literal does not match format string

Root Cause

이 오류는 문자열을 포맷 마스크 없이 날짜로 변환하는 쿼리(암묵적 변환)에서 발생합니다. Oracle은 이 변환에 세션의 NLS_DATE_FORMAT을 사용하는데, 이 값은 접속하는 클라이언트의 로케일에 따라 달라집니다. 한국어 윈도우 환경에서는 RR/MM/DD, 영문 로케일의 리눅스 태블로 서버에서는 DD-MON-RR이 적용되므로 같은 쿼리가 서버에서만 실패합니다. 뷰 정의 안의 암묵적 변환도 호출하는 세션을 기준으로 실행되므로, 태블로에서 해당 컬럼을 문자열로 가져와도 오류가 발생합니다.

리눅스 태블로 서버는 설치 시점의 시스템 로케일을 아래 파일에 기록하고, 서비스를 실행할 때 이 값을 사용합니다. 따라서 설치 후 OS 로케일을 변경해도 서비스에는 반영되지 않습니다. Oracle JDBC 드라이버는 NLS_LANG 환경변수도 참조하지 않습니다.

~tableau/.config/systemd/tableau_server.conf.d/10-lang.conf

현재 세션 값은 아래 쿼리를 사용자 지정 SQL로 만든 시트를 서버에 게시하여 확인할 수 있습니다.

SELECT parameter, value
FROM nls_session_parameters
WHERE parameter IN ('NLS_LANGUAGE','NLS_TERRITORY','NLS_DATE_FORMAT')

Solution

이 문제는 두 가지 방법으로 해결할 수 있습니다.

방법 1. 태블로 서버의 서비스 로케일 변경
수정할 쿼리나 뷰가 많을 때 적합한 방법입니다. 10-lang.conf의 로케일을 ko_KR.UTF-8로 변경한 뒤 서비스를 재시작합니다. 절차는 태블로 공식 문서의 포워드 프록시 설정 방식과 동일합니다.

tsm stop
sudo su -l tableau
sed -i 's/^LANG=.*/LANG=ko_KR.UTF-8/' ~/.config/systemd/tableau_server.conf.d/10-lang.conf
exit
sudo /opt/tableau/tableau_server/packages/scripts.<version>/stop-administrative-services
sudo /opt/tableau/tableau_server/packages/scripts.<version>/start-administrative-services
tsm restart

적용 후 위의 확인 시트에서 KOREAN, KOREA, RR/MM/DD가 조회되면 정상입니다.

방법 2. SQL에서 명시적으로 변환
뷰나 사용자 지정 SQL의 암묵적 변환에 포맷을 명시하면 서버 환경과 관계없이 동일하게 동작합니다.

WHERE 날짜컬럼 >= TO_DATE('2020-01-01', 'YYYY-MM-DD')

태블로에서 문자열 컬럼을 날짜로 사용할 때는 데이터 타입을 직접 변경하는 대신 DATEPARSE를 사용합니다. 포맷이 명시된 TO_DATE로 변환되어 전송됩니다.

DATEPARSE("yyyy-MM-dd", [CLOSE_DATE])

💡
10-lang.conf는 파일이 이미 존재하면 설치 스크립트가 다시 생성하지 않으므로, 변경한 로케일은 버전 업그레이드 후에도 유지됩니다. 신규 설치 시에는 initialize-tsm 실행 전에 OS 로케일을 ko_KR.UTF-8로 설정하면 처음부터 한국어 로케일로 구성됩니다.