কোনও ডাটাবেস স্কিমা বিদ্যমান থাকলে আমি কীভাবে জিজ্ঞাসা করব


102

আমাদের বিল্ড প্রক্রিয়াটির অংশ হিসাবে আমরা 4 টি পৃথক পরিবেশে কোড মোতায়েন করার সাথে সাথে আমরা একটি ডাটাবেস আপডেট স্ক্রিপ্টটি চালাই। উপরন্তু, যেহেতু একই ক্যোয়ারী যতক্ষণ না আমরা উতপাদনে মুক্তি ড্রপ যুক্ত হয়ে যাবে এটা হয়েছে একটি প্রদত্ত ডাটাবেসের উপর একাধিক বার চালানোর জন্য পাবে। এটার মত:

IF NOT EXISTS (SELECT * FROM sys.tables WHERE object_id = OBJECT_ID(N'[Table]'))
BEGIN
  CREATE TABLE [Table]
  (...)
END

বর্তমানে আমার স্থাপনা / বিল্ড স্ক্রিপ্টে একটি স্কিমা বিবৃতি তৈরি করুন। স্কিমার অস্তিত্বের জন্য আমি কোথায় জিজ্ঞাসা করব?


4
গৃহীত উত্তর পরিবর্তন বিবেচনা করুন। আপনি যে উত্তরটি গ্রহণ করেছেন তা লিখিতভাবে আপনার পক্ষে কাজ করেছে এমনটি সম্ভব নয় not
অ্যারন বারট্রান্ড

উত্তর:


169

আপনি sys.schemas খুঁজছেন ?

IF NOT EXISTS (SELECT * FROM sys.schemas WHERE name = 'jim')
BEGIN
EXEC('CREATE SCHEMA jim')
END

নোট করুন যে CREATE SCHEMAঅবশ্যই নিজের ব্যাচে চালানো উচিত ( নীচের উত্তর অনুসারে )


ডার্ন ... যে সময়ে পোস্টটি আরও পঠনযোগ্য করে তুলতে আমাকে সম্পাদনা করতে লেগেছে ... আপনি আমার সমস্যাটি সমাধান করেছেন। অনেক ধন্যবাদ!
পালসহেড

18
এটি এসকিউএল ২০০৮ এ কাজ করে না কারণ ক্রিট স্কেমার একটি ব্যাচে প্রথম বিবৃতি হওয়া দরকার, একটি কাজের জন্য ভিফিলবি পোস্টটি দেখুন
সার্জিওম

4
পারফরম্যান্সটি উন্নত করতে আপনি 'sys.schemas থেকে 1 নির্বাচন করুন' ব্যবহার করতে পারেন।
বিজয়সিলভেস্টার

4
@vijaysylvester না, এটি একটি পৌরাণিক কাহিনী। এসকিউএল সার্ভার কলামের তালিকাটি অপ্টিমাইজ করে যাতে আপনি সেখানে কী রেখেছেন তা বিবেচ্য নয়। সম্পূর্ণ উপেক্ষা করা। প্রমাণ চান? রাখুনSELECT 1/0...
অ্যারন

4
আমি এই উত্তর আপডেট করেছি ভুল হতে না (অর্থাত নীচের থেকে স্ক্রিপ্ট ব্যবহার করতে stackoverflow.com/a/521271/2688 )
bdukes

157

@ বিডুকস স্কিমার উপস্থিতি আছে কিনা তা নির্ধারণের জন্য ঠিক আছে, তবে উপরের বিবৃতিটি এসকিউএল সার্ভার 2005-এ কাজ করবে না CREATE SCHEMA <name>its এটির নিজস্ব ব্যাচে চালানো দরকার। একটি কাজ প্রায় একটি এক্সিকিউটিউটে CREATE SCHEMAবিবৃতি কার্যকর করা হয় ।

আমি আমার বিল্ড স্ক্রিপ্টগুলিতে যা ব্যবহার করেছি তা এখানে:

IF NOT EXISTS (SELECT 1 FROM sys.schemas WHERE name = '<name>')
BEGIN
    -- The schema must be run in its own batch!
    EXEC( 'CREATE SCHEMA <name>' );
