जाहिर है, मेरी CLR असेंबली फ़ंक्शन गतिरोध पैदा कर रहा है?


9

हमारे एप्लिकेशन को Oracle डेटाबेस या Microsoft SQL सर्वर डेटाबेस के साथ समान रूप से अच्छी तरह से काम करने की आवश्यकता है। इसे सुविधाजनक बनाने के लिए, हमने अपने क्वेरी सिंटैक्स को समरूप बनाने के लिए मुट्ठी भर यूडीएफ बनाए। उदाहरण के लिए, SQL सर्वर में GETDATE () और Oracle में SYSDATE है। वे एक ही कार्य करते हैं लेकिन वे अलग-अलग शब्द हैं। हमने दोनों प्लेटफ़ॉर्म के लिए अब () नामक एक रैपर UDF लिखा, जो एक सामान्य फ़ंक्शन नाम में संबंधित प्लेटफ़ॉर्म विशिष्ट सिंटैक्स को लपेटता है। हमारे पास ऐसे अन्य कार्य हैं, जिनमें से कुछ अनिवार्य रूप से कुछ भी नहीं करते हैं, लेकिन पूरी तरह से समरूपीकरण के लिए मौजूद हैं। दुर्भाग्य से, यह SQL सर्वर के लिए एक लागत है। इनलाइन स्केलर यूडीएफ प्रदर्शन पर कहर बरपाता है और पूरी तरह से समानता को निष्क्रिय करता है। एक विकल्प के रूप में, हमने समान लक्ष्यों को पूरा करने के लिए सीएलआर असेंबली फ़ंक्शन लिखा। जब हमने इसे एक ग्राहक को तैनात किया तो उन्हें लगातार गतिरोध का अनुभव होने लगा। यह विशेष रूप से ग्राहक प्रतिकृति और उच्च उपलब्धता तकनीकों का उपयोग कर रहा है और मुझे आश्चर्य हो रहा है कि यहां कुछ प्रकार की बातचीत चल रही है। मुझे नहीं समझ में आया कि CLR फ़ंक्शन को शुरू करने से इस तरह की समस्याएं कैसे होंगी। संदर्भ के लिए, मैंने मूल स्केलर यूडीएफ परिभाषा के साथ-साथ सी # में प्रतिस्थापन सीएलआर परिभाषा और इसके लिए एसक्यूएल घोषणा को शामिल किया है। मेरे पास एक्सएमएल भी है जो मैं प्रदान कर सकता हूं यदि वह मदद करता है।

मूल यूडीएफ

CREATE FUNCTION [fn].[APAD]
(
    @Value VARCHAR(4000)
    , @tablename VARCHAR(4000) = NULL
    , @columnname VARCHAR(4000) = NULL
)

RETURNS VARCHAR(4000)
WITH SCHEMABINDING
AS

BEGIN
    RETURN LTRIM(RTRIM(@Value))
END
GO

सीएलआर विधानसभा समारोह

[SqlFunction(IsDeterministic = true)]
public static string APAD(string value, string tableName, string columnName)
{
    return value?.Trim();
}

SQL सर्वर घोषणा CLR फ़ंक्शन के लिए

CREATE FUNCTION [fn].[APAD]
(
    @Value NVARCHAR(4000),
    @TableName NVARCHAR(4000),
    @ColumnName NVARCHAR(4000)
) RETURNS NVARCHAR(4000)
AS
EXTERNAL NAME ASI.fn.APAD
GO

9
नियतात्मक स्केलर सीएलआर कार्यों को गतिरोध में योगदान नहीं देना चाहिए। बेशक CLR फ़ंक्शन जो डेटाबेस पढ़ सकता है। आपको अपने प्रश्न में गतिरोध XML को शामिल करना चाहिए।
डेविड ब्राउन -

जवाबों:


7

SQL सर्वर का कौन सा संस्करण (संस्करण) आप उपयोग कर रहे हैं?

