Import from .sql file Oracle SQL Developer excluding duplicates - sql

I have exported a table from one database using Oracle SQL Developer as .sql file and want to import it into another database that has exactly the same table, but the problem is that some entries appear in both tables.
Is there a way when importing using Oracle SQL Developer to exclude entries that already exist in the destination table?

There are at least two ways:
You can use the SQLLDR tool or external table to load
You can load your sql file into the database and then remove duplicates.
Let's use this file:
data.sql
insert into test_table (id) values (1);
insert into test_table (id) values (1);
insert into test_table (id) values (2);
insert into test_table (id) values (2);
insert into test_table (id) values (2);
insert into test_table (id) values (3);
insert into test_table (id) values (3);
SQLLDR:
At first you create integrity constraints for your table for example:
SQL> create table test_table (
2 id number(10) primary key
3 );
Table created.
Then create a control file:
LOAD DATA
INFILE data.sql
INTO TABLE test_table
(
id position(37:37)
)
After running you will see:
SQL> select * from test_table;
ID
----------
1
2
3
And the bad file (This lines were rejected because of the integrity violation):
data.bad
insert into test_table (id) values (1);
insert into test_table (id) values (2);
insert into test_table (id) values (2);
insert into test_table (id) values (3);
You can generate the external table using this control file, so I don't show you how to use it.
Load and remove duplicates:
Let's recreate the test_table table:
SQL> create table test_table (
2 id number(10)
3 );
Table created.
Using SQL Developer load your sql file and check the content:
SQL> select * from test_table;
ID
----------
1
1
2
2
2
3
3
7 rows selected.
and then remove duplicates:
SQL> delete test_table where rowid not in (select min(rowid) from test_table group by id);
4 rows deleted.
SQL> select * from test_table;
ID
----------
1
2
3
I believe there is a way more ways to complete your tasks, I showed only ways that came in my head right away.

Related

Oracle if value to be inserted in foreign key is -1, insert null instead

I have a xml script I'm reading from to populate my database with data. One of the nodes in the xml file don't have a idDirector field (the nodes are movies) and so the xml reads a -1 as idDirector and then my stored procedure tries to insert -1 into the fk field and this makes my database returna constraint error : director -1 doesn't exist in Director table. How can I make it so it inserts null instead and make my fk field nullable?
CREATE TABLE Film (
PRIMARY KEY (idFilm),
FOREIGN KEY (idDirector) REFERENCES Director
);
Thank you
Looks like CASE to me, e.g.
insert into film (id_film, id_director)
select id_film,
case when id_director = -1 then null
else id_director
end
from ...
Will it work? Yes:
SQL> create table director (id number primary key);
Table created.
SQL> create table film (id number primary key, id_director number references director);
Table created.
SQL> insert into director values (100);
1 row created.
Inserting -1 fails:
SQL> insert into film (id, id_director) values (1, -1);
insert into film (id, id_director) values (1, -1)
*
ERROR at line 1:
ORA-02291: integrity constraint (SCOTT.SYS_C0065885) violated - parent key not
found
Inserting NULL works:
SQL> insert into film (id, id_director) values (1, null);
1 row created.
SQL>

Is there any difference on a table having PK and having and UNIQUE constraint

