惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

云风的 BLOG
云风的 BLOG
Security Archives - TechRepublic
Security Archives - TechRepublic
V
Vulnerabilities – Threatpost
C
CXSECURITY Database RSS Feed - CXSecurity.com
P
Proofpoint News Feed
G
GRAHAM CLULEY
P
Privacy International News Feed
The Hacker News
The Hacker News
Forbes - Security
Forbes - Security
U
Unit 42
N
News and Events Feed by Topic
D
Darknet – Hacking Tools, Hacker News & Cyber Security
C
Cyber Attacks, Cyber Crime and Cyber Security
C
Cisco Blogs
A
About on SuperTechFans
cs.CV updates on arXiv.org
cs.CV updates on arXiv.org
D
Docker
I
Intezer
Spread Privacy
Spread Privacy
The Last Watchdog
The Last Watchdog
V2EX - 技术
V2EX - 技术
S
Security @ Cisco Blogs
F
Full Disclosure
S
Secure Thoughts
M
MIT News - Artificial intelligence
Microsoft Security Blog
Microsoft Security Blog
G
Google Developers Blog
aimingoo的专栏
aimingoo的专栏
W
WeLiveSecurity
cs.CL updates on arXiv.org
cs.CL updates on arXiv.org
Project Zero
Project Zero
Recorded Future
Recorded Future
Cyberwarzone
Cyberwarzone
S
Security Affairs
AWS News Blog
AWS News Blog
H
Help Net Security
The GitHub Blog
The GitHub Blog
Hacker News: Ask HN
Hacker News: Ask HN
Vercel News
Vercel News
P
Proofpoint News Feed
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
The Register - Security
The Register - Security
S
Schneier on Security
F
Fortinet All Blogs
C
CERT Recently Published Vulnerability Notes
L
LINUX DO - 最新话题
T
Tor Project blog
T
The Exploit Database - CXSecurity.com
MongoDB | Blog
MongoDB | Blog
Webroot Blog
Webroot Blog

DEV Community

