Oracle ORA-30036 오류 원인과 해결 방법 완벽 가이드

ORA-30036
2026년 10월 09일 | DBMS Error 가이드

이 글에서 다루는 내용

ORA-30036 에러의 원인 분석, 해결 SQL, 예방 방법을 실무 관점에서 정리합니다.

ORA-30036 unable to extend segment in undo tablespace 는?

ORA-30036 에러는 Oracle 데이터베이스가 Undo 테이블스페이스 내에서 세그먼트를 확장할 수 없을 때 발생하는 오류입니다. 주로 대용량 DML(INSERT, UPDATE, DELETE) 작업 중 Undo 공간이 부족해지거나, Undo 테이블스페이스의 크기가 너무 작게 설정되어 있을 때 나타납니다. 이 에러가 발생하면 진행 중인 트랜잭션이 롤백되며, 데이터 정합성 문제로 이어질 수 있으므로 신속한 조치가 필요합니다.


주요 발생 원인

1. Undo 테이블스페이스 용량 부족

가장 흔한 원인으로, Undo 테이블스페이스에 할당된 물리적 공간이 현재 수행 중인 트랜잭션의 Undo 데이터를 저장하기에 부족한 경우입니다. 특히 대량의 데이터를 한 번에 처리하는 배치 작업이나 야간 ETL 작업 시 자주 발생합니다. Autoextend 옵션이 비활성화되어 있거나, 디스크 공간 자체가 부족한 경우 에러가 트리거됩니다.

2. UNDO_RETENTION 파라미터와 실제 공간의 불일치

UNDO_RETENTION 파라미터가 높게 설정되어 있으면, Oracle은 해당 시간 동안 Undo 데이터를 보존하려 합니다. 이때 새로운 트랜잭션을 위한 Undo 공간이 부족해질 수 있습니다. Retention Guarantee 옵션이 활성화된 경우, Oracle이 기존 Undo 데이터를 덮어쓰지 않아 공간 부족이 더욱 심화됩니다.

3. 장시간 실행되는 트랜잭션 (Long-running Transaction)

오랫동안 커밋되지 않은 트랜잭션은 해당 트랜잭션이 시작된 시점부터 현재까지의 모든 Undo 정보를 점유합니다. 여러 세션에서 동시에 대규모 DML 작업이 진행되는 경우, Undo 공간 경합이 발생하여 ORA-30036이 트리거됩니다. 특히 커밋 없이 반복적인 UPDATE를 수행하는 애플리케이션 로직 버그가 주요 원인이 되기도 합니다.


해결 방법

1. 현재 Undo 테이블스페이스 상태 확인

문제를 진단하기 위해 먼저 현재 Undo 테이블스페이스의 사용 현황을 확인합니다.

-- Undo 테이블스페이스 사용량 확인
SELECT tablespace_name,
       ROUND(SUM(bytes) / 1024 / 1024, 2)       AS total_mb,
       ROUND(SUM(CASE WHEN status = 'EXPIRED' THEN bytes ELSE 0 END) / 1024 / 1024, 2)  AS expired_mb,
       ROUND(SUM(CASE WHEN status = 'UNEXPIRED' THEN bytes ELSE 0 END) / 1024 / 1024, 2) AS unexpired_mb,
       ROUND(SUM(CASE WHEN status = 'ACTIVE' THEN bytes ELSE 0 END) / 1024 / 1024, 2)   AS active_mb
FROM   dba_undo_extents
GROUP  BY tablespace_name;

-- Undo 테이블스페이스 데이터 파일 크기 및 여유 공간 확인
SELECT file_name,
       ROUND(bytes / 1024 / 1024, 2)     AS file_size_mb,
       autoextensible,
       ROUND(maxbytes / 1024 / 1024, 2)  AS max_size_mb
FROM   dba_data_files
WHERE  tablespace_name = (SELECT value FROM v$parameter WHERE name = 'undo_tablespace');

2. Undo 테이블스페이스 크기 확장

가장 빠른 해결책은 Undo 테이블스페이스에 데이터 파일을 추가하거나 기존 파일 크기를 늘리는 것입니다.

-- 방법 1: 기존 데이터 파일 크기 확장
ALTER DATABASE DATAFILE '/u01/app/oracle/oradata/ORCL/undotbs01.dbf'
RESIZE 4096M;

-- 방법 2: Autoextend 활성화
ALTER DATABASE DATAFILE '/u01/app/oracle/oradata/ORCL/undotbs01.dbf'
AUTOEXTEND ON NEXT 512M MAXSIZE 8192M;

-- 방법 3: 새로운 데이터 파일 추가
ALTER TABLESPACE UNDOTBS1
ADD DATAFILE '/u01/app/oracle/oradata/ORCL/undotbs02.dbf'
SIZE 2048M AUTOEXTEND ON NEXT 512M MAXSIZE 8192M;

3. 장시간 실행 중인 트랜잭션 식별 및 처리

-- 현재 활성화된 장시간 트랜잭션 조회
SELECT s.sid,
       s.serial#,
       s.username,
       s.status,
       t.start_time,
       ROUND((SYSDATE - TO_DATE(t.start_time, 'MM/DD/YY HH24:MI:SS')) * 24 * 60, 2) AS elapsed_min,
       t.used_ublk * 8192 / 1024 / 1024 AS undo_used_mb,
       s.sql_id,
       s.program
FROM   v$transaction t
JOIN   v$session     s ON t.ses_addr = s.saddr
ORDER  BY elapsed_min DESC;

-- 문제가 되는 세션 강제 종료 (필요 시)
ALTER SYSTEM KILL SESSION '&sid, &serial#' IMMEDIATE;

4. UNDO_RETENTION 파라미터 조정

