বিদেশী কী বাধা কেবলমাত্র এসকিএল সার্ভারে উপস্থিত থাকলে কীভাবে বাদ দেব?


235

নিম্নলিখিত কোডটি ব্যবহার করে যদি একটি টেবিল উপস্থিত থাকে তবে আমি কী করতে পারি না তা সীমাবদ্ধতার সাথে কীভাবে করতে হবে তা আমি জানি না:

IF EXISTS(SELECT 1 FROM sys.objects WHERE OBJECT_ID = OBJECT_ID(N'TableName') AND type = (N'U')) DROP TABLE TableName
go 

আমি এই কোডটি ব্যবহার করে বাধাও যুক্ত করব:

ALTER TABLE [dbo].[TableName] 
  WITH CHECK ADD CONSTRAINT [FK_TableName_TableName2] FOREIGN KEY([FK_Name])
    REFERENCES [dbo].[TableName2] ([ID])
go

উত্তর:


321

এরিক আইজ্যাকসের উত্তরে আরও সহজ সমাধান সরবরাহ করা হয়েছে । তবে এটি কোনও টেবিলে বাধা খুঁজে পাবে। আপনি যদি কোনও নির্দিষ্ট টেবিলে কোনও বিদেশী কী বাধা লক্ষ্য করতে চান, এটি ব্যবহার করুন:

IF EXISTS (SELECT * 
  FROM sys.foreign_keys 
   WHERE object_id = OBJECT_ID(N'dbo.FK_TableName_TableName2')
   AND parent_object_id = OBJECT_ID(N'dbo.TableName')
)
  ALTER TABLE [dbo.TableName] DROP CONSTRAINT [FK_TableName_TableName2]

1
এটি যদি উপস্থিত থাকে তবে আমি সত্যিই পরে আছি .. দুঃখিত। আমি আমার প্রশ্ন আপডেট করব যাতে এটি আরও স্পষ্ট হয়!
সোলেরদেবদেব

2
আপনি নামে বিন্দু দিয়ে মতিন উত্পন্ন পররাষ্ট্র কী ব্যবহার করেন তাহলে আপনি ভালো নাম প্রায় বন্ধনী রাখতে হবে [dbo] [FK_dbo.MyTable_Etc]।
ডেভিড Sopko

এমএসএসকিউএল 2017 এ, দেখে মনে হচ্ছে কলামটি এখন constraint_object_idকেবল পরিবর্তে কল করছেobject_id
কোডেনমেজারো

1
এটি কাজ করে না। ওবিজেইসিআইডিআইডি ('[CONSTRAINT_NAME]', 'এফ') আমার জানা বিদেশী কীতে রয়েছে এবং এটি বাতিল হয়ে গেছে।
মেলবোর্ন বিকাশকারী

1
@ মেলবোর্ন ডেভেলপার আপনার যদি স্কোমা উপসর্গের প্রয়োজন হয় তবে যদি ডিএনও নন স্কিমায় বিদেশী কী উপস্থিত থাকে। উদাহরণস্বরূপ, আইএফ (নির্বাচন করুন ওবিজেইসিআইডিআইডি (এন '[স্কিমা]। [এফকে_নাম]', এন'এফ ')) বাতিল নয়। আমার কাছে আপনার মত একই সমস্যা ছিল (আপনার সমাধানটি আমার পক্ষেও কাজ করেছিল), তবে আমি এটি উদাহরণের মাধ্যমে কাজ করতে পেলাম। আমি এসকিউএল সার্ভার 2012 চালিয়ে যাচ্ছি
iokevins

318

এটি বর্তমান প্রস্তাবিত সমাধানের চেয়ে অনেক সহজ:

IF (OBJECT_ID('dbo.FK_ConstraintName', 'F') IS NOT NULL)
BEGIN
    ALTER TABLE dbo.TableName DROP CONSTRAINT FK_ConstraintName
END

