INSERT, SELECT, VALUES - sql

I have table like this:-
(BL_SUBSCRIBER)
Name Null? Type
----------------------------------------- -------- -------
MSISDN NOT NULL VARCHAR2(20)
SUBSCRIBER_ID NOT NULL VARCHAR2(20)
BILLING_ID VARCHAR2(20)
SUB_TYPE NOT NULL VARCHAR2(2)
SUB_TYPE_EXTRA VARCHAR2(20)
LANGUAGE NOT NULL VARCHAR2(2)
TIME_RESTRICT_FLAG NOT NULL VARCHAR2(1)
and table like this:-
(BL_SUBSCRIBER_PACKAGE)
MSISDN NOT NULL VARCHAR2(50)
PACKAGE_SEQ NOT NULL NUMBER(8)
ID NOT NULL VARCHAR2(20)
OBJTYPE NOT NULL VARCHAR2(10)
TYPE NOT NULL VARCHAR2(10)
I want to fill the table BL_SUBSCRIBER with the MSISDN from BL_SUBSCRIBER_PACKAGE
and at the same time , I want to fill the other columns (NOT NULL) with any data,
I tried the following
insert into BL_SUBSCRIBER (
MSISDN,
SUBSCRIBER_ID,
SUB_TYPE,
LANGUAGE)
values (
select MSISDN from BL_SUBSCRIBER_PACKAGE,
sub_id_seq.nextval, //sub_id_seq is a sequence already defined.
'prepaid',
'EN')
but it gives me errors(missing expression)
SO, can anyone tell me how to copy data from one table to another and insert the default needed data (in this case it is must because it is NOT NULL).
PS:I'm Using Oracle Database
Thanks.

When you use a select as the source for an insert you don't need the values:
insert into BL_SUBSCRIBER (MSISDN,SUBSCRIBER_ID,SUB_TYPE,LANGUAGE)
select MSISDN
sub_id_seq.nextval,
'prepaid',
'EN'
from BL_SUBSCRIBER_PACKAGE;
As usual the correct syntax is documented in the manual:
https://docs.oracle.com/cd/E11882_01/server.112/e41084/statements_9014.htm#SQLRF55051
and it also has an example for this:
https://docs.oracle.com/cd/E11882_01/server.112/e41084/statements_9014.htm#SQLRF55103

try
insert into BL_SUBSCRIBER (MSISDN,SUBSCRIBER_ID,SUB_TYPE,LANGUAGE)
select
MSISDN,
sub_id_seq.nextval, //sub_id_seq is a sequence already defined.
'prepaid',
'EN'
from BL_SUBSCRIBER_PACKAGE;
Also check out #a_horse_with_no_name answer below for some useful Oracle documentation links - https://stackoverflow.com/a/27851367/1466341

Related

Populate snowflake table with default values without selecting default column values from the file data

I am trying to load a table (drop table and load the data - similar to truncate and load) dynamically. Let us assume that table needs to have 4 fields, ID, Name, SeqNo, and DtTimeStamp.
The data is being selected from an externally staged csv\text file that has only two fields (ID and Name). The below query gives an error for the nonmatching of a number of columns. How to resolve that issue?
CREATE OR REPLACE TABLE SOMETABLENAME(ID NUMBER(38,0), Name
VARCHAR(255), SeqNo NUMBER(38,0) NOT NULL AUTOINCREMENT, DtTimeStamp
TIMESTAMP_NTZ(9) NOT NULL DEFAULT CURRENT_TIMESTAMP()) AS SELECT A.$1
AS ID, A.$2 AS Name FROM #EXTERNALSTAGE/SOME_FILE.CSV A;
If you carefully look at the above SQL statement, my table has two extra fields that need to be auto-populated for every row it loads. But I am unable to make it work?
Any suggestions are highly appreciated.
Thanks in Advance!
Sathya
CREATE TABLE … AS SELECT (CTAS)
CREATE TABLE <table_name> ( <col1_name> , <col2_name> , ... ) AS SELECT ...
The number of column names specified must match the number of SELECT list items in the query; the types of the columns are inferred from the types produced by the query.
To resolve it, CTAS and INSERT INTO could be two separate steps:
CREATE OR REPLACE TABLE SOMETABLENAME(
ID NUMBER(38,0),
Name VARCHAR(255),
SeqNo NUMBER(38,0) NOT NULL AUTOINCREMENT,
DtTimeStamp TIMESTAMP_NTZ(9) NOT NULL DEFAULT CURRENT_TIMESTAMP()
);
-- here INSERT/SELECT have matching column list
INSERT INTO SOMETABLENAME(ID, Name)
SELECT A.$1 AS ID, A.$2 AS Name FROM #EXTERNALSTAGE/SOME_FILE.CSV A;

