HSQL: Error when attempting to create foreign key constraint - hsqldb

The following is my table's create DDL:
create table REFDATA.CONFIG_COLLECTION (
COLLECTION_ID NUMBER(22,7) not null,
COLLECTION_CD VARCHAR2(12) not null,
COLLECTION_TYPE VARCHAR2(12) not null,
COLLECTION_DESC VARCHAR2(255),
primary key (COLLECTION_ID)
)
create unique index REFDATA.CONFIG_COLLECTION_AK on REFDATA.CONFIG_COLLECTION (COLLECTION_CD);
I then have the following alter to create a foreign key:
alter table REFDATA.CONFIG_COLLECTION_MEMBER
add foreign key (COLLECTION_CD)
references REFDATA.CONFIG_COLLECTION (COLLECTION_CD);
I get the following error when HSQLDB loads:
Caused by: java.sql.SQLException: Primary or unique constraint required on main table: CONFIG_COLLECTION in statement [
alter table REFDATA.CONFIG_COLLECTION_MEMBER
add foreign key (COLLECTION_CD)
references REFDATA.CONFIG_COLLECTION (COLLECTION_CD)]
at org.hsqldb.jdbc.Util.sqlException(Unknown Source)
at org.hsqldb.jdbc.jdbcStatement.fetchResult(Unknown Source)
at org.hsqldb.jdbc.jdbcStatement.execute(Unknown Source)
at org.apache.commons.dbcp.DelegatingStatement.execute(DelegatingStatement.java:264)
at org.springframework.jdbc.core.JdbcTemplate$1ExecuteStatementCallback.doInStatement(JdbcTemplate.java:420)
at org.springframework.jdbc.core.JdbcTemplate.execute(JdbcTemplate.java:395)
... 46 more
What is the problem here? It looks to me like I have the unique constraint correctly specified. This is version 1.8 of HSQLDB.

A unique index is not a unique constraint. You don't need the unique index but must create a unique constraint.
ALTER TABLE REFDATA.CONFIG_COLLECTION ADD CONSTRAINT CONFIG_COLLECTION_AK UNIQUE(COLLECTION_CD);

Related

PostgreSQL Partition and Unique Conflict

I am attempting to set up a database with partitions, however I am running into an error when creating the activity table. The 3 Table CREATEs (without the actual data) are as follows:
CREATE TABLE collection (
id SERIAL PRIMARY KEY
);
CREATE TABLE asset (
id SERIAL,
collection_id INT,
CONSTRAINT fk_collection
FOREIGN KEY(collection_id)
REFERENCES collection(id),
CONSTRAINT asset_pkey PRIMARY KEY(id, collection_id)
)PARTITION BY LIST(collection_id);
CREATE TABLE activity(
id SERIAL,
collection_id INT,
CONSTRAINT fk_collection
FOREIGN KEY(collection_id)
REFERENCES collection(id),
CONSTRAINT activity_pkey PRIMARY KEY(id, collection_id),
asset_id INT,
CONSTRAINT fk_asset
FOREIGN KEY(asset_id)
REFERENCES asset(id)
) PARTITION BY LIST(collection_id);
ERROR: there is no unique constraint matching given keys for referenced table "asset"
SQL state: 42830
My understanding of the error is that foreign keys must be unique. Because I must add collection_id as a primary key to partition item, I cannot also designate id as unique. When I attempt to make id unique, this is what happens:
ALTER TABLE asset
ADD CONSTRAINT u_id UNIQUE (id);
ERROR: unique constraint on partitioned table must include all partitioning columns
DETAIL: UNIQUE constraint on table "asset" lacks column "collection_id" which is part of the partition key.
SQL state: 0A000
Even if I successfully add the UNIQUE constraint on id and collection_id, it continues to throw me SQL state: 42830. Do I have to restructure my data or is there a better way to go about this that I'm not thinking of?
Would it be enough to merge the foreign keys on asset into one composite key, or does that violate some other constraint of your data?
CREATE TABLE activity(
id SERIAL,
collection_id INT,
asset_id INT,
CONSTRAINT activity_pkey PRIMARY KEY(id, collection_id),
CONSTRAINT fk_asset_collection
FOREIGN KEY(asset_id, collection_id)
REFERENCES asset(id, collection_id)
) PARTITION BY LIST(collection_id);

Oracle SQL : Cannot create a foreign key based on index of more than one column