আপনার যদি অন্য ধরণের বাধা ছাড়তে হয় তবে দ্বিতীয় পরামিতি অবস্থানে OBJECT_ID () ফাংশনে যাওয়ার জন্য এগুলি প্রযোজ্য কোডগুলি:

C = CHECK constraint
D = DEFAULT (constraint or stand-alone)
F = FOREIGN KEY constraint
PK = PRIMARY KEY constraint
UQ = UNIQUE constraint

আপনি দ্বিতীয় পরামিতি ছাড়াই OBJECT_ID ব্যবহার করতে পারেন।

প্রকারের সম্পূর্ণ তালিকা এখানে :

অবজেক্টের ধরণ:

AF = Aggregate function (CLR)
C = CHECK constraint
D = DEFAULT (constraint or stand-alone)
F = FOREIGN KEY constraint
FN = SQL scalar function
FS = Assembly (CLR) scalar-function
FT = Assembly (CLR) table-valued function
IF = SQL inline table-valued function
IT = Internal table
P = SQL Stored Procedure
PC = Assembly (CLR) stored-procedure
PG = Plan guide
PK = PRIMARY KEY constraint
R = Rule (old-style, stand-alone)
RF = Replication-filter-procedure
S = System base table
SN = Synonym
SO = Sequence object

প্রযোজ্য: এসকিউএল সার্ভার ২০১৪ এর মাধ্যমে এসকিউএল সার্ভার ২০১২।

SQ = Service queue
TA = Assembly (CLR) DML trigger
TF = SQL table-valued-function
TR = SQL DML trigger
TT = Table type
U = Table (user-defined)
UQ = UNIQUE constraint
V = View
X = Extended stored procedure

1
এখানে প্রকারের সম্পূর্ণ তালিকা (এটি কেবল কীগুলি নয়, এটি সমস্ত ধরণের স্টাফের জন্য কাজ করে )।
রাফিন

2
লিঙ্ক এবং প্রকারের তালিকা যুক্ত করার স্বাধীনতা নিয়েছে।
মিচ গম

10
এটি প্রদর্শিত হয় যে সীমাবদ্ধতাটি যদি ডিবিও স্কিমাতে না থাকে তবে আপনাকেও স্কিমা নাম অন্তর্ভুক্ত করতে হবে। উদাহরণস্বরূপ: OBJECT_ID ('MySchema.FK_MyConstraint', 'F')
জিলস স্মিথ

1
এই উপায়টি সহজ হতে পারে তবে অন্য সারণি স্পষ্টভাবে সীমাবদ্ধতাগুলি সন্ধান এবং অপসারণের জন্য আরও ভাল, এমনকি একই নাম সহ বিভিন্ন সারণী / স্কিমা / ডাটাবেসের ক্ষেত্রেও সীমাবদ্ধ রয়েছে।
সিএসএস

1
আমি এখানে একটি সমস্যা দেখছি এটি কখনই নিশ্চিত করে না যে কন্টেন্টটি যে টেবিলটিতে রয়েছে সেগুলি আমরা রেখে দিচ্ছি।
সন্দীপ কাঁচাত

36

এসকিউএল সার্ভার 2016 এ আপনি উপস্থিত থাকলে ড্রপ ব্যবহার করতে পারেন:

CREATE TABLE t(id int primary key, 
               parentid int
                    constraint tpartnt foreign key references t(id))
GO
ALTER TABLE t
DROP CONSTRAINT IF EXISTS tpartnt
GO
DROP TABLE IF EXISTS t

Http://blogs.msdn.com/b/sqlserverstorageengine/archive/2015/11/03/DP-if-exists-new-thing-in-sql-server-2016.aspx দেখুন


15
IF (OBJECT_ID('DF_Constraint') IS NOT NULL)
BEGIN
    ALTER TABLE [dbo].[tableName]
    DROP CONSTRAINT DF_Constraint
END

14