Authentication Security Deep Dive: From Brute Force to Salted Hashing (With Java Examples) Why AI Systems Don’t Fail — They Drift Spilling beans for how i learn for exam😁"Reinforcement Learning Cheat Sheet" I Replaced Chrome with Safari for AI Browser Automation. Here's What Broke (and What Finally Worked) How Python Borrows Other People's Work The $40 Architecture: Processing 1 Billion API Requests with 99.99% Uptime Vibe Coding: A Workflow Guide (From Zero to SaaS) Most webhook security guides protect the wrong side. The scary part is delivery. Headless CMS for TanStack Start: Build a Blog with Cosmic EU Age Verification App "Hacked in 2 Minutes" — What Actually Happened Comfy Cloud’s delete function does not actually remove files Running AI Models on GPU Cloud Servers: A Beginner Guide Event-driven media intelligence with AWS Step Functions and Bedrock I scored 500 AI prompts across 8 quality dimensions — here's what broke How to Call Google Gemini API from Next.js (Free Tier, No Backend Needed) The Portal Protocol: Reclaiming Human Connection in the Age of AI How to Fix Your Team's Scattered Knowledge Problem With a Self-Hosted Forum Intro to tc Cloud Functors: A Graph-First Mental Model for the Modern Cloud Designing Multi-Tenant Backends With Both Ownership and Team Access I Built a Neumorphic CSS Library with 77+ Components — Here's What I Learned PostgreSQL Performance Optimization: Why Connection Pooling Is Critical at Scale Cómo construí un SaaS multi-rubro para gestionar expensas en Argentina con FastAPI + Vue 3 🚀 I Built an Ethical Hacking Scanner Tool – Open Source Project I Replaced /usage and /context in Claude Code With a Single Statusline A Pythonic Way to Handle Emails (IMAP/SMTP) with Auto-Discovery and AI-Ready Design I Collected 8.9 Million Polymarket Price Points — Here's What I Found About How Markets Really Move EcoTrack AI — Carbon Footprint Tracker & Dashboard Everyone's Using AI. No One Agrees How. 5 self-hosted ebook managers worth trying in 2026 Building Your First AI Agent with LangChain: From Chatbot to Autonomous Assistant Common SOC 2 Failures (Real World) Stop Vibe-Checking Your AI App: A Practical Guide to Evals How to Use SonarQube and SonarScanner Locally to Level Up Your Code Quality Your Next To-Do App Is Dead — I Replaced Mine with an OpenClaw AI Sign a Nostr event in 60 lines of Python using coincurve — no nostr-sdk, no nbxplorer, no rust toolchain ITGC Audit Explained Like You’re in Big 4 Patch Tuesday abril 2026: Microsoft parcha 163 vulnerabilidades y un zero-day en SharePoint Stop scraping everything: a better way to track competitor price changes Listing on MCPize + the Official MCP Registry while routing payments OUTSIDE the marketplace — how I kept 100% of my x402 revenue Building an AI-Powered Risk Intelligence System Using Serverless Architecture Why We Ripped Function Overloading Out of Our AI Toolchain Testing AI-Generated Code: How to Actually Know If It Works SaaS Churn Is Killing Your Business. Here Is What to Do About It (Without a Support Team) The Speed of AI Is No Longer Linear - And Self-Improving Models Are Why How to Implement RBAC for MCP Tools: A Practical Guide for Engineering Teams From Standard Quote to Persuasive Proposal: AI Automation for Arborists I built a CLI that scaffolds complete multi-tenant SaaS apps Axios CVE-2025–62718: The Silent SSRF Bug That Could Be Hiding in Your Node.js App Right Now The dashboard that ended our friendship Data Pipelines Explained Simply (and How to Build Them with Python) The Hidden Cost of AI Systems Nobody Talks About. undefined vs undeclared, and how typeof behaves Switching from file-based jobs to NATS/Kafka in Rust without changing code io_uring Adventures: Rust Servers That Love Syscalls Why Agentic AI is Killing the Traditional Database The POUR principles of web accessibility for developers and designers Quantum Neural Network 3D — A Deep Dive into Interactive WebGL Visualization How To Install Caveman In Codex On macOS And Windows Automation Pipeline Reliability: Why Your Workflow Breaks When Nobody Is Watching I Built an 'Open World' AI Coding Agent — It Works From ANY Folder From Freelancing to Product: A Tech Service Company's SaaS Transformation China's AI Giants: Adding Tencent Hunyuan & ByteDance Doubao to AI University (74 Providers) On the Vibe Coders and Their Lies clerk: Auto-Summarize Your Claude Code Sessions AI Weekly — 2026/04/10–04/17 | The Model Lockdown Is Here, but the Toolchain Is the Real Battleground AI 週報 — 2026/04/10–2026/04/17 模型封鎖潮來了,但工具鏈才是真戰場 Maybe this is how Open-Source apps are born... 🚀 Fine-Tune LLMs with LoRA and QLoRA: 2026 Guide tRPC v11 + Next.js App Router: End-to-End Type Safety Without the Boilerplate ShadCN UI in 2026: Why I Stopped Installing Component Libraries and Started Owning My Components SaaS Billing in React Server Components: Stripe + Supabase Without a Single `useEffect` Join our DEV Weekend Challenge — $1,000 in Prizes Across TEN winners! Submissions Due April 20 at 6:59 AM UTC. Implementing FSRS Spaced Repetition in Flutter + Supabase — Adding Memory Science to an AI Learning App "I Texted My Localhost From the Train — Claude Code Fixed the Bug Before I Got Home" I Built a Sales Prep AI and It Went Deeper Than Expected Design to Code #2: One JSON, Eleven Outputs Solving the 100M-Row Problem: A Summary Table Pattern for High-Volume Push Notification Logs Flutter Web With Wasm: What Actually Changes For Developers I Built 50 Royalty-Free Soundtracks for My Side Project in a Weekend Using AI Music Generation The Vibe Coding Security Checklist: 7 Things to Check Before You Ship Stop Letting Googlebot Guess Fix Your React App's SEO Right Desconstruindo o Streaming do LinkedIn: Como Criar um Engine de Extração de Vídeo de Alta Performance com HLS e FFmpeg (EDA Part-1) EDA (Exploratory Data Analysis) Explained With Real Life — Why Looking at Your Data Is the Most Important Step in Machine Learning Brand Relationship Management at Scale: Our 4-Touch Outreach System for 200+ Brands Why String.fromEnvironment() Might Return an Empty String in Dart JGuardrails 1.0.0 — Hardening Java LLM Apps Against Jailbreaks, Toxicity, and Prompt Injection Plan and Schedule a Full Week of Threads Content From One Claude Conversation Coding Cat Oran Ep3, Five Tables Changed Everything Updated: BFF Pattern I'm done watching freelancers get buried by 200 proposals. So I'm building the alternative. This is my first post BFS Algorithm in Java Step by Step Tutorial with Examples Tracking LLM Pricing Monthly: An Open Dataset for 22 AI Models How We Measure Content ROI on a Comparison Site: Revenue Attribution Without Perfect Data Introducing Nova AI Ops: The AI-Native Operating System for SRE Teams I built a free desktop video downloader for Windows — Grabbit How Talkie OCR Helps Vision-Impaired & Dyslexic Users Read the World Around Them VRCFaceTracking安装和iPhone面捕配置教程,有bug Even CrowdStrike Can't See Your Agents The Automation Gold Rush: What n8n Workflows and Claude Are Opening Up for Developers Right Now
Oracle ORA-00055 오류 원인과 해결 방법 완벽 가이드
umzzil nng · 2026-05-30 · via DEV Community