I'm not able to create a foreign key based on index of more than one column.
Adding the foreign key returns the error :
ORA-02270: no matching unique or primary key for this column-list.
Below the code :
CREATE TABLE test_ek_uk (NOOPER VARCHAR2(7) NOT NULL
,NUMSEQ NUMBER NOT NULL
,ANY_TEXT VARCHAR2(4000));
CREATE UNIQUE INDEX test_ek_uk_nooper_numseq ON test_ek_uk (NOOPER, NUMSEQ);
CREATE TABLE test_ek_fk (ID NUMBER UNIQUE NOT NULL, NOOPER VARCHAR2(7), NUMSEQ number);
ALTER TABLE test_ek_fk ADD CONSTRAINT test_ek_fk_FK FOREIGN KEY (NOOPER, NUMSEQ) REFERENCES test_ek_uk (NOOPER, NUMSEQ);
A Foreign Key references either a Primary Key constraint or a Unique constraint. And it must be a constraint, a unique index is not enough.
If you already have index then you can create unique constraint based on that index. For your case:
alter table test_ek_uk
add constraint test_ek_uk_nooper_numseq unique (NOOPER, NUMSEQ)
using index altest_ek_uk_nooper_numseq;
But if you don't have that index - there is no need to create it explicitly.
So, instead of creating the unique index you could create a unique constraint:
alter table test_ek_uk
add constraint test_ek_uk_nooper_numseq unique (NOOPER, NUMSEQ);
The unique index is created in the background when you create this unique constraint.

How do I change a column I created a while ago in sql to foreign key

I need to change multiple tables to foreign keys. I have used the command
ALTER TABLE financial_transactions
ADD FOREIGN KEY (item_rental_id) REFERENCES transaction_id(item_rental_id);
The table name was financial_transactions and the column name was item_rental_id. It gives me an error saying:
Foreign key 'FK__financial__item___46E78A0C' references invalid table 'transaction_id'.
How do I resolve this?
Yes, this is a correct script to create a foreign key
ALTER TABLE financial_transactions
ADD FOREIGN KEY (item_rental_id) REFERENCES customer_rentals(item_rental_id);
However, if you are trying to add a foreign key constraint on a table with data already in it, you have to make sure that the item_rental_id in financial_transactions table are also in the customer_rentals table. Otherwise, you will have a referential integrity error.
To illustrate:
CREATE TABLE customer_rentals_1
(item_rental_id INT,
PRIMARY KEY (item_rental_id)
);
CREATE TABLE financial_transactions_1
(transaction_id INT,
item_rental_id INT,
PRIMARY KEY (transaction_id)
);
ALTER TABLE financial_transactions_1
ADD FOREIGN KEY (item_rental_id) REFERENCES customer_rentals_1(item_rental_id);
The scripts above will run successfully.
CREATE TABLE customer_rentals_2
(item_rental_id INT,
PRIMARY KEY (item_rental_id)
);
CREATE TABLE financial_transactions_2
(transaction_id INT,
item_rental_id INT,
PRIMARY KEY (transaction_id)
);
INSERT INTO financial_transactions_2
VALUES (1000, 9999);
ALTER TABLE financial_transactions_2
ADD FOREIGN KEY (item_rental_id) REFERENCES customer_rentals_2(item_rental_id);
But, this will have the following error since item_rental_id 9999 is not present in customer_rentals_2 table
Msg 547, Level 16, State 0, Line 31
The ALTER TABLE statement conflicted with the FOREIGN KEY constraint "FK__financial__item___76969D2E". The conflict occurred in database "TESTDB", table "dbo.customer_rentals_2", column 'item_rental_id'.
You have to give second table name
both way can do it
1. Add reference without name
ALTER TABLE financial_transactions
ADD FOREIGN KEY (item_rental_id) REFERENCES customer_rentals(item_rental_id);
2.Add reference with a name
ALTER TABLE financial_transactions
ADD CONSTRAINT FK_Financial_Transactions_Customer_Rental_Item_Rental_ID
FOREIGN KEY (item_rental_id) REFERENCES Customer_rentals(item_rental_id);

Primary & Foreign Key Constraints Confusion

