How to set two column unique in SQL - sql

I am creating a table ,in the table two column is unique, I mean columnA and columnB do not have same value:
such as :
Table X
A B
1 2(RIGHT,unique)
2 2(RIGHT, unique)
1 3(RIGHT, not unique)
2 3(RIGHT, not unique)
1 2 (WRONG, not unique)
How to create such a table?
many thanks!
create table X
(
[ID] INTEGER PRIMARY KEY AUTOINCREASE NOT NULL,\
[A] INTEGER,
[B] INTEGER);

Create a unique key column:
CREATE TABLE X
(
ID INTEGER PRIMARY KEY AUTOINCREASE NOT NULL,
A INTEGER,
B INTEGER,
UNIQUE KEY(A, B)
);
INSERT INTO X(A, B) VALUES(1, 2);
INSERT INTO X(A, B) VALUES(2, 2);
INSERT INTO X(A, B) VALUES(1, 3);
INSERT INTO X(A, B) VALUES(2, 3);
INSERT INTO X(A, B) VALUES(1, 2);
The last line will fail because the combination a = 1 and b = 2 already exists in the table.

CREATE UNIQUE INDEX `my_index_name` ON `my_table` (`col1`,`col2`)

Related

Create new records in one table-A and add as foreign key to table-B if the foreign key field in table-B is null -PostgresSQL

Table A and Table B look like shown below. The intention is to write an SQL script to run and update the tables. Table B has a foreign key to Table-A. If the field is null in Table B, then create a new record in Table-A and update Table B with that foreign key
It is expected to add two new records in Table A and add those foreign key in the Table B as per the above example. Thanks in advance
I wrote for you sample for do it.
But I don't know your business logic detail. You can change some solutions.
CREATE TABLE tablea (
id serial4 NOT NULL,
"name" varchar NULL,
CONSTRAINT tablea_pk PRIMARY KEY (id)
);
CREATE TABLE tableb (
id serial4 NOT NULL,
a_id int4 NULL,
"name" varchar NULL,
CONSTRAINT tableb_pk PRIMARY KEY (id)
);
INSERT INTO tableb (id, a_id, "name") VALUES(1, 100, 'b1');
INSERT INTO tableb (id, a_id, "name") VALUES(2, NULL, 'b2');
INSERT INTO tableb (id, a_id, "name") VALUES(3, NULL, 'b3');
INSERT INTO tableb (id, a_id, "name") VALUES(4, NULL, 'b4');
-- create function for inserting data into tablea and returning these id
CREATE OR REPLACE FUNCTION tablea_inserting()
RETURNS integer
LANGUAGE plpgsql
AS $function$
declare
ret int4;
begin
insert into tablea ("name") values ('test')
returning id into ret;
return ret;
end
$function$
;
-- After then you can update your tableb
update tableb set
a_id = tablea_inserting()
where a_id is null
select * from tableb;
Result:
id a_id name
1 100 b1
2 1 b2
3 2 b3
4 3 b4

UNIQUE constraint failed SQL

I want to create two Tables, but it does not work because of "UNIQUE constraint failed".
Can someone explain to me what is wrong with my querees?
CREATE TABLE A (
ka INT PRIMARY KEY,
a2 VARCHAR(1)
);
INSERT INTO A VALUES (1,'s');
INSERT INTO A VALUES (2,'s');
INSERT INTO A VALUES (3,'s');
INSERT INTO A VALUES (4,'m');
INSERT INTO A VALUES (5,'m');
INSERT INTO A VALUES (6,'b');
INSERT INTO A VALUES (7,'b');
INSERT INTO A VALUES (8,'b');
INSERT INTO A VALUES (9,'b');
CREATE TABLE B (
a2 VARCHAR(1),
b2 INT,
PRIMARY KEY (a2),
FOREIGN KEY (a2) REFERENCES A(a2)
);
INSERT INTO B VALUES ('s',12);
INSERT INTO B VALUES ('s',23);
INSERT INTO B VALUES ('s',34);
INSERT INTO B VALUES ('m',45);
INSERT INTO B VALUES ('m',56);
INSERT INTO B VALUES ('b',67);
INSERT INTO B VALUES ('b',78);
INSERT INTO B VALUES ('b',89);
INSERT INTO B VALUES ('b',90);
(Edited: there is more than one issue here.)
A primary key for table B must be unique. In your case, it needs to be something other than a2. If you need a primary key (usually you do just as a part of good design), you likely need a separate dedicated column.
Something like:
CREATE TABLE B (
kb INT,
a2 VARCHAR(1),
b2 INT,
PRIMARY KEY (kb),
--FOREIGN KEY (a2) REFERENCES A(a2) -- This is also an issue
);
INSERT INTO B VALUES (101, 's',12);
INSERT INTO B VALUES (102, 's',23);
INSERT INTO B VALUES (103, 's',34);
INSERT INTO B VALUES (104, 'm',45);
INSERT INTO B VALUES (105, 'm',56);
INSERT INTO B VALUES (106, 'b',67);
INSERT INTO B VALUES (107, 'b',78);
INSERT INTO B VALUES (108, 'b',89);
INSERT INTO B VALUES (109, 'b',90);
EDIT:
The second issue is that your foreign key from table B is referencing a non-unique column in table A. Foreign keys define a many-to-one relationship, but your data indicates a potentially many-to-many relationship. The first three "s" rows in table B each match all three "s" rows in table A. While you can define a JOIN in a query that matches ON B.a2 = A.a2, you can't use a foreign key to define this relationship.