How to update rows with the same foreign key without updating them all

I'm working on my university project and I need some help about Oracle database.
I have two tables USERFORM and ACADEMICTRAINING.
USERFORM
Name Null? Type
-------------- -------- ------------
USER_ID NOT NULL NUMBER(5)
FIRSTNAME NOT NULL VARCHAR2(30)
LASTNAME NOT NULL VARCHAR2(30)
EMAIL NOT NULL VARCHAR2(60)
BORN_DATE NOT NULL DATE
PHONE NOT NULL VARCHAR2(20)
ACCESSPASSWORD NOT NULL VARCHAR2(30)
ACADEMICTRAINING
Name Null? Type
-------------- -------- -------------
AT_ID NOT NULL NUMBER(5)
START_DATE NOT NULL DATE
END_DATE NOT NULL DATE
INSTITUTION NOT NULL VARCHAR2(100)
COURSE NOT NULL VARCHAR2(70)
AT_DESCRIPTION VARCHAR2(200)
AT_ID is a foreign key that references USERFORM on USER_ID column.
I would like to know if there's some way to UPDATE one single row without affecting other rows with the same foreign key.
Your data structure is messed up, which is what is confusing you. Why are you naming a user column AT_ID. Also the foreign keys are not declared. A better approach is:
CREATE TABLE ACADEMICTRAINING (
USER_ID NUMBER(5) NOT NULL FOREIGN KEY REFERENCES USERFORM(USER_ID),
START_DATE DATE NOT NULL,
END_DATE DATE NOT NULL
INSTITUTION VARCHAR2(100) NOT NULL
COURSE VARCHAR2(70) NOT NULL
AT_DESCRIPTION VARCHAR2(200)
);
You really want to have a primary key in the table. Under most circumstances, I would recommend an auto-incrementing primary key. But that is hard to do automatically in Oracle prior to Oracle 12. Such a column should be called something like ACADEMICTRAINING_ID.
Instead, you really want a unique key. I don't know what fits your requirements, but let's say the first two columns cannot be repeated (more columns might be involved). Then:
ALTER TABLE ACADEMICTRAINING ADD CONSTRAINT UNQ_ACADEMICTRAINING_2
UNIQUE (USER_ID, START_DATE);
All that said, what you need in your UPDATE is a way to choose which row. Something like this:
UPDATE ACADEMICTRAINING
SET . . .
WHERE USER_ID = :USER_ID AND START_DATE = :START_DATE;
If you had a primary key, it would look like:
UPDATE ACADEMICTRAINING
SET . . .
WHERE ACADEMICTRAINING_ID = :ACADEMICTRAINING_ID;
Try this.
Update ACADEMICTRAINING
set COURSE = 'BSC.CS'
where AT_ID = (select USER_ID
from USERFORM
where FIRSTNAME = 'Ali'
and LASTNAME = 'Ahmed'
and PHONE = '44425183658558' );

how to define a constraint for column to have alphanumeric values in oracle?

I need to create a table which has a column. the entries should be alphanumeric.
how can i define a constraint for this situation
I tried using,
create table bankAccount
(
accNo varchar2(15) check (accNo like '%[A-Za-Z0-9]%')
);
but during input no data is stored and no entries are created.
You would use REGEXP_LIKE() but if all the characters have to be alphanumeric then you need start and end anchors:
CREATE TABLE bankaccount
( accno VARCHAR2(15) CHECK ( REGEXP_LIKE(accno, '^[A-Za-z0-9]+$') ) );
(Note that you can also use the [[:alnum:]] POSIX character class instead of [A-Za-z0-9].)
If you want the account numbers to be exactly 15 characters, then you might want something like this:
CREATE TABLE bankaccount
( accno VARCHAR2(15) CHECK ( REGEXP_LIKE(accno, '^[A-Za-z0-9]{15}$') ) );
And if you want only uppercase letters:
CREATE TABLE bankaccount
( accno VARCHAR2(15) CHECK ( REGEXP_LIKE(accno, '^[A-Z0-9]+$') ) );
Hope this helps.
You would use regexp_like():
accNo varchar2(15) check (regexp_like(accNo, '^[A-Za-z0-9]+$'))

