2009-10-15 35 views
5

मैं StackQL के लिए अगले अद्यतन पर काम कर रहा हूं।क्या मैं संग्रहीत प्रक्रिया के भीतर एक डिफ़ॉल्ट स्कीमा सेट कर सकता हूं?

एक चीज जो मैं करना चाहता हूं उसके पास कई रिलीज पर पूछताछ करने की क्षमता है। इसलिए जब मैंने अक्टूबर डेटा लोड किया, उदाहरण के लिए, मैंने पुराने सितंबर डेटाबेस को हटाया नहीं। यह अभी भी बाहर है। वास्तव में, आप भी अभी भी इसे इस तरह डेटाबेस नाम शामिल करके क्वेरी कर सकते हैं:

select top 10 * from SO_Sept09..Posts 

यह और भी अधिक महत्वपूर्ण हो जाएगा के रूप में वे ServerFault और SuperUser के लिए डेटा उपलब्ध कराने के शुरू करते हैं।

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

प्रश्नों अंत में सिर्फ इस तरह exec() कार्य करने के लिए पारित कर रहे हैं:

exec(@QueryText) 

क्या मैं क्या कर सकते हैं या तो संग्रहित प्रक्रिया या QueryText स्ट्रिंग के लिए आगे जोड़ते में (USE [DatabaseName] आला) डिफ़ॉल्ट सेट करने के लिए है एक प्रश्न में इस्तेमाल स्कीमा?

+0

उत्कृष्ट सवाल! – RBarryYoung

उत्तर

3

संशोधित @QueryText खुद के अलावा, केवल एक चीज मैं के बारे में सोच सकते हैं एक उपयोगकर्ता के डिफ़ॉल्ट स्कीमा है:

ALTER USER SO_Sept09_Reader WITH DEFAULT_SCHEMA = SO_Sept09 

... और उसके बाद प्रत्येक स्कीमा आप उपयोग करना चाहते के लिए एक अन्य उपयोगकर्ता के रूप कनेक्ट। हैक हैक।

लेकिन यदि आपकी क्वेरी गतिशील रूप से बनाई गई है (और मुझे यकीन है कि आप जानते हैं कि यह अक्सर एक अच्छा विचार क्यों नहीं है), तो क्वेरी टेक्स्ट में केवल स्कीमा प्लेसहोल्डर जोड़ने के लिए सबसे आसान हो सकता है, और स्कीमा नाम पास कर सकता है एक प्रतिस्थापन समारोह के लिए क्वेरी के साथ।

+0

स्कीमा प्लेसहोल्डर जोड़ना निश्चित रूप से एक विकल्प नहीं है। साइट किसी को एसक्यूएल क्वेरी को फिर से स्टैक ओवरव्लो सार्वजनिक डेटा डंप लिखने और चलाने की सुविधा देती है, और वे बस कुछ भी लिख सकते हैं। उपयोगकर्ता को बदलना भी बाहर है, क्योंकि यह समवर्ती मुद्दों का कारण बनता है। लेकिन यह मुझे कई उपयोगकर्ताओं को रखने का विचार देता है और फ्लाई पर कनेक्शन स्ट्रिंग चुनता है। –

+0

हाँ, उत्तरार्द्ध वह है जो मैं सुझा रहा था; प्रति स्कीमा में एक या अधिक (स्थिर) उपयोगकर्ता; फ्लाई पर उपयोगकर्ताओं को स्विच करें (मिलान कनेक्शन तारों से कनेक्ट करके)। –

1

एक और संभावना प्रत्येक स्कीमा में प्रत्येक एसपी की प्रतियां उत्पन्न करने के लिए है, एक एसपी में unmodified तालिका नाम एक ही स्कीमा में टेबल को संदर्भित करता है।

नोट इस के अंदर इस तरह के एक सपा गतिशील एसक्यूएल साथ काम नहीं करता:

CREATE PROCEDURE schema_a.SP 
    @somesql AS varchar(MAX) 
AS 
BEGIN 
    EXEC (@somesql) 
END 

CREATE PROCEDURE schema_b.SP 
    @somesql AS varchar(MAX) 
AS 
BEGIN 
    EXEC (@somesql) 
END 

, काम नहीं करेगा क्योंकि स्कीमा आत्मीयता EXEC के अंदर खो दिया है।

इस जबकि:

CREATE PROCEDURE schema_a.SP 
AS 
BEGIN 
    SELECT * FROM tbl -- Will use schema_a.tbl first 
END 

CREATE PROCEDURE schema_b.SP 
AS 
BEGIN 
    SELECT * FROM tbl -- Will use schema_b.tbl first 
END 

ठीक काम करता है।

इसी तरह:

EXEC ('EXEC schema_a.SP') 

स्पष्ट रूप से ठीक काम करेगा।