Why does constraint fail when upsert used in conjunction with triggers?

Please could someone explain why this unique constraint fails and if there is any workaround or suggestions.
With this schema:
CREATE TABLE abc
(
a INTEGER NOT NULL,
b INTEGER NOT NULL,
c INTEGER NOT NULL
);
CREATE UNIQUE INDEX unique_a_b ON abc(a, b);
CREATE TABLE xyz
(
x INTEGER NOT NULL,
y INTEGER NOT NULL,
z INTEGER NOT NULL
);
CREATE UNIQUE INDEX unique_x_y ON xyz(x, y);
I have triggers on a table xyz for both insert and update operations, they both perform insert or replace on table abc which has a unique index.
CREATE TRIGGER on_insert_xyz
AFTER INSERT
ON xyz
BEGIN
INSERT OR REPLACE INTO abc(a, b, c)
SELECT * FROM xyz LIMIT 1;
END;
CREATE TRIGGER on_update_xyz
AFTER UPDATE
ON xyz
BEGIN
INSERT OR REPLACE INTO abc(a, b, c)
SELECT * FROM xyz LIMIT 1;
END;
I have an upsert statement on table xyzthat causes the triggers to execute. If the upsert statement causes the update trigger to execute, then the unique index constraint fails on table abc.
INSERT INTO xyz(x, y, z) VALUES(1, 2, 3) ON CONFLICT(x, y) DO UPDATE SET z = excluded.z -- Works;
INSERT INTO xyz(x, y, z) VALUES(1, 2, 4) ON CONFLICT(x, y) DO UPDATE SET z = excluded.z -- Fails;
UNIQUE constraint failed: abc.a, abc.b

How to insert values in table if there is a primary key on id field in it?

I have trouble, I have table named my_table)
id name
1 A
2 B
3 C
and I want to insert top 2 so, values have autoincrement automaticaly like this
insert into my_table (name) values (A), (B);
Is this possible in postgressql?
May be I should have count() + 1, then count() + 2 here
insert into my_table (id, name) values (count(*) + 1, A), (count(*) + 2, B);
or something like this
because my id has constraint
BIGSEREIAL PRIMARY KEY NOT NULL
And I cant add values without getting the last id in table.
You can do:
create table my_table (
id int not null generated always as identity,
name varchar(10) not null
);
insert into my_table (name) values ('A'), ('B');
Then:
select * from my_table;
Result:
id name
-- ----
1 A
2 B
See running example at db<>fiddle.

PostgreSQL connections constraint

I have table with two columns, id1 and id2.
If i have for example foo-bar respectively in these columns,I need a constraint that forbids entry bar-foo.
Thanks!
CREATE TABLE mytable(
id1 integer,
id2 integer
);
CREATE UNIQUE INDEX ON mytable(least(id1, id2), greatest(id1, id2));
This should ddo the trick:
test=> INSERT INTO mytable VALUES (1, 2);
INSERT 0 1
test=> INSERT INTO mytable VALUES (1, 3);
INSERT 0 1
test=> INSERT INTO mytable VALUES (2, 1);
ERROR: duplicate key value violates unique constraint "mytable_least_greatest_idx"
DETAIL: Key ((LEAST(id1, id2)), (GREATEST(id1, id2)))=(1, 2) already exists.