When I try to disable the constraint I am getting the following error
cannot disable constraint (SCOTT.EMPLOYEE_PK) - dependencies exist
Please give me the solution for this problem.
Can I use CASCADE to disable the constraint?
If I use CASCADE, then will I able to enable the constraint again?
According to the documentation the action to do is:
Either disable the foreign key constraints or use disable cascade
So use this to disable the primary key and its index:
alter table employee disable primary key
You can re-enable the index/constraint when done, but make sure you don't invalidate the index:
alter table employee enable primary key
Also read: Modifying, Renaming, or Dropping Existing Integrity Constraints.
Related
I am copying data from one PostgreSQL v10 table to another. The destination table has several foreign key constraints. I was surprised that I did not get any errors, even though none of the tables referred to by the foreign key constraints had any data.
Before I did the copy, I used DISABLE TRIGGER ALL to ensure that the trigger defined on the destination table did not fire. I was surprised that the copy succeeded. After ENABLE TRIGGER ALL, I tried to add one more row, a copy of an existing row. That failed with a foreign key constraint violation. I then did DISABLE TRIGGER ALL, tried to add the new row, and it succeeded.
I conclude that in PostgreSQL 10, DISABLE TRIGGER ALL will disable foreign key constraint checks. Is that expected behavior?
Details can be found here.
Yes, that's expected.
From "ALTER TABLE":
DISABLE/ENABLE [ REPLICA | ALWAYS ] TRIGGER
These forms configure the firing of trigger(s) belonging to the table. (...) One can disable or enable a single trigger specified by name, or all triggers on the table, or only user triggers (this option excludes internally generated constraint triggers such as those that are used to implement foreign key constraints or deferrable uniqueness and exclusion constraints). Disabling or enabling internally generated constraint triggers requires superuser privileges; it should be done with caution since of course the integrity of the constraint cannot be guaranteed if the triggers are not executed. (...)
While generating the Create DB script for the existing Foreign Key constraint through SSMS, we could able to see two set of alter statements. one with NOCHECK ADD and another with CHECK.
ALTER TABLE [dbo].[claim] WITH NOCHECK ADD CONSTRAINT [FK_CLAIM_COPCID]
FOREIGN KEY([copcid])
REFERENCES [dbo].[copc] ([CopcId])
GO
ALTER TABLE [dbo].[claim] CHECK CONSTRAINT [FK_CLAIM_COPCID]
GO
Why we are getting two set of scripts to create a new Constraint?.
The first alter statement is creating a constraint and instructing that constraint to be added without checking whether the existing rows obey the new constraint.
When you add a constraint without first checking the rows, it will not be fully active until you enable it. That's what the second statement does, it enables the new constraint. If there are rows that break the constraint, you won't be able to enable it.
I have the following code
--first statement
ALTER TABLE [nameOfMyTable] WITH CHECK ADD CONSTRAINT [nameOfMyConstraint] FOREIGN KEY([myFK])
REFERENCES [tableReference] ([myFK])
GO
--second statement
ALTER TABLE [nameOfMyTable] CHECK CONSTRAINT [nameOfMyConstraint]
GO
First, i define a CHECK constraint on a table. What does mean second statement?
The 2nd statement is redundant, the only time it would be needed is if the first statement had WITH NOCHECK. By default WITH CHECK is added if you don't explicitly state CHECK or NOCHECK in the ADD CONSTRAINT statement.
sql server management studio generate this code by default – Mikhail
Because the code is being auto generated it is just being constructed by a set of steps. Some of those steps will have some overlap so the "table definition" step may enable or disable the check the constraint while it creates the table, but the "setup constraints" step may also enable or disable the constraint.
Relevant documentation:
WITH CHECK | WITH NOCHECK
Specifies whether the data in the table is or is not validated against a newly added or re-enabled FOREIGN KEY or CHECK constraint.
If not specified, WITH CHECK is assumed for new constraints, and WITH
NOCHECK is assumed for re-enabled constraints.
If you do not want to verify new CHECK or FOREIGN KEY constraints against existing data, use WITH NOCHECK. We do not recommend doing
this, except in rare cases. The new constraint will be evaluated in
all later data updates. Any constraint violations that are suppressed
by WITH NOCHECK when the constraint is added may cause future updates
to fail if they update rows with data that does not comply with the
constraint.
The query optimizer does not consider constraints that are defined WITH NOCHECK. Such constraints are ignored until they are re-enabled
by using ALTER TABLE WITH CHECK CHECK CONSTRAINT ALL.
{ CHECK | NOCHECK } CONSTRAINT
Specifies that constraint_name is enabled or disabled. This option can only be used with FOREIGN KEY and CHECK constraints. When NOCHECK
is specified, the constraint is disabled and future inserts or updates
to the column are not validated against the constraint conditions.
DEFAULT, PRIMARY KEY, and UNIQUE constraints cannot be disabled.
From the docs:
Specifies that constraint_name is enabled or disabled. This option can only be used with FOREIGN KEY and CHECK constraints. When NOCHECK is specified, the constraint is disabled and future inserts or updates to the column are not validated against the constraint conditions. DEFAULT, PRIMARY KEY, and UNIQUE constraints cannot be disabled.
The second statement in the given context is redundant if run immediately after the creation of the constraint (with out without WITH CHECK, creation of the foreign key constraint with ADD CONSTRAINT FOREIGN KEY will do the WITH CHECK immediately by default).
The second statement is used to reenable constraint checking
ALTER TABLE [nameOfMyTable] CHECK CONSTRAINT [nameOfMyConstraint];
usually after it has been disabled, like so:
ALTER TABLE [nameOfMyTable] NOCHECK CONSTRAINT [nameOfMyConstraint];
GO
Scripting tools often create DDL like this - overkill, although I guess they really want to be sure :)
There is a third flavour, which is to re-check the validity of the constraint, e.g. after doing a Bulk Copy or similar which may have invalidated the constraint (marked it as untrusted). This is done like so:
ALTER TABLE [nameOfMyTable] WITH CHECK CHECK CONSTRAINT [nameOfMyConstraint];
Edit Hopefully this SQLFiddle clears this up?
I saw thisone in MSDN magazine.i wanted to Temporary disable Foreignkeys,Can i do using following code.. Not needed to delete but temporary disable because i wanted to enable again
ALTER TABLE Orders
NOCHECK CONSTRAINT
FK_Orders_Customers
-- Disable the constraint.
ALTER TABLE Orders NOCHECK CONSTRAINT FK_Orders_Customers
-- Reenable the constraint.
ALTER TABLE Orders WITH CHECK CHECK CONSTRAINT FK_Orders_Customers
Yes, as you've suspected ALTER TABLE [table] CHECK / NOCHECK CONSTRAINT *FK_Name* enables and disables foreign key constraint checking. It also proves why it is a good idea to explicitly name your constraints i.e. to avoid names like FK__TABLE__A2A64E930CBAE877.
One point to note that after inserting / changing data with disabled foreign key constraints is that SQL won't trust your constraint if you simply enable it with CHECK CONSTRAINT. You will need to do the following to get SQL to recheck the constraint during re enable:
ALTER TABLE [table] WITH CHECK CHECK CONSTRAINT *FK_Name*
You can check for violations with
DBCC CHECKCONSTRAINTS ([table])
Ref : http://msdn.microsoft.com/en-us/library/ms177456(v=sql.90).aspx (Disabling Constraints) and also see http://geekswithblogs.net/dturner/archive/2011/01/31/sql-constraints-check-and-nocheck.aspx
I had to modify an existing constraint so it would cascade updates and deletes.
To do this I first removed the constraint and was planning on adding it (through an ALTER TABLE) but this fails.
When I commit the query below it gives me the error 'ORA-01735: invalid ALTER TABLE option':
ALTER TABLE
PARAM
ADD CONSTRAINT
FK_PARAM_PORTLET FOREIGN KEY (PORTLETID)
REFERENCES PORTLET(ID)
ON DELETE CASCADE ON UPDATE CASCADE;
Any idea what it could be? Am I overlooking something?
Oracle does not support ON UPDATE CASCADE in foreign keys.
Have a look at this question for tips: How to create a Foreign Key with "ON UPDATE CASCADE" on Oracle?
UPDATE CASCADE is not supported in Oracle. You will need to manage this via triggers.
Check Oracle statement:
Referential integrity constraints can specify particular actions to be
performed on the dependent rows in a child table if a referenced
parent key value is modified. The referential actions supported by the
FOREIGN KEY integrity constraints of Oracle are UPDATE and DELETE NO
ACTION, and DELETE CASCADE.