Why should not violate foreign key while enable? - sql-server

Why should not violate foreign key while enable in SQL Server?
We have two tables, Order Header and Order Detail.
Order header table's OrderID column references OrderDetail table's OrderID column.
Then I'm going to migrate with some data from production database to these table.
I just disable these table foreign key constraint and inserted data from production Db.
After insertion of data, the order details table's OrderID column contains the values 101,102,103, but the order header table's Order ID column contains value 100 only.
Then I try to enable the foreign key constraint using the following t-sql code
exec sp_msforeachtable "ALTER TABLE ? CHECK CONSTRAINT ALL"
Why should not violate the foreign key with existing data while enabling?

When you moving data from multiple tables which connected with FKey - you should:
or preserve key values in both tables
or issue new values changing appropriate FKey column in referencing table when moving
When you enabling the FKey constraint - it is by default checks for data consistency

Related

How to add another primary key in SQL Server

I have a SQL Server table that has primary keys
CompanyID
ClientID
ReportName
I need to add a column that is an additional key and an incremented ID.
alter table Exports
add id int identity(1,1)
How do I write the statement to make this a key as well?
You can have only 1 primary key or identity column in each table in SQL Server.
If you want to have one more column as primary key, then you may use the combination of the columns as the primary key.
Or you can set the constraints UNIQUE and NOT NULL to the columns so that they will act same as a primary key (but these columns can't be referred as foreign keys)
In case of auto incremental columns (identity), you can only have 1 identity column per table. It can also be set as a primary key. Otherwise, if you need multiple columns as auto-increment, then probably you can use a calculated column, a trigger or a sequence object from which you may fetch the values for each record

Foreign Key constraint on set of rows of a table data sql server

I have a ValidationTable like
and OrderProcessing table like
I want to create foreign key constraint on OrderProcessing table on column OrderType that references first 3 rows of ValidationTable (of ValidationType = "orders"). Is this possible? I referred similar questions but those did not really help.
I don't believe it is possible to link a specific set of rows.
The constraint has to be for the whole column.

SQL Server having a column as both PK and FK

I have not done much database design work and I was searching around for some example.
While I know the difference from a primary and foreign key, one thing that caught be off guard was that even if a Table has a primary key and is used as a foreign key in another table, as I was used the GUI SSMS tools, I noticed that I sometime end up having this
PhoneID (PK, int, not null)
While my User table
UserId(PK,FK, int, not null)
BOTH of these tables have these ID's as primary keys in those tables, along with foreign keys in other tables, but why does one of them have "PK,FK" obviously I accidentally created it, but should it be like that?
It is Possible for a Primary key to be a Foreign Key as well at the same time.
But looking at you database design, In your case I dont think it was intentional it was done by mistake. And if it wasnt done by mistake then you need to fix it.
In your dbo.PhoneType Table the column PhoneTypeID needs to be a Primary key only not a Foreign key. My guess is this was done by mistake, you wanted to create a Foreign key in your dbo.Phone table on column PhoneTypeID referencing PhoneTypeID column in dbo.PhoneType table. But somehow you end up create a foreign key constraint on the Primary key column of the dbo.Phontype table.
This Design contradicts constraints.
In simple english : The foreign Key Constraint on your dbo.PhoneType(PhoneTypeID) enforces that you cannot have a PhoneTypeID in dbo.PhoneType table unless it exists in PhoneTypeID column of dbo.Phone table.
On the other hand Foreign Key Constraint on dbo.Phone(PhoneTypeID) enforces that you cannot have a PhoneTypeID in dbo.Phone unless it exists in dbo.PhoneType(PhoneTypeID).
and same is true for the UserID column in dbo.Users table.
Solution
You need to drop the following Constraints to make it work properly.
1) In dbo.PhoneType table Drop Foreign key constraint referencing
PhoneTypeID column in dbo.phone table.
2) In dbo.Users Table drop the Drop Foreign key constraint referencing
UserID column in dbo.phone table.
It's entirely possible, yes. A primary key of a table could also be a foreign key referencing another table.
In your case, I'm not exactly sure what you did. You can check the constraints to see which column the UserId column is referencing.
As an additional note, simply adding a foreign reference to a table does not implicitly make that column a foreign key on another table. For example, just because you add FK_PhoneTypeID to the Phone table, SQL Server does not automatically make PhoneTypeID column in the PhoneType table a FK. In your statements, somewhere, it's possible that you made assignments to other columns, or even to themselves.

Are foreign keys indexed automatically in SQL Server?