currently trying to apply foreign keys to my created tables but I'm getting the SQL error:
SQL Error: ORA-02270: no matching unique or primary key for this column-list
02270. 00000 - "no matching unique or primary key for this column-list"
*Cause: A REFERENCES clause in a CREATE/ALTER TABLE statement
gives a column-list for which there is no matching unique or primary
key constraint in the referenced table.
*Action: Find the correct column names using the ALL_CONS_COLUMNS
catalog view
I'm at a massive loss on where to go from here, I think everythings in order but I just can't point out what's wrong.
Here are the relavent create and alter scripts i'm using if anybody can point out where i'm going wrong:
Creation of Results & DopingTest:
CREATE TABLE Results
(
RaceID NUMBER,
HorseID NUMBER,
JockeyID NUMBER,
Position numeric(2)
);
CREATE TABLE DopingTest
(
RaceID NUMBER,
HorseID NUMBER,
TakenBy varchar2(60)
);
And the adding of constraints:
ALTER TABLE Results
ADD(
CONSTRAINT pk_ResultsID
PRIMARY KEY (RaceID,HorseID));
ALTER TABLE DopingTest
ADD(
CONSTRAINT pk_DopingTest
PRIMARY KEY (RaceID, HorseID));
ALTER TABLE Results
ADD(
CONSTRAINT fk_raceID
FOREIGN KEY (RaceID)
REFERENCES Race(RaceID),
CONSTRAINT fk_horseID
FOREIGN KEY (HorseID)
REFERENCES Horse(HorseID),
CONSTRAINT fk_JockeyID
FOREIGN KEY (JockeyID)
REFERENCES Jockey(JockeyID));
ALTER TABLE DopingTest
ADD(
CONSTRAINT fk_RaceIDDT
FOREIGN KEY (RaceID)
REFERENCES Results(RaceID),
CONSTRAINT fk_HorseIDDT
FOREIGN KEY (HorseID)
REFERENCES Results(HorseID));
Any help would be greatly appreciated, thanks.
If results has a composite primary key, the foreign key would have to reference both components of the key.
ALTER TABLE DopingTest
ADD(
CONSTRAINT fk_RaceIDDT
FOREIGN KEY (RaceID, HorseID)
REFERENCES Results(RaceID, HorseID)
);

How do I make a Table's Attribute a Foreign Key within that Table?

I had to write the SQL to create the tables, attributes, and primary & foreign keys in this ERD:
http://imgur.com/VYZbwr6
In the table 'Financial_Transactions' in the ERD there is a attribute called 'previous_transaction_id' and another attribute called 'transaction_id'. In this table 'previous_transaction_id' is a Foreign Key for this table in addition to being an attribute. It references the last 'transaction_id' in the table.
Here is my SQL for the 'financial_transactions' table:
CREATE TABLE financial_transactions(
transaction_id int IDENTITY(1,1) NOT NULL,
account_id int NOT NULL,
item_rental_id int NOT NULL,
previous_transaction_id int,
transaction_type_code int NOT NULL,
transaction_date date NOT NULL,
transaction_amount money NOT NULL,
transaction_comment varchar(512) NOT NULL);
ALTER TABLE financial_transactions ADD CONSTRAINT pk_financial_transactions PRIMARY KEY (transaction_id);
ALTER TABLE financial_transactions ADD CONSTRAINT fk_financial_transactions_accounts FOREIGN KEY(account_id)
REFERENCES accounts (account_id);
ALTER TABLE financial_transactions ADD CONSTRAINT fk_financial_transactions_customer_rentals FOREIGN KEY(item_rental_id)
REFERENCES customer_rentals (item_rental_id);
ALTER TABLE financial_transactions ADD CONSTRAINT fk_financial_transactions_financial_transactions FOREIGN KEY(previous_transaction_id)
REFERENCES financial_transactions (previous_transaction_id);
ALTER TABLE financial_transactions ADD CONSTRAINT fk_financial_transactions_transaction_types FOREIGN KEY(transaction_type_code)
REFERENCES transaction_types (transaction_type_code);
When I run my SQL (includes statements for each table in the script) I get these errors:
"Msg 1776, Level 16, State 0, Line 87
There are no primary or candidate keys in the referenced table 'financial_transactions' that match the referencing column list in the foreign key 'fk_financial_transactions_financial_transactions'.
Msg 1750, Level 16, State 0, Line 87
Could not create constraint. See previous errors."
All other statements execute normally.
What am I doing wrong?
*I used this statement originally under CREATE TABLE: previous_transaction_id int NOT NULL,
However, it resulted in the same error and when searching I saw a similar question that was fixed by removing the NOT NULL.
Here
ALTER TABLE financial_transactions ADD CONSTRAINT
fk_financial_transactions_financial_transactions
FOREIGN KEY(previous_transaction_id)
REFERENCES financial_transactions (previous_transaction_id);
You have a column referencing itself. Was that your intent or did you want to reference the transaction_id?
There is nothing wrong with defining a foreign key to the same table but you have a column referencing itself.
Try replacing:
ALTER TABLE financial_transactions ADD CONSTRAINT fk_financial_transactions_financial_transactions FOREIGN KEY(previous_transaction_id)
REFERENCES financial_transactions (previous_transaction_id);
With:
ALTER TABLE financial_transactions ADD CONSTRAINT fk_financial_transactions_financial_transactions FOREIGN KEY(previous_transaction_id)
REFERENCES financial_transactions (transaction_id);