My merge is not correct in Oracle 11G - sql

Can somebody explain to me what I am doing wrong with this statement. Its pretty basic....
merge into week1wrs
using
(select wr_id,fname,lname from wrname_id) on
(week1wrs.fname=wrname_id.fname and week1wrs.lname=wrname_id.LNAME)
when matched then update set week1wrs.WR_ID=wrname_id.wr_id
when not matched update set week1wrs.Name_id='';
* I am using oracle 11g

use table alias names as Target (T) and Source (S)
merge into week1wrs T
using
(select wr_id,fname,lname from wrname_id) S on
(S.fname=T.fname and S.lname=T.LNAME)
when matched then update set T.WR_ID=S.wr_id
when not matched --need to be insert here.

when not matched update set week1wrs.Name_id=''
When not matched you can only INSERT, you cannot update.
Merge syntax:
MERGE INTO table
USING table | subquery
ON condition
WHEN MATCHED THEN UPDATE SET col = expression | DEFAULT
where_clause
DELETE where_clause
WHEN NOT MATCHED THEN INSERT (col, col2)
VALUES (expr1, expr2 | DEFAULT)
where_clause
WHERE condition;

Related

How to update multiple records in one go

I want to update columns of a table whose values are NULL and I want to do this for 5 rows, but I'm getting the error : missing SET keyword
I am running the query in oracle SQL developer
The query I'm using is
UPDATE top(5) table_name
set col1=value1,
col2=value2,
col3=value3 where col1=null;
Second query I used is
UPDATE table_name
set col1=value1,
col2=value2,
col3=value3 where col1=null and rownum<=5;
You can do this in below way:
UPDATE table_name
set (col1,col2,col3) = (select col1,col2,col3 from table_name where col1 is null and rownum<=5)
where col1 is null;

MERGE statement DELETE alternative in SQL Server

I have a Query using T-SQL MERGE Statement. Due to performance issues I am re writing the Query using IF Exists Update and If Not Exists Insert. I am able to write Insert/Update without any issue. But I am unable to handle the DELETE. Can some one please help me on this?
Here is the sample
---SAMPLE MERGE STATEMENT
MERGE
member_topic AS target
USING
someOtherTable AS source
ON
target.mt_member = source.mt_member
WHEN MATCHED THEN
UPDATE SET target.mt_notes = source.mt_notes
WHEN NOT MATCHED THEN
INSERT (mt_member, mt_topic, mt_notes) VALUES (source.mt_member, source.mt_notes)
WHEN NOT MATCHED BY SOURCE THEN
DELETE member_topic;
--UPDATE
UPDATE T SET T.mt_notes = S.mt_notes
FROM member_topic T
JOIN someOtherTable S ON T.mt_member=S.mt_member
--INSERT
INSERT INTO member_topic(mt_member, mt_topic, mt_notes)
SELECT mt_member, mt_topic, mt_notes
FROM someOtherTable S
WHERE NOT EXISTS(SELECT 1
FROM member_topic T
WHERE T.mt_member=S.mt_member)
How to handle
WHEN NOT MATCHED BY SOURCE THEN
DELETE member_topic;
in single DELETE Statement.
a sample script to be embedded between begin and end in proc
MERGE dbo.Tablet AS TARGET
USING dbo.QueryView AS SOURCE
ON (
TARGET.[ID] = SOURCE.[ID]
)
WHEN MATCHED
THEN
UPDATE SET
TARGET.[ID] = SOURCE.[ID]
WHEN NOT MATCHED BY TARGET THEN
INSERT (ID, [Name] )
VALUES (SOURCE.[ID], SOURCE.[Name] )
WHEN NOT MATCHED BY SOURCE THEN
DELETE;
Try
DELETE T
FROM member_topic T
WHERE NOT EXISTS(SELECT 1
FROM someOtherTable S
WHERE T.mt_member=S.mt_member)
DELETE t
FROM member_topic t
LEFT JOIN someOtherTable s ON t.mt_member = s.mt_member
WHERE s.mt_member IS NULL

How to update all of the values of a table using merge into statement

How to update all the values from source table to destination table using merge into statement?
What I am trying to do is something like:
merge into src_table
using (select * from dest) dest_table
on (<some_condition>)
when matched then update set src_table.* = dest_table.*
where <condition>
I didn't find anything related to this on Google. I know one can achieve this using execute immediate style statement but I am looking for a better way.
you can do it with pl/sql
for src in ( select * from B ) loop
update A set ROW = src where A.id = src.id;
end loop;
or you can use alter table;
alter table your_table
rename to
your_new_table;

