2026년 08월 11일 | DBMS Error 가이드
이 글에서 다루는 내용
22019 에러의 원인 분석, 해결 SQL, 예방 방법을 실무 관점에서 정리합니다.
22019 invalid escape character 는?
PostgreSQL 에러 코드 22019는 LIKE 또는 SIMILAR TO 연산자를 사용할 때 이스케이프 문자(escape character)가 올바르지 않게 지정되었을 때 발생합니다. 이 에러는 주로 ESCAPE 절에 단일 문자가 아닌 값(빈 문자열, 두 글자 이상의 문자열 등)을 지정하거나, 특수한 방식으로 이스케이프 문자를 처리할 때 나타납니다. SQL 표준에 따르면 이스케이프 문자는 정확히 하나의 문자여야 하며, 이 규칙을 위반할 경우 PostgreSQL은 즉시 이 에러를 반환합니다.
주요 발생 원인
- ESCAPE 절에 잘못된 길이의 문자열 사용
가장 흔한 원인은 LIKE 또는 SIMILAR TO의 ESCAPE 절에 단일 문자가 아닌 문자열을 제공하는 경우입니다. SQL 표준과 PostgreSQL 명세 모두 이스케이프 문자는 반드시 정확히 1개의 문자여야 한다고 규정하고 있습니다. 예를 들어 ESCAPE ''처럼 빈 문자열을 사용하거나, ESCAPE '\\'처럼 두 글자 이상의 문자열을 사용하면 이 에러가 발생합니다.
- 애플리케이션 레이어에서 동적으로 생성된 이스케이프 문자 오류
ORM(Object-Relational Mapping) 도구나 애플리케이션 코드에서 동적으로 SQL 쿼리를 생성할 때, 이스케이프 문자 부분이 잘못 처리되어 에러가 발생하는 경우가 많습니다. 특히 사용자 입력값을 그대로 이스케이프 문자로 사용하려 할 때, 입력값의 길이 검증을 생략하면 런타임에서 이 에러가 발생할 수 있습니다. 이런 경우에는 쿼리 생성 로직을 점검하고 반드시 단일 문자인지 확인해야 합니다.
- standard_conforming_strings 설정과 이스케이프 처리 혼동
PostgreSQL의 standard_conforming_strings 설정에 따라 백슬래시(\)의 해석 방식이 달라집니다. 이 설정이 on인 경우(PostgreSQL 9.1 이후 기본값) 백슬래시는 일반 문자로 처리되며, 이스케이프 시퀀스로 사용하려면 E'' 리터럴을 사용해야 합니다. 이 설정을 잘못 이해하고 쿼리를 작성하면 의도하지 않은 이스케이프 문자가 전달되어 22019 에러가 발생할 수 있습니다.
해결 방법
원인 1: ESCAPE 절에 올바른 단일 문자 사용
잘못된 예시와 올바른 예시를 비교하여 수정합니다.
-- ❌ 잘못된 사용: 빈 문자열을 이스케이프 문자로 사용
SELECT * FROM products
WHERE product_code LIKE '10\%' ESCAPE '';
-- ❌ 잘못된 사용: 두 글자 이상의 문자열을 이스케이프 문자로 사용
SELECT * FROM products
WHERE product_code LIKE '10!_%' ESCAPE '!!';
-- ✅ 올바른 사용: 정확히 한 글자의 이스케이프 문자 사용
SELECT * FROM products
WHERE product_code LIKE '10!%' ESCAPE '!';
-- ✅ 올바른 사용: 기본 이스케이프 문자인 백슬래시 사용
SELECT * FROM products
WHERE product_code LIKE '10\%' ESCAPE '\';
원인 2: 동적 쿼리에서의 이스케이프 처리
애플리케이션에서 동적으로 쿼리를 생성할 때는 이스케이프 문자의 길이를 반드시 검증해야 합니다.
-- PL/pgSQL에서 동적 LIKE 쿼리를 안전하게 사용하는 예시
CREATE OR REPLACE FUNCTION search_products(p_pattern TEXT)
RETURNS TABLE(product_id INT, product_name TEXT) AS $$
DECLARE
v_escape_char CHAR(1) := '!';
v_safe_pattern TEXT;
BEGIN
-- 패턴 내의 특수문자를 이스케이프 처리
v_safe_pattern := replace(replace(replace(p_pattern, '!', '!!'), '%', '!%'), '_', '!_');
RETURN QUERY
SELECT p.product_id, p.product_name
FROM products p
WHERE p.product_name LIKE '%' || v_safe_pattern || '%' ESCAPE v_escape_char;
END;
$$ LANGUAGE plpgsql;
-- 함수 호출 예시
SELECT * FROM search_products('50% discount');
SELECT * FROM search_products('size_L item');
원인 3: standard_conforming_strings 설정에 따른 올바른 이스케이프 처리
-- 현재 설정 확인
SHOW standard_conforming_strings;
-- standard_conforming_strings = on 일 때 (기본값, PostgreSQL 9.1+)
-- 백슬래시를 이스케이프 문자로 사용하려면 명시적으로 ESCAPE 절 지정
SELECT * FROM orders
WHERE order_ref LIKE '100\%' ESCAPE '\';
-- E'' 리터럴을 사용하는 방법 (이전 버전 호환)
SELECT * FROM orders
WHERE order_ref LIKE E'100\\%' ESCAPE E'\\';
-- 권장 방법: 백슬래시 외의 문자를 이스케이프 문자로 사용하여 혼동 방지
SELECT * FROM orders
WHERE order_ref LIKE '100#%' ESCAPE '#';
-- SIMILAR TO 에서의 올바른 사용
SELECT * FROM customers
WHERE email SIMILAR TO '%(gmail|yahoo)\.com' ESCAPE '\';
추가: LIKE 패턴 이스케이프 헬퍼 함수 만들기
-- 실무에서 사용할 수 있는 LIKE 패턴 이스케이프 유틸리티 함수
CREATE OR REPLACE FUNCTION escape_like_pattern(
p_input TEXT,
p_escape_char CHAR(1) DEFAULT '!'
)
RETURNS TEXT AS $$
BEGIN
-- 이스케이프 문자 자체를 먼저 이스케이프하고, 그 다음 % 와 _ 처리
RETURN replace(
replace(
replace(p_input, p_escape_char, p_escape_char || p_escape_char),
'%', p_escape_char || '%'
),
'_', p_escape_char || '_'
);
END;
$$ LANGUAGE plpgsql IMMUTABLE STRICT;
-- 사용 예시
SELECT * FROM products
WHERE product_name LIKE '%' || escape_like_pattern('50% off_sale') || '%' ESCAPE '!';
-- 결과 확인용 테스트
SELECT escape_like_pattern('hello_world%test');
-- 결과: hello!_world!%test
예방 방법
- 이스케이프 문자 처리 표준화 및 함수화
프로젝트 전반에 걸쳐 LIKE 패턴에 사용할 이스케이프 문자를 하나로 통일하고, 위에서 소개한 escape_like_pattern() 같은 유틸리티 함수를 공통 라이브러리로 만들어 사용하세요. 이렇게 하면 개별 쿼리마다 이스케이프 처리를 직접 구현하는 실수를 방지할 수 있으며, 코드 리뷰 시 일관성을 유지할 수 있습니다. 또한 팀 내 코딩 컨벤션 문서에 이스케이프 문자 사용 규칙을 명시적으로 기재하여 신규 개발자도 즉시 올바른 방법을 적용할 수 있도록 하세요.
- 입력값 검증 및 파라미터 바인딩 적극 활용
애플리케이션 레이어에서 사용자 입력값을 SQL 쿼리에 직접 삽입하지 말고, 반드시 준비된 구문(Prepared Statement)과 파라미터 바인딩을 사용하세요. 또한 이스케이프 문자로 사용할 값은 항상 길이 검증(정확히 1자)을 수행하는 로직을 추가하고, 단위 테스트에 경계 케이스(빈 문자열, 특수문자 포함 문자열 등)를 포함시켜 배포 전에 에러를 사전에 발견할 수 있도록 하세요.
관련 에러
- 22025 (invalid_escape_sequence): 이스케이프 문자 자체는 유효하지만, 이스케이프 시퀀스의 구성이 올바르지 않을 때 발생합니다. 예를 들어
E'\q'처럼 유효하지 않은 이스케이프 시퀀스를 사용하는 경우입니다. - 2200C (invalid_use_of_escape_character): 이스케이프 문자가 허용되지 않는 컨텍스트에서 사용되었을 때 발생하는 에러입니다.
- 22021 (character_not_in_repertoire): 문자 인코딩 변환 시 해당 문자가 대상 인코딩에 존재하지 않을 때 발생하며, 이스케이프 처리와 관련된 인코딩 문제 해결 시 함께 확인할 필요가 있습니다.
- 42601 (syntax_error): 이스케이프 문자 관련 구문 자체가 완전히 잘못된 경우 22019 대신 구문 오류로 처리될 수 있으며, 두 에러를 혼동하지 않도록 주의해야 합니다.
주요 DBMS error code를 정리하는 시리즈입니다.
블로그 홈에서 다른 에러도 확인하세요.
본 포스트는 AI가 생성한 기술 가이드입니다. 운영 환경 적용 전 충분한 검토를 권장합니다.