আপনি যদি আসল সীমাবদ্ধতার নাম জানেন তবে জেমসের উত্তর ঠিক কাজ করে। জটিল জিনিসটি হ'ল উত্তরাধিকার এবং অন্যান্য বাস্তব বিশ্বের পরিস্থিতিতে আপনি হয়ত জানেন না এই সীমাবদ্ধতাটি কী বলা হয় ।

যদি আপনি এটি ব্যবহার করতে পারেন তা এড়াতে যদি আপনি সদৃশ সীমাবদ্ধতা তৈরির ঝুঁকি তৈরি করেন:

create function fnGetForeignKeyName
(
    @ParentTableName nvarchar(255), 
    @ParentColumnName nvarchar(255),
    @ReferencedTableName nvarchar(255),
    @ReferencedColumnName nvarchar(255)
)
returns nvarchar(255)
as
begin 
    declare @name nvarchar(255)

    select @name = fk.name  from sys.foreign_key_columns fc
    join sys.columns pc on pc.column_id = parent_column_id and parent_object_id = pc.object_id
    join sys.columns rc on rc.column_id = referenced_column_id and referenced_object_id = rc.object_id 
    join sys.objects po on po.object_id = pc.object_id
    join sys.objects ro on ro.object_id = rc.object_id 
    join sys.foreign_keys fk on fk.object_id = fc.constraint_object_id
    where 
        po.object_id = object_id(@ParentTableName) and 
        ro.object_id = object_id(@ReferencedTableName) and
        pc.name = @ParentColumnName and 
        rc.name = @ReferencedColumnName

    return @name
end

go

declare @name nvarchar(255)
declare @sql nvarchar(4000)
-- hunt for the constraint name on 'Badges.BadgeReasonTypeId' table refs the 'BadgeReasonTypes.Id'
select @name = dbo.fnGetForeignKeyName('dbo.Badges', 'BadgeReasonTypeId', 'dbo.BadgeReasonTypes', 'Id')
-- if we find it, the name will not be null
if @name is not null 
begin 
    set @sql = 'alter table Badges drop constraint ' + replace(@name,']', ']]')
    exec (@sql)
end

5
ALTER TABLE [dbo].[TableName]
    DROP CONSTRAINT FK_TableName_TableName2

5
সম্ভবত এটি একটি TRY..CATCHব্লকে রেখে দিন।
onedaywhen

"... যদি এটি স্কিএল সার্ভারে বিদ্যমান থাকে? ..." - আপনি কীভাবে এই সীমাবদ্ধতার উপস্থিতি পরীক্ষা করবেন?
new2ios 13

3
Declare @FKeyRemoveQuery NVarchar(max)

IF EXISTS(SELECT 1 FROM sys.foreign_keys WHERE parent_object_id = OBJECT_ID(N'dbo.TableName'))

BEGIN
    SELECT @FKeyRemoveQuery='ALTER TABLE dbo.TableName DROP CONSTRAINT [' + LTRIM(RTRIM([name])) + ']'   
    FROM sys.foreign_keys
    WHERE parent_object_id = OBJECT_ID(N'dbo.TableName')

    EXECUTE Sp_executesql @FKeyRemoveQuery 

END

কেবলমাত্র অতিরিক্ত আমি যুক্ত করব সিজে.ফায়ারগাইন_কিগুলি থেকে বাছাইকৃত ফিল্টার হিসাবে নামটি অন্তর্ভুক্ত করা উচিত কারণ টেবিলে একাধিক বিদেশী কী থাকতে পারে
কোয়েনিন

1

আমি মনে করি এটি আপনার পক্ষে সহায়ক হবে ...

    DECLARE @ConstraintName nvarchar(200)
SELECT 
    @ConstraintName = KCU.CONSTRAINT_NAME