Oracle adding records from multiple tables

My objective is to build a master Serial No table from many different tables and each Serial No must be unique.
CREATE TABLE "TBL_SERIAL_NUMBER_MASTER"
( "INTERNAL_RECORD_ID" VARCHAR2(60) NOT NULL ENABLE,
"ASSET_ID" VARCHAR2(60),
"SERIAL_NUMBER" VARCHAR2(1000) NOT NULL ENABLE,
"VALID" VARCHAR2(60) DEFAULT 'Valid',
"HOST_NAME" VARCHAR2(255),
CHECK ( valid IN ('Invalid', 'Valid')) ENABLE,
CHECK ( valid IN ('Invalid', 'Valid')) ENABLE,
CHECK ( valid IN ('Invalid', 'Valid')) ENABLE,
CONSTRAINT "TBL_SERIAL_NUMBER_MASTER_CON" PRIMARY KEY ("SERIAL_NUMBER") ENABLE
) ;
CREATE OR REPLACE TRIGGER "TBL_SERIAL_NUMBER_MASTER_INTER" BEFORE
INSERT
ON tbl_serial_number_master FOR EACH ROW WHEN (
NEW.internal_record_id IS NULL
) BEGIN :NEW.internal_record_id := tbl_serial_number_master_inter.NEXTVAL;
END;
/
ALTER TRIGGER "TBL_SERIAL_NUMBER_MASTER_INTER" ENABLE;
I have already updated the SERIAL_NUMBER field using one table. Now I am trying to add more Serial Nos from another table. These other tables have duplicate and null value Serial Nos. Can you please advise how I can create the query to add unique Serial Nos that are already not in the TBL_SERIAL_NUMBER_MASTER.
Please assume following fields for the other table.
TABLE_SOURCE_B
ID :-PK
SERIAL_NUMBER
List item
Name
In your Master Table, 'Internal_Record_Id' has Not Null constraint. So I am inserting values of ID field of Source table into 'internal_record_id'.
Try the following query.
INSERT INTO
TBL_SERIAL_NUMBER_MASTER (INTERNAL_RECORD_ID,SERIAL_NUMBER)
SELECT ID,SERIAL_NUMBER
FROM TABLE_SOURCE_B B
WHERE B.SERIAL_NUMBER NOT IN(SELECT SERIAL_NUMBER
FROM TBL_SERIAL_NUMBER_MASTER);
Hope it helps!

Inserting null values when using bulk insert

I have one table:
CREATE TABLE cust (
cust_id NOT NULL,
cust_name NOT NULL,
address NULL
);
I have to insert these rows into another table:
CREATE TABLE 1cust_det (
cust_id NOT NULL,
cust_name NOT NULL,
address NOT NULL
);
Unfortunately the cust.address column contains NULL values. I want to insert these rows from cust to 1cust_det using a cursor. What do I have to do?
INSERT INTO
cust_det
SELECT
cust_id,
cust_name,
COALESCE(address, 'UNKNOWN')
FROM
cust
If you have access to change the destination table, just add a default to the column.
CREATE TABLE 1cust_det (
cust_id NOT NULL,
cust_name NOT NULL,
address NOT NULL DEFAULT 'DEFAULT_VALUE');
or if you can edit the existing destination table and it doesnt get drooped
ALTER TABLE 1cust_det
ALTER address SET DEFAULT 'DEFAULT_VALUE'
The easiest way if you don't have control of the destination table to add a default value to the address column is to use a case statement in the insert itself. In the example below you can also use a ISNULL evaluation, but you might want to search for empty strings as well. Please try to find a better way to insert instead of using a cursor.
INSERT dbo.1cust_det
(cust_id,cust_name,[address])
SELECT cust_id,cust_name,
CASE
WHEN [address] IS NULL THEN 'some default value'
ELSE [address]
END AS [address]
FROM cust
Above answers are correct. You may have another table that may have address for cust_id. Join that table to get missing address. I have seen that in almost all databases, address is stored for every customer. You must get address where address is NULL in the table cust.