In TOAD, I can see my table said doesn't have PK. But there is an unique constraint for the PK candidate.
I try to make the field PK but toad said there is already a constraint for it on the table.
And can't remove the constraint because said someone else depend on it.
So should I leave it like that. Or go the extra mile disable all dependencies remove the unique constraint and create a PK?
Let me try to explain it. As Eric said, unique key constraint will accept (many) nulls for the constrained column.
First, create a table with unique key constraint (the one you have now):
SQL> create table test (id number constraint uk_test unique, --> unique key constraint
2 name varchar2(20));
Table created.
SQL> -- This is the first record - no problem with it
SQL> insert into test (id, name) values (1, 'Little');
1 row created.
SQL> -- Uniqueness violated
SQL> insert into test (id, name) values (1, 'Foot');
insert into test (id, name) values (1, 'Foot')
*
ERROR at line 1:
ORA-00001: unique constraint (SCOTT.UK_TEST) violated
SQL> -- Let's insert some NULL values into the constrained column
SQL> insert into test (id, name) values (null, 'Foot');
1 row created.
SQL> insert into test (id, name) values (null, 'Big');
1 row created.
SQL> -- The result: not too pretty, eh?
SQL> select * From test;
ID NAME
---------- --------------------
1 Little
Foot
Big
A step further: apply a new, NOT NULL constraint to the unique key column, so that it "acts" as if it were a primary key:
SQL> delete from test;
3 rows deleted.
SQL> -- add NOT NULL constraint
SQL> alter table test modify id not null;
Table altered.
SQL> -- The first record is OK
SQL> insert into test (id, name) values (1, 'Little');
1 row created.
SQL> -- Uniqueness violated
SQL> insert into test (id, name) values (1, 'Foot');
insert into test (id, name) values (1, 'Foot')
*
ERROR at line 1:
ORA-00001: unique constraint (SCOTT.UK_TEST) violated
SQL> -- This worked previously, but won't any longer because of the NOT NULL constraint
SQL> insert into test (id, name) values (null, 'Foot');
insert into test (id, name) values (null, 'Foot')
*
ERROR at line 1:
ORA-01400: cannot insert NULL into ("SCOTT"."TEST"."ID")
Finally, to show that now it acts as if it were a primary key constraint:
SQL> delete from test;
1 row deleted.
SQL> -- Let's drop the unique key constraint
SQL> alter table test drop constraint uk_test;
Table altered.
SQL> -- Add the primary key constraint (no duplicates, no nulls)
SQL> alter table test add constraint pk_test primary key (id);
Table altered.
SQL> -- The first record is OK
SQL> insert into test (id, name) values (1, 'Little');
1 row created.
SQL> -- Uniqueness violated
SQL> insert into test (id, name) values (1, 'Foot');
insert into test (id, name) values (1, 'Foot')
*
ERROR at line 1:
ORA-00001: unique constraint (SCOTT.PK_TEST) violated
SQL> -- Not null violated
SQL> insert into test (id, name) values (null, 'Foot');
insert into test (id, name) values (null, 'Foot')
*
ERROR at line 1:
ORA-01400: cannot insert NULL into ("SCOTT"."TEST"."ID")
Basically, now you got the same errors as previously, i.e. primary key = unique key + NOT NULL.
You can't create a primary key if the column is already constrained by the unique key - you already know that.
As you can't drop the unique key constraint (because foreign keys reference it), apply the NOT NULL constraint to that column.
Alternatively,
drop all foreign key constraints
drop unique key
create primary key
recreate foreign key constraints
You can replace the UNIQUE constraint for a PK in three easy steps:
Just create the PK with the same column(s).
Then change all FKs to make them point to the PK constraint instead of the UNIQUE constraint.
Finally, drop the UNIQUE constraint.
Easy.

PL/SQL developer how to get the row that made the insert fail?

I'm doing a method that inserts into the table which has a unique column. What I don't know is if I can access the insert value that made the insert fail.
For example:
table1(id,name, phone);
name is unique.
insert (1,a,123);
insert (2,a,1234);
What I want is when I do the second insert I to return the id value '1' without having to recur to a query.
Thank you in advance.
From oracle 10g r2 you can use log errors clause of insert command to log errors in a separate table. Here is an example:
SQL> create table test_table(
2 id number primary key,
3 col1 varchar2(7)
4 )
5 ;
Table created
-- creates a table for logging errors (table name will be prefaced with err$_)
SQL> begin dbms_errlog.create_error_log('TEST_TABLE'); end;
2 /
PL/SQL procedure successfully completed
-- violates primary key constraint
SQL> insert into test_table(id, col1)
2 ( select 1, level
3 from dual
4 connect by level <= 3)
5 log errors reject limit unlimited;
1 row inserted
SQL> commit;
SQL> select * from test_table;
ID COL1
---------- -------
1 1
SQL> select * from err$_test_table;
ORA_ERR_NUMBER$ ORA_ERR_MESG$ ORA_ERR_ROWID$ ORA_ERR_OPTYP$ ORA_ERR_TAG$ ID COL1
--------------- ------------------------------------------------------------------------------------------------------------
1 ORA-00001: unique constraint (HR.SYS_C008315) violated I 1 2
1 ORA-00001: unique constraint (HR.SYS_C008315) violated I 1 3
maybe you can write a trigger(before insert) on your table, on which insert about to happen. In this you can check if the column value(name) already exists in table.
In case it does you may insert this duplicate record in another table for further reference
Another approach is to write the insert in a procedure where the name may be checked and the duplicate name could be stored in a table.
Hope it helps