umzzil nng

ORA-00055 maximum number of DML locks exceeded 는?

ORA-00055 에러는 Oracle 데이터베이스에서 DML(Data Manipulation Language) 잠금(Lock)의 최대 허용 개수를 초과했을 때 발생하는 에러입니다. Oracle은 INSERT, UPDATE, DELETE, MERGE 등의 DML 작업 시 해당 테이블에 대한 테이블 수준의 DML 잠금(TM Lock)을 내부적으로 관리하는데, 이 잠금을 저장하는 내부 구조체(Enqueue)의 슬롯이 모두 소진되면 이 에러가 발생합니다. 주로 동시에 수백~수천 개의 세션이 다수의 테이블에 대해 DML을 수행하는 대용량 OLTP 환경이나 배치 처리 환경에서 나타나며, 서비스 중단으로 이어질 수 있어 신속한 조치가 필요합니다.


주요 발생 원인

1. DML_LOCKS 파라미터 값이 너무 낮게 설정된 경우

DML_LOCKS 초기화 파라미터는 인스턴스 전체에서 허용되는 DML 잠금의 최대 개수를 결정합니다. 기본값은 4 * TRANSACTIONS 값으로 자동 계산되지만, 트랜잭션 수가 급증하거나 초기 설정 당시 예상보다 훨씬 많은 동시 DML이 발생하는 경우 이 값이 턱없이 부족해질 수 있습니다. 특히 애플리케이션 기능이 추가되거나 사용자 수가 급격히 늘어난 시스템에서 자주 목격됩니다.

2. 하나의 트랜잭션에서 지나치게 많은 테이블을 동시에 조작하는 경우

단일 트랜잭션 내에서 수십~수백 개의 테이블에 순차적으로 DML을 수행하면, 트랜잭션이 완료(COMMIT 또는 ROLLBACK)되기 전까지 해당 테이블 수만큼 DML 잠금이 점유된 채 유지됩니다. 배치 프로그램이나 복잡한 ERP 트랜잭션에서 이런 패턴이 많고, 커밋 없이 장시간 실행되는 배치 작업이 잠금을 독식하는 상황이 발생합니다. 결국 다른 세션이 잠금 슬롯을 할당받지 못해 ORA-00055가 연쇄적으로 발생하게 됩니다.

3. 커밋 없이 장시간 유지되는 미완료 트랜잭션(Long-Running Transaction)

명시적인 COMMIT 없이 오랜 시간 유지되는 트랜잭션은 DML 잠금 슬롯을 계속 점유합니다. 특히 애플리케이션 로직에서 예외 처리가 미흡하거나, 커넥션 풀에서 세션이 트랜잭션을 열어 놓은 채 반환되는 경우, 해당 슬롯이 해제되지 않아 점차 가용 슬롯이 줄어듭니다. 이런 좀비(Zombie) 트랜잭션이 누적될 경우 순간적으로 DML 잠금 한계에 도달할 수 있습니다.


해결 방법

원인 1 해결: DML_LOCKS 파라미터 값 증가

먼저 현재 설정값과 실제 사용량을 확인합니다.

-- 현재 DML_LOCKS 파라미터 값 확인
SHOW PARAMETER DML_LOCKS;

-- 또는
SELECT name, value, description
FROM   v$parameter
WHERE  name = 'dml_locks';

-- 현재 시스템에서 사용 중인 DML Lock(Enqueue) 현황 확인
SELECT inst_id,
       eq_type,
       total_req#,
       total_wait#,
       succ_req#,
       failed_req#
FROM   gv$enqueue_stat
WHERE  eq_type = 'TM'
ORDER BY inst_id;

-- 현재 활성화된 DML Lock 세부 현황
SELECT s.sid,
       s.serial#,
       s.username,
       s.status,
       l.type,
       l.lmode,
       l.request,
       o.object_name,
       o.object_type