Would the following SQL statement automatically create an index on Table1.Table1Column, or must one be explicitly created?
Database engine is SQL Server 2000
CREATE TABLE [Table1] (
. . .
CONSTRAINT [FK_Table1_Table2] FOREIGN KEY
(
[Table1Column]
) REFERENCES [Table2] (
[Table2ID]
)
)
SQL Server will not automatically create an index on a foreign key. Also from MSDN:
A FOREIGN KEY constraint does not have
to be linked only to a PRIMARY KEY
constraint in another table; it can
also be defined to reference the
columns of a UNIQUE constraint in
another table. A FOREIGN KEY
constraint can contain null values;
however, if any column of a composite
FOREIGN KEY constraint contains null
values, verification of all values
that make up the FOREIGN KEY
constraint is skipped. To make sure
that all values of a composite FOREIGN
KEY constraint are verified, specify
NOT NULL on all the participating
columns.
As I read Mike's question, He is asking whether the FK Constraint will create an index on the FK column in the Table the FK is in (Table1). The answer is no, and generally. (for the purposes of the constraint), there is no need to do this The column(s) defined as the "TARGET" of the constraint, on the other hand, must be a unique index in the referenced table, either a Primary Key or an alternate key. (unique index) or the Create Constraint statment will fail.
(EDIT: Added to explicitly deal with comment below -)
Specifically, when providing the data consistency that a Foreign Key Constraint is there for. an index can affect performance of a DRI Constraint only for deletes of a Row or rows on the FK side. When using the constraint, during a insert or update the processor knows the FK value, and must check for the existence of a row in the referenced table on the PK Side. There is already an index there. When deleting a row on the PK side, it must verify that there are no rows on the FK side. An index can be marginally helpful in this case. But this is not a common scenario.
Other than that, in certain types of queries, however, where the query processor needs to find the records on the many side of a join which uses that foreign key column. join performance is increased when an index exists on that foreign key. But this condition is peculiar to the use of the FK column in a join query, not to existence of the foreign Key constraint... It doesn't matter whether the other side of the join is a PK or just some other arbitrary column. Also, if you need to filter, or order the results of a query based on that FK column, an index will help... Again, this has nothing to do with the Foreign Key constraint on that column.
No, creating a foreign key on a column does not automatically create an index on that column. Failing to index a foreign key column will cause a table scan in each of the following situations:
Each time a record is deleted from the referenced (parent) table.
Each time the two tables are joined on the foreign key.
Each time the FK column is updated.
In this example schema:
CREATE TABLE MasterOrder (
MasterOrderID INT PRIMARY KEY)
CREATE TABLE OrderDetail(
OrderDetailID INT,
MasterOrderID INT FOREIGN KEY REFERENCES MasterOrder(MasterOrderID)
)
OrderDetail will be scanned each time a record is deleted in the MasterOrder table. The entire OrderDetail table will also be scanned each time you join OrderMaster and OrderDetail.
SELECT ..
FROM
MasterOrder ord
LEFT JOIN OrderDetail det
ON det.MasterOrderID = ord.MasterOrderID
WHERE ord.OrderMasterID = #OrderMasterID
In general not indexing a foreign key is much more the exception than the rule.
A case for not indexing a foreign key is where it would never be utilized. This would make the server's overhead of maintaining it unnecessary. Type tables may fall into this category from time to time, an example might be:
CREATE TABLE CarType (
CarTypeID INT PRIMARY KEY,
CarTypeName VARCHAR(25)
)
INSERT CarType .. VALUES(1,'SEDAN')
INSERT CarType .. VALUES(2,'COUP')
INSERT CarType .. VALUES(3,'CONVERTABLE')
CREATE TABLE CarInventory (
CarInventoryID INT,
CarTypeID INT FOREIGN KEY REFERENCES CarType(CarTypeID)
)
Making the general assumption that the CarType.CarTypeID field is never going to be updated and deleting records would be almost never, the server overhead of maintaing an index on CarInventory.CarTypeID would be unnecessary if CarInventory was never searched by CarTypeID.
According to: https://learn.microsoft.com/en-us/sql/relational-databases/tables/primary-and-foreign-key-constraints?view=sql-server-ver16#indexes-on-foreign-key-constraints
Unlike primary key constraints, creating a foreign key constraint does not automatically create a corresponding index

Modifying an existing column to a foreign key

I have an oracle db which has no Foreign Keys, all table relations are handled by the software. For example, table Customer with columns Customer.customercode, Customer.Name where customercode is the primary key and table Order with columns Order.ordercode (PK), Order.customercode where customercode has no foreign key constraint. So far the application handles all transactions and takes care of all the table relations so that the data are consistent. I need to change this to a proper relational DB implementation, so I need to modify Order.customercode to be a FK from table Customer. Any sqlplus statement to do this without losing my data?
In Oracle, creating a foreign key would never lose any data, but it will fail if the data doesn't correspond to the new constraint. Assuming your data is OK, you can use an alter table statement:
ALTER TABLE order
ADD CONSTRAINT order_customer_fk FOREIGN KEY (customercode)
REFERENCES customer(customercode)

Resources