SQLPlus AUTO_INCREMENT Error

When I try and run the following command in SQLPlus:
CREATE TABLE Hotel
(hotelNo NUMBER(4) NOT NULL AUTO_INCREMENT,
hotelName VARCHAR(20) NOT NULL,
city VARCHAR(50) NOT NULL,
CONSTRAINT hotelNo_pk PRIMARY KEY (hotelNo));
I get the following error:
(hotelNo NUMBER(4) NOT NULL AUTO_INCREMENT,
*
ERROR at line 2:
ORA-00907: missing right parenthesis
What am I doing wrong?
Many will gripe about this not being a standard feature in Oracle, but when it’s as easy as two more commands after your CREATE TABLE command I can’t see any good reason to use fancy SQL on every insert.
First let’s create a simple table to play with.
SQL> CREATE TABLE test
(id NUMBER PRIMARY KEY,
name VARCHAR2(30));
Table created.
Now we’ll assume we want ID to be an auto increment field. First we need a sequence to grab values from.
SQL> CREATE SEQUENCE test_sequence
START WITH 1
INCREMENT BY 1;
Sequence created.
Now we can use that sequence in a BEFORE INSERT trigger on the table.
CREATE OR REPLACE TRIGGER test_trigger
BEFORE INSERT
ON test
REFERENCING NEW AS NEW
FOR EACH ROW
BEGIN
SELECT test_sequence.nextval INTO :NEW.ID FROM dual;
END;
/
SQL> INSERT INTO test (name) VALUES ('Jon');
1 row created.
SQL> INSERT INTO test (name) VALUES (’Bork’);
1 row created.
SQL> INSERT INTO test (name) VALUES (’Matt’);
1 row created.
SQL> SELECT * FROM test;
ID NAME
———- ——————————
1 Jon
2 Bork
3 Matt
Oracle has no auto_increment, you need to use sequences.
Or - starting with Oracle 12.1 - you can simply have:
CREATE TABLE employee
(
id NUMBER GENERATED by default on null as IDENTITY
....
)

DB2 Temp Tables: Not storing or not retrieving information

I'm an MSSQL guy, but I'm working on a DB2 query that needs to create a temp table, insert into it, and do stuff with it. As a much-shortened test, I'm using the following query, which is providing the same result..
declare global temporary table tt_testingSyntax (id int);
insert into session.tt_testingSyntax (id) values (1);
insert into session.tt_testingSyntax (id) values (2);
insert into session.tt_testingSyntax (id) values (3);
insert into session.tt_testingSyntax (id) values (4);
select * from session.tt_testingSyntax;
Zero rows are returned. Why would that be? I've created the tablespace and verified the table is in scope throughout the query.
Try:
declare global temporary table tt_testingSyntax (id int)
ON COMMIT PRESERVE ROWS NOT LOGGED;
insert into session.tt_testingSyntax (id) values (1);
insert into session.tt_testingSyntax (id) values (2);
insert into session.tt_testingSyntax (id) values (3);
insert into session.tt_testingSyntax (id) values (4);
select * from session.tt_testingSyntax;
There are two options...ON COMMIT DELETE ROWS (the default) or ON COMMIT PRESERVE ROWS.
I ended up unknowingly having access to create my own tables (i.e. for user X, I could create X.temp1). Since this query need only be run once, this works fine. Thanks.