+0

अभी भी एक झुकाव है, लेकिन मुझे अतिरिक्त उपयोगकर्ताओं को बनाने से बेहतर पसंद है। –

+0

काम नहीं किया। जब मैंने कोशिश की तो उसने डबो में टेबल उठाया। –

+0

मैं RBArryYoung के उत्तर के रूप में EXECUTE के साथ जाऊंगा क्योंकि आप पहले से ही गतिशील SQL का उपयोग कर रहे हैं। स्कीमा एफ़िनिटी आपके लिए काम नहीं कर रही है कि एक बार जब आप निष्पादन को दबाते हैं, तो आप एसपी से स्कीमा का संदर्भ खो रहे हैं जो निष्पादन कहता है, जैसे कि यह सब कुछ के बारे में खो देता है। –

0

अनचाहे, लेकिन: क्या आप अलग-अलग स्कीमा के डेटा को एक दृश्य में जोड़ सकते हैं, और स्कीमा नाम को कॉल करने वाले कॉलम को जोड़ सकते हैं?

CREATE VIEW AllPosts AS 
    SELECT Data1, Data2, 'Sept09' AS Partition FROM SO_Sept09..Posts 
    UNION ALL 
    SELECT Data1, Data2, 'Oct09' AS Partition FROM SO_Oct09..Posts 
    ... 

SELECT * FROM AllPosts WHERE Partition = 'Sept09' 
SELECT * FROM dbo.AllPosts('Sept09') -- if use table-valued function instead 
+0

यह एक विचार है, लेकिन यह मेरी बहुत सारी अनुक्रमणिका को तोड़ देगा। –

+0

आप विचारों को इंडेक्स कर सकते हैं, हालांकि पूरे गुफाओं के साथ। http://msdn.microsoft.com/en-us/library/dd171921.aspx http://msdn.microsoft.com/en-us/library/ms191432.aspx –

11

यहां विभिन्न स्थानों पर ऐसा करने के तरीके हैं, लेकिन पूरी तरह से नहीं।तरीका यह है है:

  1. प्रत्येक स्कीमा

  2. के लिए एक अनूठा लॉगिन & उपयोगकर्ता बनाओ इन उपयोगकर्ताओं को एक अलग स्कीमा के मालिकों बनाओ।

  3. प्रत्येक ऐसे उपयोगकर्ता की डिफ़ॉल्ट स्कीमा को उस स्कीमा के रूप में सेट करें जो उनके पास है।

  4. उस डिफ़ॉल्ट स्कीमा के संदर्भ में अपने SQL आदेश निष्पादित करने के लिए वाक्यविन्यास EXECUTE ('sql commands') AS USER = 'schema-owner' का उपयोग करें।

निम्न स्क्रिप्ट इस दर्शाता है:

--====== Create the Login for the User: 
CREATE LOGIN [UserTest1] WITH PASSWORD='whatever', DEFAULT_DATABASE=[TestUsers], DEFAULT_LANGUAGE=[us_english] 
GO 

--====== Make a User for the Login: 
CREATE USER [UserTest1] FOR LOGIN [UserTest1] 
GO 

--====== Make a Schema owned by the User and default to it: 
--  (I assume that you already have the schemas) 
CREATE SCHEMA [UserTest1] AUTHORIZATION [UserTest1] 
GO 
ALTER USER [UserTest1] WITH DEFAULT_SCHEMA=[UserTest1] 
GO 

--====== Make a sProc in dbo 
CREATE PROCEDURE [dbo].[TestSchema_Exec] AS 
    SELECT 'executing in schema [dbo]' 
GO 
--====== Make a similar sProc in New Schema 
CREATE PROCEDURE [UserTest1].[TestSchema_Exec] AS 
    SELECT 'executing in schema [UserTest1]' 
GO 

--========= Demonstrate that we can switch Default Schemas: 
EXEC('TestSchema_Exec') 

EXEC('TestSchema_Exec') AS USER = 'UserTest1' 
0

ठीक है, मैं यह है कि मेरे लिए थोड़ा बेहतर काम कर सकते हैं करने के लिए एक नया तरीका है। यह माइकल पेट्रोट्टा के उत्तर पर मेरी टिप्पणी पर एक प्रकार है:

लेकिन यह मुझे कई उपयोगकर्ताओं के विचार और फ्लाई पर कनेक्शन स्ट्रिंग चुनने का विचार देता है।

मैं क्या करूँगा इन प्रश्नों को निष्पादित करने के लिए केवल एक उपयोगकर्ता है, लेकिन मैं सही प्रारंभिक कैटलॉग निर्दिष्ट करने के लिए फ्लाई पर कनेक्शन स्ट्रिंग को स्वैप कर दूंगा।

संबंधित मुद्दे

 संबंधित मुद्दे