FROM   v$lock l
JOIN   v$session s ON l.sid = s.sid
JOIN   dba_objects o ON l.id1 = o.object_id
WHERE  l.type = 'TM'
ORDER BY s.sid;

충분한 여유값을 확인한 후 파라미터를 동적으로 변경합니다. DML_LOCKS동적 파라미터가 아니므로 SPFILE 변경 후 재기동이 필요합니다.

-- SPFILE을 사용하는 경우 (재기동 후 적용)
ALTER SYSTEM SET DML_LOCKS = 10000 SCOPE = SPFILE;

-- 변경 후 DB 재기동
-- SHUTDOWN IMMEDIATE;
-- STARTUP;

-- 변경 확인
SELECT name, value
FROM   v$spparameter
WHERE  name = 'dml_locks';

⚠️ 주의: DML_LOCKS = 0으로 설정하면 DML 잠금 자체를 비활성화할 수 있으나, 이 경우 DROP TABLE, TRUNCATE 등 DDL 작업이 불가능해지므로 운영 환경에서는 절대 권장하지 않습니다.


원인 2 해결: 트랜잭션 범위 최소화 및 배치 분리

하나의 트랜잭션에서 처리하는 테이블 수를 줄이고, 적절한 중간 COMMIT을 삽입합니다.

-- 나쁜 예시: 하나의 트랜잭션에서 수십 개 테이블 처리
BEGIN
    UPDATE table_01 SET col1 = 'A' WHERE condition;
    UPDATE table_02 SET col1 = 'B' WHERE condition;
    -- ... table_03 ~ table_99 반복 ...
    UPDATE table_99 SET col1 = 'Z' WHERE condition;
    COMMIT; -- 모든 DML 잠금이 이 시점까지 점유됨
END;
/

-- 좋은 예시: 논리 단위로 분리하여 중간 커밋
BEGIN
    -- 1단계: 마스터 테이블 처리
    UPDATE table_01 SET col1 = 'A' WHERE condition;
    UPDATE table_02 SET col1 = 'B' WHERE condition;
    COMMIT; -- 잠금 즉시 해제

    -- 2단계: 상세 테이블 처리
    UPDATE table_03 SET col1 = 'C' WHERE condition;
    UPDATE table_04 SET col1 = 'D' WHERE condition;
    COMMIT; -- 잠금 즉시 해제
END;
/

-- 대량 배치 처리 시 BULK COLLECT + FORALL + 중간 커밋 패턴
DECLARE
    TYPE t_id_list IS TABLE OF orders.order_id%TYPE;
    l_ids   t_id_list;
    l_limit NUMBER := 1000; -- 배치 사이즈

    CURSOR c_orders IS
        SELECT order_id FROM orders WHERE status = 'PENDING';
BEGIN
    OPEN c_orders;
    LOOP
        FETCH c_orders BULK COLLECT INTO l_ids LIMIT l_limit;
        EXIT WHEN l_ids.COUNT = 0;

        FORALL i IN 1 .. l_ids.COUNT
            UPDATE orders
            SET    status = 'PROCESSING',
                   updated_dt = SYSDATE
            WHERE  order_id = l_ids(i);

        COMMIT; -- 배치 단위 커밋으로 DML 잠금 슬롯 주기적 해제

    END LOOP;
    CLOSE c_orders;
EXCEPTION
    WHEN OTHERS THEN
        ROLLBACK;
        CLOSE c_orders;
        RAISE;
END;
/


원인 3 해결: 장시간 미완료 트랜잭션 탐지 및 정리

-- 장시간 활성 상태의 트랜잭션 탐지 (10분 이상)
SELECT s.sid,
       s.serial#,
       s.username,
       s.machine,
       s.program,
       s.status,
       s.last_call_et       AS idle_seconds,
       t.start_time,
       ROUND((SYSDATE - TO_DATE(t.start_time, 'MM/DD/YY HH24:MI:SS')) * 1440, 2) AS elapsed_min,
       t.used_ublk          AS undo_blocks_used
FROM   v$transaction t
JOIN   v$session s ON t.addr = s.taddr
WHERE  (SYSDATE - TO_DATE(t.start_time, 'MM/DD/YY HH24:MI:SS')) * 1440 > 10
ORDER BY elapsed_min DESC;