END

একটি যাদুমন্ত্র মত কাজ করে! এটি এমনকি আমার মুদ্রণ বিবৃতি এবং সমস্ত কিছু রাখতে দেয়।
টনি

2

এটি পুরানো তাই আমি যুক্ত করতে বাধ্য হচ্ছি: এসকিউএল সার্ভার ২০০৮ এর জন্য ++++++++++++++> এই সমস্ত কাজ (নির্বাচিত অংশের জন্য), তারপরে এটি ব্যবহার EXECUTE('CREATE SCHEMA <name>')করার জন্য এটি নেতিবাচক ফলাফলগুলিতে তৈরি করুন।

DECLARE @schemaName sysname = 'myfunschema';
-- shortest
If EXISTS (SELECT 1 WHERE SCHEMA_ID(@schemaName) IS NOT NULL)
PRINT 'YEA'
ELSE
PRINT 'NOPE'

SELECT DB_NAME() AS dbname WHERE SCHEMA_ID(@schemaName) IS NOT NULL -- nothing returned if not there

IF NOT EXISTS ( SELECT  top 1 *
                FROM    sys.schemas
                WHERE   name = @schemaName )
PRINT 'WOOPS MISSING'
ELSE
PRINT 'Has Schema'

SELECT SCHEMA_NAME(SCHEMA_ID(@schemaName)) AS SchemaName1 -- null if not there otherwise schema name returned

SELECT SCHEMA_ID(@schemaName) AS SchemaID1-- null if not there otherwise schema id returned


IF EXISTS (
    SELECT sd.SchemaExists 
    FROM (
        SELECT 
            CASE 
                WHEN SCHEMA_ID(@schemaName) IS NULL THEN 0
                WHEN SCHEMA_ID(@schemaName) IS NOT NULL THEN 1
                ELSE 0 
            END AS SchemaExists
    ) AS sd
    WHERE sd.SchemaExists = 1
)
BEGIN
    SELECT 'Got it';
END
ELSE
BEGIN
    SELECT 'Schema Missing';
END

4
IF schema_id ('MySchemaName') IS NULLভাল কাজ করে এবং স্বীকৃত উত্তরের চেয়ে কিছুটা বেশি সুবিধাজনক বলে মনে হচ্ছে।
ব্র্যাডিসি 10:53

