मेरे पास दो UPDATE हैं - एक पहले CI को लॉक करता है और फिर NCI (स्टेटस पर) क्योंकि स्टेटस कॉलम को भी अपडेट किया जा रहा है। दूसरा पहले से ही NCI पर U लॉक का मालिक है क्योंकि वह जानता है कि यह बदल रहा है और फिर CI पर U लॉक प्राप्त करने की कोशिश करता है।
इन्हें क्रमबद्ध करने के लिए सबसे आसान तरीका क्या है? एक TABLE-level hint का उपयोग करना अजीब लगता है क्योंकि यह एक आंतरिक अनुक्रमण मुद्दा है - इसमें केवल एक तालिका शामिल है - क्या UPDLOCK, HOLDLOCK स्वचालित रूप से बस उस तालिका पर आवश्यक सभी अनुक्रमणिकाओं पर लागू होता है और इस तरह इसे क्रमबद्ध करने के लिए मजबूर करता है?
यहाँ प्रश्न हैं:
UPDATE htt_action_log
SET status = 'ABORTED', CLOSED = GETUTCDATE()
WHERE transition_uuid = '{F53ADDDA-E46B-4726-66D8-D7B640B66597}'
AND status = 'OPEN';
वह एक X CI (क्रिएट किए गए कॉलम) में पंक्ति को लॉक करता है और फिर NCI पर X लॉक करने का प्रयास करता है जिसमें स्टेटस कॉलम शामिल होता है।
UPDATE htt_action_log
SET status = 'RUNNING {36082BCD-EB52-4358-E3D3-4D96FD5B9F0F} 1360094342'
WHERE action_uuid = (SELECT TOP 1 action_uuid
FROM htt_action_log
WHERE transition_uuid = '{F53ADDDA-E46B-4726-66D8-D7B640B66597}'
AND status = 'OPEN'
ORDER BY action_seq)
यह एक U उसी NCI को लॉक करता है - मुझे लगता है कि नेस्टेड क्वेरी के लिए, फिर अपडेट के लिए CI को लॉक करने के लिए जाता है।
इस प्रकार आदेश गतिरोध पैदा करता है।
सबसे आसान समाधान दो प्रश्नों को पूरी तरह से ब्लॉक करने के लिए मजबूर करना है - अर्थात क्रमबद्ध करें। यह मजबूर करने का सबसे आसान तरीका क्या है, बस WITH (UPDLOCK, HOLDLOCK)
तालिका के संदर्भों में डालें (पहले में एक और दूसरे में दो)?
DDL:
नोट क्लाइंट के पास इस तालिका पर अधिक अनुक्रमणिकाएँ हैं जो इस अद्यतन से प्रभावित होनी चाहिए, लेकिन गतिरोध ग्राफ़ में इसका उल्लेख नहीं किया गया है।
CREATE TABLE [dbo].[HTT_ACTION_LOG](
[ACTION_UUID] [varchar](128) NOT NULL,
[TRANSITION_UUID] [varchar](128) NOT NULL,
[STATUS] [varchar](128) NOT NULL,
[CREATED] [datetime] NOT NULL,
[CLOSED] [datetime] NULL,
[ACTION_SEQ] [int] NOT NULL,
[ACTION_TYPE] [varchar](15) NOT NULL,
[ACTION_NAME] [varchar](50) NOT NULL,
[ACTION_RESULT] [varchar](8000) NULL,
[PENDING_SINCE] [datetime] NULL,
[ACTION_SQL] [varchar](8000) NULL,
[ERROR_OK] [int] NULL,
[ERROR_COND] [varchar](2048) NULL,
[RETRY] [varchar](128) NULL,
CONSTRAINT [PK_HTT_ACTION_LOG_1] UNIQUE NONCLUSTERED
(
[ACTION_UUID] ASC
)
)
CREATE CLUSTERED INDEX [IK_HTT_ACTION_LOG_2] ON [dbo].[HTT_ACTION_LOG]
(
[CREATED] ASC
)
CREATE NONCLUSTERED INDEX [IK_HTT_ACTION_LOG_1] ON [dbo].[HTT_ACTION_LOG]
(
[TRANSITION_UUID] ASC,
[STATUS] ASC
)
INCLUDE ( [ACTION_UUID],
[ACTION_SEQ])
CREATE NONCLUSTERED INDEX [IK_HTT_ACTION_LOG_4] ON [dbo].[HTT_ACTION_LOG]
(
[ACTION_UUID] ASC,
[STATUS] ASC
)
CREATE NONCLUSTERED INDEX [missing_index_11438530_11438529_HTT_ACTION_LOG] ON [dbo].[HTT_ACTION_LOG]
(
[TRANSITION_UUID] ASC,
[ACTION_TYPE] ASC
)
INCLUDE ( [ACTION_NAME])
CREATE NONCLUSTERED INDEX [missing_index_7207590_7207589_HTT_ACTION_LOG] ON [dbo].[HTT_ACTION_LOG]
(
[STATUS] ASC
)
INCLUDE ( [CREATED],
[PENDING_SINCE],
[ACTION_NAME])
CREATE NONCLUSTERED INDEX [missing_index_8535421_8535420_HTT_ACTION_LOG] ON [dbo].[HTT_ACTION_LOG]
(
[TRANSITION_UUID] ASC
)
INCLUDE ( [ACTION_UUID],
[STATUS])
ALTER TABLE [dbo].[HTT_ACTION_LOG] SET (LOCK_ESCALATION = AUTO)
ALTER TABLE [dbo].[HTT_ACTION_LOG] WITH CHECK ADD CONSTRAINT [FK_HTT_ACTION_LOG_1] FOREIGN KEY([TRANSITION_UUID])
REFERENCES [dbo].[HTT_TRANSITION_LOG] ([TRANSITION_UUID])
ALTER TABLE [dbo].[HTT_ACTION_LOG] CHECK CONSTRAINT [FK_HTT_ACTION_LOG_1]
ALTER TABLE [dbo].[HTT_ACTION_LOG] ADD DEFAULT ('OPEN') FOR [STATUS]
ALTER TABLE [dbo].[HTT_ACTION_LOG] ADD DEFAULT (getutcdate()) FOR [CREATED]
ALTER TABLE [dbo].[HTT_ACTION_LOG] ADD DEFAULT ((0)) FOR [ERROR_OK]