-- 특정 세션이 보유한 DML Lock 목록 확인
SELECT l.sid,
       s.serial#,
       s.username,
       s.machine,
       o.owner,
       o.object_name,
       o.object_type,
       DECODE(l.lmode,
              0, 'None',
              1, 'Null',
              2, 'Row Share',
              3, 'Row Exclusive',
              4, 'Share',
              5, 'Share Row Exclusive',
              6, 'Exclusive') AS lock_mode
FROM   v$lock l
JOIN   v$session s ON l.sid = s.sid
JOIN   dba_objects o ON l.id1 = o.object_id
WHERE  l.type = 'TM'
  AND  l.sid = :target_sid; -- 조사할 SID 입력

-- 문제 세션 강제 종료 (최후 수단)
-- 반드시 애플리케이션팀과 협의 후 수행할 것
ALTER SYSTEM KILL SESSION '&sid,&serial#' IMMEDIATE;

-- RAC 환경에서는 inst_id 추가
ALTER SYSTEM KILL SESSION '&sid,&serial#,@&inst_id' IMMEDIATE;


예방 방법

1. DML_LOCKS 파라미터 모니터링 자동화 및 적정값 유지

DML 잠금 사용률이 임계치(예: 80%)를 초과하면 즉시 알림을 받을 수 있도록 모니터링을 구성합니다. 아래 쿼리를 스케줄러에 등록하거나 OEM(Oracle Enterprise Manager) Alert으로 설정해 두면 사전에 문제를 탐지할 수 있습니다.

-- DML_LOCKS 사용률 모니터링 쿼리 (주기적으로 실행)
SELECT p.value                              AS dml_locks_limit,
       COUNT(l.type)                        AS current_tm_locks,
       ROUND(COUNT(l.type) / p.value * 100, 2) AS usage_pct,
       CASE
           WHEN ROUND(COUNT(l.type) / p.value * 100, 2) >= 80
           THEN '⚠️  경고: DML Lock 사용률 80% 초과!'
           ELSE '✅ 정상'
       END AS status
FROM   v$parameter p
LEFT JOIN v$lock l ON l.type = 'TM'
WHERE  p.name = 'dml_locks'
GROUP BY p.value;

운영 환경에서는 현재 최대 TM Lock 사용치의 최소 3~4배 여유를 두고 DML_LOCKS 값을 설정하는 것을 권장합니다. 분기마다 사용 추이를 검토하고, 업무량 증가에 따라 선제적으로 파라미터를 조정하는 관리 프로세스를 수립해야 합니다.

2. 애플리케이션 트랜잭션 설계 원칙 수립 및 코드 리뷰 프로세스 강화

트랜잭션은 가능한 한 짧게(Short Transaction) 유지하고, 한 트랜잭션 내에서 조작하는 테이블 수를 최소화하는 설계 원칙을 팀 내 개발 가이드라인으로 명문화합니다. 배치 프로그램 개발 시에는 반드시 적절한 배치 사이즈와 중간 커밋 로직을 코드 리뷰 체크리스트 항목으로 포함시켜, 문제가 되는 코드가 운영 환경에 배포되기 전에 사전 차단합니다. 또한 커넥션 풀 설정에서 connection-timeoutidle-timeout을 적절히 구성하여 좀비 트랜잭션이 누적되지 않도록 애플리케이션 레벨에서도 방어합니다.


관련 에러

에러 코드 설명
ORA-00060 deadlock detected while waiting for resource — DML 잠금 경합이 심화되면 데드락으로 이어질 수 있음
ORA-04031 unable to allocate shared memory — 잠금 관련 내부 구조체가 Shared Pool 메모리 부족으로 할당 실패할 때 발생
ORA-00054 resource busy and acquire with NOWAIT specified — 잠금 획득 대기 없이 즉시 실패를 요청했을 때 발생하는 관련 에러
ORA-02049 timeout: distributed transaction waiting for lock — 분산 트랜잭션 환경에서 DML 잠금 대기 시간 초과 시 발생
ORA-00257 archiver error — 아카이브 로그 공간 부족으로 DML 자체가 중단될 수 있어, 장시간 트랜잭션 유발 원인이 되기도 함

💡 DBA 팁: ORA-00055는 단독으로 발생하기보다 ORA-00060(데드락), ORA-00054(리소스 점유) 등과 함께 나타나는 경우가 많습니다. AWR(Automatic Workload Repository) 리포트에서 Enqueue Activity 섹션의 TM - Contention 항목을 주기적으로 점검하면 이 에러가 발생하기 전에 전조 증상을 포착할 수 있습니다.