SQL Server : use a transaction in the then clause of merge

In a merge statement, when not matched, I need to insert into target table and update another table. How can I achieve this?
merge table1 as TARGET
using table2 as SOURCE ON <conditions>
when not matched by target
then
/*--------can i do this?---------*/
BEGIN TRANSACTION
insert (columnnames) values(v1,..., vn) /*insert into target*/
update source
set column1 = value1 /*update source*/
END TRANSACTION;
The whole merge statement is atomic (either the whole statement completes or the whole statement gets rolled back) so that you don't need to create a transaction.
Here's an example from Microsoft:
MERGE Production.UnitMeasure AS target
USING (SELECT #UnitMeasureCode, #Name) AS source (UnitMeasureCode, Name)
ON (target.UnitMeasureCode = source.UnitMeasureCode)
WHEN MATCHED THEN
UPDATE SET Name = source.Name
WHEN NOT MATCHED THEN
INSERT (UnitMeasureCode, Name)
VALUES (source.UnitMeasureCode, source.Name)
OUTPUT deleted.*, $action, inserted.* INTO #MyTempTable;

Having MERGE INTO do 2 things when Not Matched?

I am using the MERGE INTO statement to work with some tables, and I've a simple question. How can I make a Matched/Not Matched Statement do 2 things? For example, I have this and it works:
MERGE INTO VMFG.dbo._AR_Mill1ActiveSchedule t --target
USING #temp --source
On t.Base_ID = #temp.WORKORDER_BASE_ID AND t.Lot_ID = #temp.WORKORDER_Lot_ID
WHEN MATCHED AND #temp.rollstatus = 'R' THEN
UPDATE
SET t.sawStatus = #temp.sawstatus, t.rollStatus = #temp.rollstatus
WHEN NOT MATCHED BY TARGET THEN
INSERT (BASE_ID, LOT_ID, sawStatus, rollstatus, preheatcheck) VALUES (#temp.WorkOrder_Base_ID, #temp.WorkOrder_Lot_ID, #temp.sawStatus, #temp.rollStatus, 'False')
WHEN NOT MATCHED BY SOURCE AND t.SawStatus = 'C' THEN
Delete ;
Drop Table #temp
Now, I want to accomplish something like this:
MERGE INTO VMFG.dbo._AR_Mill1ActiveSchedule t --target
USING #temp --source
On t.Base_ID = #temp.WORKORDER_BASE_ID AND t.Lot_ID = #temp.WORKORDER_Lot_ID
WHEN MATCHED AND #temp.rollstatus = 'R' THEN
UPDATE
SET t.sawStatus = #temp.sawstatus, t.rollStatus = #temp.rollstatus
WHEN NOT MATCHED BY TARGET THEN
INSERT (BASE_ID, LOT_ID, sawStatus, rollstatus, preheatcheck) VALUES (#temp.WorkOrder_Base_ID, #temp.WorkOrder_Lot_ID, #temp.sawStatus, #temp.rollStatus, 'False')
WHEN NOT MATCHED BY SOURCE AND t.SawStatus = 'C' THEN
INSERT INTO _AR_Mill1RemovedWO (BASE_ID, LOT_ID) VALUES (#temp.WorkOrder_Base_ID, #temp.WorkOrder_Lot_ID)
Delete ;
Drop Table #temp
However, when I run this I get the error "Incorrect syntax near the keyword 'INTO'".
I've tried using the OUTPUT clause but I couldn't get it to work correctly, and would rather use an insert statement anyways if possible.
Thank you :)
EDIT:
The Output clause would be awesome to use, but I'll explain why it hasn't worked. When I used it, i.e.:
....
WHEN NOT MATCHED BY SOURCE AND t.SawStatus = 'C' THEN
--INSERT INTO _AR_Mill1RemovedWO (BASE_ID, LOT_ID) VALUES (#temp.WorkOrder_Base_ID, #temp.WorkOrder_Lot_ID)
Delete
OUTPUT deleted.Base_ID, deleted.Lot_ID INTO VMFG.dbo._AR_Mill1RemovedWO
;
Drop Table #temp
I run in to a problem. It adds rows to my table that weren't actually deleted. It's like it's just adding everything, regardless of being deleted. Is there a reason for this?
This is impossible to do with a single MERGE statement. Use the OUTPUT clause to direct information about the writes executed into a table variable. Execute a second statement such as INSERT to write to the second table.