Oracle:Select Statement with If else in Oracle - sql

I have following two tables TestCustomer and TestEmail.I would like to retrieve emailAddress based on email_stat on TestCustomer and outside boolean parameter "noFlag".If noFlag is "true" get all the email addresses associated with customer_id other get only "A" ones.Any Help would be appreciated.
create table TestEmail(emai_id varchar(18),emailaddress varchar(20))
create table TestCustomer(customer_id varchar(18),emai_id varchar(18),email_stat char(1))
Insert Into TestEmail(emai_id,emailaddress)values('12345','abc#gmail.com');
Insert Into TestEmail(emai_id,emailaddress)values('123456','abcd#gmail.com');
Insert Into TestEmail(emai_id,emailaddress)values('123457','abcde#gmail.com');
Insert Into TestCustomer(customer_id,emai_id,email_stat)values('223459','12345','A');
Insert Into TestCustomer(customer_id,emai_id,email_stat)values('223458','123456','I');
Insert Into TestCustomer(customer_id,emai_id,email_stat)values('223459','123457','A');
Expected Input:
customer_id=223458 and noFlag='true'
Expected Output
Expected Input:
customer_id=223458 and noFlag='false'
Expected Output
Empty Result.

SELECT [DISTINCT] emailaddress
FROM TestEmail
JOIN TestCustomer USING (emai_id)
-- insert parameter-1 instead of 223458
WHERE TestCustomer.customer_id = 223458
-- insert parameter-2 instead of 'noFlag'
AND TestCustomer.email_stat = CASE WHEN noFlag = 'true'
THEN TestCustomer.email_stat
ELSE 'A'
END
fiddle

If you just want the emails, you can use exists:
select e.emailaddress
from testemail e
where exists (select 1
from testcustomer c
where c.email_id = e.email_id and
c.customer_id = :customer_id and
(c.email_stat = 'A' or :noflag = 'true')
);

Related

Sql Query to populate insert and update date

I need help in populating ins_dts and upd_dts logic.
Insert and Update date present in both tables so I need to know in coalesce if value is populating from a.col_cmmt_txt, a.col_dscr_txt, a.col_annt_txt, then use insert and update date from test1 table else if populated value from b.target_col_desc then populate insert and update from test2 table :
select
a.schema, a.table, a.column,
coalesce(a.col_cmmt_txt, a.col_dscr_txt, a.col_annt_txt, b.target_col_descr) as coldscr,
a.dw_ins_dts, a.dw_upd_dts
from
test1 a
left join
test2 b on a.schema = upper(b.schema)
and a.table = upper(b.table)
and a.column = upper(target_col)
To me, it looks like a case:
SELECT a.schema,
a.table_,
a.column_,
COALESCE (a.col_cmmt_txt,
a.col_dscr_txt,
a.col_annt_txt,
b.target_col_descr) AS coldscr,
--
CASE
WHEN a.col_cmmt_txt IS NOT NULL
OR a.col_dscr_txt IS NOT NULL
OR a.col_annt_txt IS NOT NULL
THEN
a.dw_ins_dts
ELSE
b.dw_ins_dts
END,
--
CASE
WHEN a.col_cmmt_txt IS NOT NULL
OR a.col_dscr_txt IS NOT NULL
OR a.col_annt_txt IS NOT NULL
THEN
a.dw_upd_dts
ELSE
b.dw_upd_dts
END
FROM test1 a
LEFT JOIN test2 b
ON a.schema = UPPER (b.schema)
AND a.table_ = UPPER (b.table_)
AND a.column_ = UPPER (target_col)

SQL query inputs needed