ব্র্যাডকে সম্মত করুন তাদের ক্ষেত্রে, যারা ব্যাতিক্রম পান: যদি SCHEMA_ID ('আউট') নল এক্সেক হয় না ('স্কেমা তৈরি করুন [আউট] প্রমাণীকরণ [আউট]' ');
জুজাসাস

1

কেবলমাত্র অতিরিক্ত "প্রতিরক্ষামূলক" হতে, নীচের সংস্করণটি> 1 টির মিলনের ক্ষেত্রে সম্ভাব্যতা (তবে অসম্ভাব্য) হিসাবে অ্যাকাউন্টের জন্য টাইপ রূপান্তর ত্রুটি উত্পন্ন করে যা Schemaবৈধকরণ কোডটি প্রায়শই ইচ্ছাকৃতভাবে ব্যতিক্রম ছুঁড়ে দেয় কারণ আমি বিশ্বাস করি এটি ভাল এবং এটি আমি বিশ্বাস করি সমস্ত সম্ভাব্য প্রত্যাবর্তনের ফলাফলের জন্য "সর্বোত্তম অনুশীলন" "তবে তা অসম্ভব এবং এমনকি যদি এটি মারাত্মক ব্যতিক্রম ঘটায় তবে প্রসেসিং বন্ধ করার পরিচিত প্রভাবগুলি অন-আটকে থাকা ত্রুটির অজানা ক্যাসকেডিং প্রভাবগুলির চেয়ে ভাল। এটি অত্যন্ত অসম্ভব, কারণ আমি মনে করি না যে এটি একটি পৃথক Countচেক + Throwবা Try- Catch- Throwআরও বেশি ব্যবহারকারী-বান্ধব মারাত্মক ত্রুটি উত্পন্ন করার পরেও মারাত্মক ত্রুটি তৈরির সমস্যার পক্ষে উপযুক্ত।

এসএস 2005-:

declare @HasSchemaX bit
set @HasSchemaX = case (select count(1) from sys.schemas where lower(name) = lower('SchemaX')) when 1 then 1 when 0 then 0 else 'ERROR' end

এসএস ২০০+:

declare @HasSchemaX bit = case (select count(1) from sys.schemas where lower(name) = lower('SchemaX')) when 1 then 1 when 0 then 0 else 'ERROR' end

তারপরে:

if @HasSchemaX = 1
begin
   ...
end -- if @HasSchemaX = 1

আমি মনে করি আপনি যখন কেস সেনসিটিভ কোলেশন ব্যবহার করেন তখন একাধিক মেলানো স্কিমা পাওয়া সম্ভব তবে আপনার "ত্রুটি পরিচালনা" এর ফলে নিম্নলিখিত ত্রুটিটি ঘটবে: বর্ণের মান 'ERROR' কে ডেটা টাইপ ইনটে রূপান্তর করার সময় রূপান্তর ব্যর্থ হয়েছিল।
ব্যবহারকারী 247702

@Stijn: তা এর "দ্বারা নকশা" কিভাবে বৈধতা কোড অনুরূপ প্রায়ই ইচ্ছাকৃতভাবে Throw Exception'র। তুমি যেমন বললে, এটা না " 'সম্ভবত'" ঘটতে, তাই এই প্রোগ্রামটিতে, এটি একটি পুরো মূল্য ছিল না Try- Catchবা আলাদা Countচেক আরও ব্যবহারকারী বান্ধব মারাত্মক ত্রুটি উৎপন্ন, কিন্তু নির্বিশেষে, আমি সম্ভবত একটি মারাত্মক ত্রুটি চাইবেন। আমি বিশ্বাস করি এবং আমি বিশ্বাস করি যে সমস্ত সম্ভাব্য প্রত্যাবর্তনের ফলাফলের জন্য এটি "সর্বোত্তম অনুশীলন" "হিসাবে গণ্য হবে এবং এমনকি এটি কেবল মারাত্মক ব্যতিক্রম ঘটানোও কারণ প্রক্রিয়াজাতকরণ বন্ধ করার জ্ঞাত প্রভাবগুলি অন-আটকে থাকা অজানা ক্যাসকেডিং প্রভাবগুলির চেয়ে ভাল is ত্রুটি
টম

এটি যে সমস্ত সুন্দর বলে মনে হচ্ছে তা নিশ্চিত ছিল না যে এটি ইচ্ছাকৃত হয়েছিল কিনা :) আপনার উত্তরটি কিছু অতিরিক্ত ব্যাখ্যা থেকে উপকৃত হতে পারে, যেমন আপনি কেবল আপনার মন্তব্যে দিয়েছিলেন।
ব্যবহারকারী 247702

@Stijn: আমার পোষা অপমান সাধারণ না তাই " 'সেরা অনুশীলনের'" হয় পরীক্ষণ না একটি এর Select, Insert, Updateবা Deleteবিবৃতি ফিরে / আরো প্রভাবিত বা কম সারি তবে অসম্ভাব্য প্রত্যাশিত #। এমনকি যদি Unique Indexবর্তমানে রয়েছে (স) রয়েছে তবে প্রত্যাশিত # (যেমন 1) সারিগুলি প্রত্যাবর্তন / প্রভাবিত হবে তা ভবিষ্যতে (দুর্ঘটনাক্রমে বা (স্বল্প দৃষ্টি দিয়ে) "" ইচ্ছাকৃতভাবে "") পরিবর্তিত হতে পারে।
টম

1

উপাদানগুলির বিন্যাস যদি এটির অনুমতি দেয় তবে এটিও কার্যকর হয়।

যদি উপস্থিত না থাকে (সিসমাস থেকে 1 টি নির্বাচন করুন যেখানে নাম = 'মাইচিমা') সেট করুন নোেক্সেক 
যাওয়া
স্কিমার মাইছেম তৈরি করুন
যাওয়া 
NOEXEC অফ সেট করুন - যদি আরও কোনও প্রক্রিয়া প্রয়োজন হয়।
যাওয়া
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.