FROM INFORMATION_SCHEMA.REFERENTIAL_CONSTRAINTS AS RC 
INNER JOIN INFORMATION_SCHEMA.KEY_COLUMN_USAGE AS KCU
    ON KCU.CONSTRAINT_CATALOG = RC.CONSTRAINT_CATALOG  
    AND KCU.CONSTRAINT_SCHEMA = RC.CONSTRAINT_SCHEMA 
    AND KCU.CONSTRAINT_NAME = RC.CONSTRAINT_NAME
WHERE
    KCU.TABLE_NAME = 'TABLE_NAME' AND
    KCU.COLUMN_NAME = 'TABLE_COLUMN_NAME'
IF @ConstraintName IS NOT NULL EXEC('alter table TABLE_NAME drop  CONSTRAINT ' + @ConstraintName)

এটি নির্দিষ্ট সারণী এবং কলামের ভিত্তিতে বিদেশী কী বাধা মুছে ফেলবে।


0

আপনি আপনার টেবিলের জন্য সমস্ত এফকে খুঁজতে এই প্রশ্নগুলি ব্যবহার করতে পারেন।

Declare @SchemaName VarChar(200) = 'Schema Name'
Declare @TableName VarChar(200) = 'Table name'

-- Find FK in This table.
SELECT 
    'IF  EXISTS (SELECT * FROM sys.foreign_keys WHERE object_id = OBJECT_ID(N''' + 
      '[' + OBJECT_SCHEMA_NAME(FK.parent_object_id) + '].[' + FK.name + ']' 
      + ''') AND parent_object_id = OBJECT_ID(N''' + 
      '[' + OBJECT_SCHEMA_NAME(FK.parent_object_id) + '].[' 
      + OBJECT_NAME(FK.parent_object_id) + ']' + ''')) ' +

    'ALTER TABLE ' +  OBJECT_SCHEMA_NAME(FK.parent_object_id) +
    '.[' + OBJECT_NAME(FK.parent_object_id) + 
    '] DROP CONSTRAINT ' + FK.name
    , S.name , O.name, OBJECT_NAME(FK.parent_object_id)
FROM sys.foreign_keys AS FK
INNER JOIN Sys.objects As O 
  ON (O.object_id = FK.parent_object_id )
INNER JOIN SYS.schemas AS S 
  ON (O.schema_id = S.schema_id)  
WHERE 
      O.name = @TableName
      And S.name = @SchemaName


-- Find the FKs in the tables in which this table is used
  SELECT 
    ' IF  EXISTS (SELECT * FROM sys.foreign_keys WHERE object_id = OBJECT_ID(N''' + 
      '[' + OBJECT_SCHEMA_NAME(FK.parent_object_id) + '].[' + FK.name + ']' 
      + ''') AND parent_object_id = OBJECT_ID(N''' + 
      '[' + OBJECT_SCHEMA_NAME(FK.parent_object_id) + '].[' 
      + OBJECT_NAME(FK.parent_object_id) + ']' + ''')) ' +

    ' ALTER TABLE ' +  OBJECT_SCHEMA_NAME(FK.parent_object_id) +
    '.[' + OBJECT_NAME(FK.parent_object_id) + 
    '] DROP CONSTRAINT ' + FK.name
    , S.name , O.name, OBJECT_NAME(FK.parent_object_id)
FROM sys.foreign_keys AS FK
INNER JOIN Sys.objects As O 
  ON (O.object_id = FK.referenced_object_id )
INNER JOIN SYS.schemas AS S 
  ON (O.schema_id = S.schema_id)  
WHERE 
      O.name = @TableName
      And S.name = @SchemaName 

0

এই প্রশ্নের গৃহীত উত্তর আমার পক্ষে কাজ করবে বলে মনে হচ্ছে না। আমি কিছুটা আলাদা পদ্ধতিতে একই জিনিস অর্জন করেছি:

IF (select object_id from sys.foreign_keys where [name] = 'FK_TableName_TableName2') IS NOT NULL
BEGIN
    ALTER TABLE dbo.TableName DROP CONSTRAINT FK_TableName_TableName2
END
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.