I have UI where there is an search functionality. There are 2 parameters in search.
User can search of either of the two params to get the result (ie either of it can be null)
I am having difficulties in getting the to write the exact sql (SP) when one of the values is null.
For example as below:
declare #param1, #param2
create table #Ids
(
Id bigint,
Name varchar(10)
)
--Inserting multiple ids in my temp table
IF #param1 IS NOT NULL
BEGIN
INSERT INTO #Ids (Id, Name)
SELECT DISTINCT Id, Name
FROM MainIdTable I
WHERE (I.Name = #param1)
END
SELECT
I.Name, S.ID, S.Value
FROM
SecondTable S
JOIN
#Ids I ON S.Id = P.Id
WHERE
S.Date = '2012-01-06'
AND s.tempId = ISNULL(#param2, p.tempId)
If user enters param1 value, the search works fine
If the user enters both param1 and param2 values, then it also works fine
But if the user doesn't enter a param1 value, but just enters a param2 value, the search doesn't work.
I believe that's because my temp table is empty and when we make a join it returns nothing.
Any workaround to get this working?
Thanks
Select I.Name, S.ID, S.Value from
SecondTable S
LEFT JOIN #Ids I on S.Id = P.Id
where S.Date = '2012-01-06'
and s.tempId = isnull(#param2, p.tempId)
You should use a left join here.

How to set value for row in table if two rows matched with inner join?

I have two table in the database. If Numbercalled matched with phone number I want to update the IsCompanyNumber called to Yes if not matched then No and if the value is Null then it should be unknown.I want do same thing for NumberCalledFrom, if it is matched with Phonenumber column in companynumber table it will say Yes, if not matched it will say No and if value is Null it will say unknown.
Create Table Test(
NumberCalled varchar(15)
,IsCompanyNumberCalled Varchar(5)
,NumberCalledFrom varchar(15)
,IscompanyCalledFrom varchar(5)
);
Create Table CompanyNumber(
ID int identity
,PhoneNumber varchar(15)
);
This is what I have tried so far.
UPDATE T
Set IsNumberCalled = ‘Yes’,
IsCompanyNumberCalled From = ‘Yes’
FROM CompanyNumber as C
Inner Join Test as T
on T.NumberCalled = C.PhoneNumber AND
T.NumberCalledFrom = C.PhoneNumber;
Kind of confused on desired result but from what it seems like you want to do a case statement would work if you want to do a select statement?
Create Table test2 as (
Select
NumberCalled,
CASE
WHEN a.numbercalled = b.phonenumber then 'Yes'
WHEN b.phonenumber is null then 'Unknown'
ELSE 'No'
END AS IsCompanyNumberCalled,
IsCompanyCalledFrom
from test a
left join companynumber b on a.numbercalled = b.phonenumber);

How to fetch all id from table after multiple insertion on a table

I am passing datatable as input parameter to a stored procedure. I have created custom type for it.
Here is my stored procedure:
INSERT INTO Employee
([Name],[Lname],[Code])
SELECT [Name],[Lname],#Code
FROM #tblEmp A
WHERE NOT EXISTS (SELECT 1
FROM Employee B
inner join Contactdetail c
on cid = B.cid
WHERE B.[Name] = A.[Name]
AND B.[Lname] = A.[Lname]
AND C.[mobno] = A.[mobno])
Here I fetching record from datatable and inserting into Employee table. Datatable contain Name,Lname and mobileno. I want to check combination of Name,Lname and mobileno.If combination of it present in Employee table,pls don't insert record([Name], [Lname], #Code ) in Employee.Else Insert.After inserting record from Employee,I want id of all inserted record.Scope_identity give last identity of table.I want all id,which are newly inserted into table because in same sp,I want to do further processing.
You can use Output clause like:
DECLARE #InsertedIDs table(EmployeeID int);
INSERT INTO Employee
([Name],[Lname],[Code])
--
OUTPUT INSERTED.ID
INTO #InsertedIDs
--
SELECT [Name],[Lname],#Code
FROM #tblEmp A
WHERE NOT EXISTS (SELECT 1
FROM Employee B
inner join Contactdetail c
on cid = B.cid
WHERE B.[Name] = A.[Name]
AND B.[Lname] = A.[Lname]
AND C.[mobno] = A.[mobno])
[DEMO]
You can this with a MERGE statement. (Could be there is a mistake in this query, but its just so you get the idea behind it...)
MERGE INTO Employee AS Target
USING (SELECT B.[Name], B.[Lname], C.[mobno]
FROM Employee B
inner join Contactdetail c
on cid = B.cid ) AS source (Name, Lname, mobno)
ON Target.[Name] = Source.[Name]
AND Target.[Lname] = Source.[Lname]
AND Target.[mobno] = Source.[mobno]
WHEN NOT MATCHED BY TARGET THEN
INSERT (Name, Lname, code) VALUES (Name, Lname, #Code);

Update multiple table column values using single query

How would you update data in multiple tables using a single query?
MySQL Example
The equivalent code in MySQL:
UPDATE party p
LEFT JOIN party_name n ON p.party_id = n.party_id
LEFT JOIN party_details d ON p.party_id = d.party_id
LEFT JOIN incident_participant ip ON ip.party_id = p.party_id
LEFT JOIN incident i ON ip.incident_id = i.incident_id
SET
p.employee_id = NULL,
c.em_address = 'x#x.org',
c.ad_postal = 'x',
n.first_name = 'x',
n.last_name = 'x'
WHERE
i.confidential_dt IS NOT NULL
What would be the same statement using Oracle 11g?
Thank you!
RTFM
It seems a single query is insufficient when using Oracle:
http://download-west.oracle.com/docs/cd/B10501_01/server.920/a96540/statements_108a.htm#2067717
/** XXX CODING HORROR... */
Depending on your needs, you could use an updateable view. You create a view of your base tables and add an "instead of" trigger to this view and you update the view directly.
Some example tables:
create table party (
party_id integer,
employee_id integer
);
create table party_name (
party_id integer,
first_name varchar2(120 char),
last_name varchar2(120 char)
);
insert into party values (1,1000);
insert into party values (2,2000);
insert into party values (3,3000);
insert into party_name values (1,'Kipper','Family');
insert into party_name values (2,'Biff','Family');
insert into party_name values (3,'Chip','Family');
commit;
select * from party_v;
PARTY_ID EMPLOYEE_ID FIRST_NAME LAST_NAME
1 1000 Kipper Family
2 2000 Biff Family
3 3000 Chip Family
... then create an updateable view
create or replace view party_v
as
select
p.party_id,
p.employee_id,
n.first_name,
n.last_name
from
party p left join party_name n on p.party_id = n.party_id;
create or replace trigger trg_party_update
instead of update on party_v
for each row
declare
begin
--
update party
set
party_id = :new.party_id,
employee_id = :new.employee_id
where
party_id = :old.party_id;
--
update party_name
set
party_id = :new.party_id,
first_name = :new.first_name,
last_name = :new.last_name
where
party_id = :old.party_id;
--
end;
/
You can now update the view directly...
update party_v
set
employee_id = 42,
last_name = 'Oxford'
where
party_id = 1;
select * from party_v;
PARTY_ID EMPLOYEE_ID FIRST_NAME LAST_NAME
1 42 Kipper Oxford
2 2000 Biff Family
3 3000 Chip Family
I was having the same problem I couldn't find a easy way to do this in Oracle.
Look here:
Oracle Update Statements for more info.
You could use Oracle MERGE statement to do this. It is a bulk update-or-insert kind of statement based on joining the target table with an inline view.
MERGE INTO bonuses D
USING (
SELECT employee_id, salary, department_id FROM employees
WHERE department_id = 80
) S ON (D.employee_id = S.employee_id)
WHEN MATCHED THEN
UPDATE SET D.bonus = D.bonus + S.salary*.01
WHEN NOT MATCHED THEN
INSERT (D.employee_id, D.bonus)
VALUES (S.employee_id, S.salary*0.1);
if you do not need the insert part, you just omit the last 3 lines above.
In some cases it's possible to use PL/SQL to achieve this. In my case I searched for matching rows in two tables by some criteria, then updated each row in a loop.
Something like this:
begin
for r in (
select t1.id as t1_id, t2.id as t2_id
from t1, t2
where ...
) loop
update t1
set ...
where t1.id = r.t1_id;
update t2
set ...
where t2.id = r.t2_id;
end loop;
end;