-- 현재 UNDO_RETENTION 값 확인
SHOW PARAMETER undo_retention;

-- UNDO_RETENTION 값 낮추기 (공간 부족 시 임시 조치)
ALTER SYSTEM SET UNDO_RETENTION = 900 SCOPE = BOTH;

-- Retention Guarantee 해제 (강제 보존 옵션 제거)
ALTER TABLESPACE UNDOTBS1 RETENTION NOGUARANTEE;

-- 현재 Retention Guarantee 설정 확인
SELECT tablespace_name, retention
FROM   dba_tablespaces
WHERE  contents = 'UNDO';

5. 새로운 Undo 테이블스페이스로 전환 (장기적 해결책)

-- 새 Undo 테이블스페이스 생성
CREATE UNDO TABLESPACE UNDOTBS2
DATAFILE '/u01/app/oracle/oradata/ORCL/undotbs2_01.dbf'
SIZE 4096M AUTOEXTEND ON NEXT 512M MAXSIZE 20480M;

-- 새 Undo 테이블스페이스로 전환
ALTER SYSTEM SET UNDO_TABLESPACE = UNDOTBS2 SCOPE = BOTH;

-- 기존 Undo 테이블스페이스 상태 확인 후 삭제 (선택)
DROP TABLESPACE UNDOTBS1 INCLUDING CONTENTS AND DATAFILES;

6. 대용량 DML의 배치 처리 (애플리케이션 레벨 해결책)

-- 한 번에 전체 처리 대신 배치로 나눠서 처리하는 예시
DECLARE
  v_batch_size NUMBER := 10000;
  v_count      NUMBER := 0;
BEGIN
  LOOP
    UPDATE large_table
    SET    status = 'PROCESSED'
    WHERE  status = 'PENDING'
      AND  ROWNUM <= v_batch_size;

    v_count := SQL%ROWCOUNT;
    COMMIT;  -- 배치마다 커밋으로 Undo 공간 해제

    EXIT WHEN v_count = 0;
  END LOOP;
  DBMS_OUTPUT.PUT_LINE('처리 완료');
END;
/

예방 방법

1. Undo 테이블스페이스 모니터링 자동화

Undo 테이블스페이스의 사용량을 주기적으로 모니터링하는 스크립트를 스케줄러에 등록하고, 임계치(예: 80%) 초과 시 자동 알림을 받도록 설정합니다. Oracle Enterprise Manager(OEM)나 커스텀 스크립트를 활용하여 사전 경고 체계를 구축하는 것이 중요합니다. 또한 Autoextend를 활성화하고 최대 크기를 넉넉하게 설정하여 디스크가 허용하는 한 자동으로 확장될 수 있도록 구성해 두는 것이 실무에서 권장됩니다.

-- Undo 사용률 모니터링 쿼리 (스케줄러 등록용)
SELECT ROUND(
         (1 - (NVL(t.free_space, 0) / t.total_space)) * 100, 2
       ) AS used_pct
FROM (
  SELECT SUM(df.bytes) / 1024 / 1024 AS total_space,
         (SELECT SUM(bytes) / 1024 / 1024
          FROM   dba_free_space
          WHERE  tablespace_name = 'UNDOTBS1') AS free_space
  FROM   dba_data_files df
  WHERE  df.tablespace_name = 'UNDOTBS1'
) t;

2. 적절한 UNDO_RETENTION 값과 테이블스페이스 크기의 균형 유지

Undo 테이블스페이스의 크기는 UNDO_RETENTION × 초당 Undo 생성량(UPS)을 기반으로 산정해야 합니다. Oracle의 V$UNDOSTAT 뷰를 활용하여 실제 워크로드 기반의 권장 크기를 계산하고, 이를 테이블스페이스 설계에 반영하는 것이 Best Practice입니다.

-- 권장 Undo 테이블스페이스 크기 계산
SELECT ROUND(
         (UR * (UPS * DBS)) / 1024 / 1024, 2
       ) AS recommended_undo_mb
FROM (
  SELECT MAX(undoblks / ((end_time - begin_time) * 86400)) AS ups,
         (SELECT TO_NUMBER(value)
          FROM   v$parameter
          WHERE  name = 'undo_retention')                  AS ur,
         (SELECT TO_NUMBER(value)
          FROM   v$parameter
          WHERE  name = 'db_block_size')                   AS dbs
  FROM   v$undostat
  WHERE  end_time > SYSDATE - 7  -- 최근 7일 데이터 기준
);

관련 에러

  • ORA-01555 (Snapshot too old): Undo 데이터가 너무 빨리 덮어쓰여져 읽기 일관성을 유지할 수 없을 때 발생합니다. ORA-30036과 반대 성격의 에러로, Undo 공간이 부족하면 ORA-30036, 보존 기간이 짧으면 ORA-01555가 발생합니다.
  • ORA-30035: Undo 세그먼트 자체를 확장할 수 없는 경우로, ORA-30036과 유사하지만 세그먼트 레벨에서 발생합니다.
  • ORA-01650 / ORA-01653: 일반 테이블스페이스의 세그먼트 확장 불가 에러로, Undo가 아닌 다른 테이블스페이스에서 같은 맥락으로 발생합니다.
  • ORA-02002: Undo 세그먼트를 오프라인으로 설정하려 할 때 활성 트랜잭션이 있는 경우 발생하며, Undo 관리 작업 중 마주칠 수 있습니다.

DBMS 에러 코드 시리즈

주요 DBMS error code를 정리하는 시리즈입니다.
블로그 홈에서 다른 에러도 확인하세요.

본 포스트는 AI가 생성한 기술 가이드입니다. 운영 환경 적용 전 충분한 검토를 권장합니다.

댓글 남기기