मुझे याद है कि SQL Server 2017 में व्यवहार में थोड़ा बदलाव बहुत पहले नहीं देखा गया था। मुझे वापस जाना होगा और देखना होगा कि क्या मुझे पता चल सकता है कि मैंने इसे कहाँ नोट किया है, लेकिन मुझे लगता है कि जब SQLCLR ऑब्जेक्ट एक्सेस किया जा रहा था तो स्कीमा लॉक शुरू किया जाना चाहिए।

जब मैं उसकी तलाश कर रहा हूं, तो मैं आपके दृष्टिकोण के बारे में निम्नलिखित कहूंगा:

  1. कृपया Sql*इनपुट मापदंडों के लिए प्रकारों का उपयोग करें , रिटर्न प्रकार। आपको SqlStringइसके बजाय उपयोग करना चाहिए stringSqlStringएक अशक्त स्ट्रिंग के समान है (आपका value?, लेकिन इसमें अन्य कार्यक्षमता है जो SQL सर्वर-विशिष्ट है। सभी Sql*प्रकारों में एक Valueसंपत्ति होती है जो अपेक्षित .NET प्रकार SqlString.Valueदेता है (जैसे रिटर्न string, SqlInt32रिटर्न int, SqlDateTimeरिटर्न DateTimeआदि)।
  2. मैं इस पूरे दृष्टिकोण के खिलाफ सिफारिश करूंगा कि गतिरोध संबंधित हैं या नहीं। मैं यह कहता हूं क्योंकि:

    1. यहां तक ​​कि नियतात्मक एसक्यूएलएलआर यूडीएफ समानांतर योजनाओं में भाग लेने में सक्षम होने के साथ, आप सबसे सरल रूप से निर्मित कार्यों के अनुकरण के लिए प्रदर्शन हिट प्राप्त करने की संभावना रखते हैं।
    2. SQLCLR API की अनुमति नहीं देता है VARCHAR। क्या आप संक्षेप में सब कुछ बदलने NVARCHARऔर फिर से VARCHARसरल ऑपरेशन के लिए वापस करने के साथ ठीक हैं ?
    3. SQLCLR API ओवरलोडिंग के लिए अनुमति नहीं देता है, इसलिए आपको कई प्रकार के कार्यों की आवश्यकता हो सकती है जो T-SQL और / या PL / SQL में विभिन्न हस्ताक्षर के लिए अनुमति देते हैं।
    4. ओवरलोडिंग की अनुमति नहीं देने के समान है, के बीच एक बड़ा अंतर है NVARCHAR(4000)और NVARCHAR(MAX): MAXप्रकार (हस्ताक्षर में उनमें से एक भी) होने के नाते SQLCLR कॉल दो बार तब तक लेते हैं जब तक MAXकि हस्ताक्षर में कोई प्रकार न हो (मुझे विश्वास है कि यह मानता है VARBINARY(MAX)बनाम के VARBINARY(4000)रूप में अच्छी तरह से सच है )। तो, आप के बीच का फैसला करने की जरूरत है:
      • केवल NVARCHAR(MAX)एक सरल एपीआई का उपयोग करना, लेकिन जब आप 8000 बाइट्स या कम स्ट्रिंग डेटा का उपयोग कर रहे हों, या प्रदर्शन हिट करें, या
      • सभी / अधिकांश / कई स्ट्रिंग फ़ंक्शंस के लिए दो भिन्नताएँ बनाना: एक MAXप्रकार के साथ , और एक बिना (जब आपको गारंटी दी जाती है कि आप स्ट्रिंग डेटा के 8000 बाइट्स कभी भी या बाहर न जाएं)। यह वह तरीका है जिसे मैंने अपने एसक्यूएल # लाइब्रेरी में अधिकांश कार्यों के लिए चुना है : एक Trim()फ़ंक्शन है जिसमें एक या एक से अधिक MAXप्रकार होने की संभावना है , और एक Trim4k()संस्करण जिसमें MAXहस्ताक्षर या परिणाम सेट स्कीमा में कहीं भी एक प्रकार नहीं है । "4k" संस्करण बिल्कुल अधिक कुशल हैं।
    5. आप प्रश्न में उदाहरण दिए गए कार्यक्षमता का अनुकरण करने के लिए सावधान नहीं हो रहे हैं। LTRIMऔर RTRIMकेवल रिक्त स्थान को ट्रिम करें, जबकि .NET String.Trim()सफ़ेद स्थान (कम से कम स्थान, टैब और न्यूलाइन्स) को ट्रिम करता है । उदाहरण के लिए:

        PRINT LTRIM(RTRIM(N'      a       '));
    6. इसके अलावा, मैंने अभी देखा कि आपका फ़ंक्शन, T-SQL और C # दोनों में, केवल 3 इनपुट मापदंडों में से 1 का उपयोग करता है। क्या यह सिर्फ अवधारणा का प्रमाण है, या कोड को फिर से बनाया गया है?

1. Sql प्रकार का उपयोग करने पर टिप के लिए धन्यवाद। मैं अब वह बदलाव करूंगा। 2. यहां काम करने के लिए बाहरी ताकतें हैं, जिनके उपयोग की आवश्यकता है। मैं इसके बारे में रोमांचित नहीं हूं, लेकिन मुझ पर भरोसा है, यह विकल्प से बेहतर है। मेरे मूल प्रश्न में थोड़ा सा स्पष्टीकरण है कि क्यों प्रतीत होता है कि असिन फ़ंक्शन मौजूद है और इसका उपयोग किया जा रहा है।
रस सोटर

@ रस्सटर अंडरस्टूड री: बाहरी ताकतें। मैं सिर्फ कुछ नुकसान की ओर इशारा कर रहा था, जो उस निर्णय के समय ज्ञात नहीं थे। किसी भी तरह से, मैं अपने नोटों को खोजने में असमर्थ हूं या कुछ विवरणों से परिदृश्य को पुन: उत्पन्न नहीं कर सकता हूं जो मुझे याद है। मुझे बस यह याद है कि 2017 में निश्चित रूप से लेनदेन के संबंध में कुछ बदल रहा है और एक विधानसभा से कोड बुला रहा है, और इससे वास्तव में नाराज हो रहा है क्योंकि यह बदतर के लिए एक अनावश्यक बदलाव की तरह लग रहा था, और मुझे इसके लिए काम करना था जो मैं काम कर रहा था पूर्व संस्करणों में ठीक है। तो, कृपया डेडलॉक XML के लिंक में एक पोस्ट करें।
सोलोमन रटज़की

उस अतिरिक्त जानकारी के लिए धन्यवाद। यहाँ XML का एक लिंक दिया गया है: dropbox.com/s/n9w8nsdojqdypqm/deadlock17.xml?dl=0
Russ Suter

@RussSuter क्या आपने टी-एसक्यूएल को इनलाइन करने की कोशिश की है? गतिरोध XML को देखते हुए (जो कि एक पंक्ति के रूप में आसान नहीं है - सभी नए लिंक किसी तरह हटा दिए गए) यह सत्र 60 और 78 के बीच पेज लॉक की एक श्रृंखला प्रतीत होती है। दोनों सत्रों के बीच 8 पृष्ठ लॉक हैं: 3 एक के लिए SPID और 5 अन्य के लिए। प्रत्येक एक अलग प्रक्रिया आईडी के साथ है, इसलिए यह समानता का मुद्दा है। यदि यह SQLCLR से संबंधित है, तो यह विडंबना हो सकती है कि SQLCLR समानता को नहीं रोक रही है। यही कारण है कि मैंने पूछा कि क्या आपने साधारण फ़ंक्शन इनलाइन डालने की कोशिश की है क्योंकि यह गतिरोध भी दिखा सकता है।
सोलोमन रटज़की
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.