I'm working with 3 tables. Based on the contents of 1 or more fields in each table, I need to update 1 of the tables with constant data. My select works great to discover how many records will need to be updated, but I can't seem to get the update to work. I co-worker, with more DB2 SQL experience, sent me code to try. His runs without error, but doesn't get the join and 'where' conditions correct to update only the needed records - it is updating way too many records.
Here is the select that is working correctly:
select *
from mylib.tabcp
inner join mylib.tabc c on cpactnum = c.actnum
inner join mylib.tabt t on cpactnum = t.actnum and cptagid = t.tagid
where (cpstatus = 'Active' and t.tagsts = 'P' and (c.actsts = 'A' or c.actsts = 'D'))
tabcp has these fields: cpactnum cpstatus cptagid
tabc has: actnum actsts
tabt has: actnum tagid tagsts
I need to update some fields in tabcp when: tabcp status is active, tabc status is A or D and tabt status is P
Here is the update my co-worker gave me - it runs, doesn't get any errors, but doesn't correctly select the records to update.
update tabcp
set cpstatus = 'Inactive',
cpdelstamp = current_timestamp,
cpdeldate = current_date,
cpdeltime = current_time,
cpdeluser = current_user
where cpstatus = 'Active'
and cpactnum in
(select e.cpactnum from tabcp e
inner join tabc c on e.cpactnum = c.actnum
inner join tabt k on e.cpactnum = k.actnum
and e.cptagid = k.tagid
where c.actsts in ('A','D') and k.tagsts = 'P')
I am too unfamiliar with DB2 SQL updating. I've tried various changes and, thus far, I just haven't gotten the 'combination' correct.
Can anyone help me, please?
Thank you!
UPDATE mylib.tabcp p
set cpstatus = 'Inactive',
cpdelstamp = current_timestamp,
cpdeldate = current_date,
cpdeltime = current_time,
cpdeluser = current_user
WHERE EXISTS
(
SELECT 1
FROM mylib.tabc c, mylib.tabt t
WHERE
p.cpactnum = c.actnum
and p.cpactnum = t.actnum and p.cptagid = t.tagid
and p.cpstatus = 'Active' and t.tagsts = 'P' and c.actsts in ('A', 'D')
)
Please try this code
enter code here
update tp
set cpstatus = 'Inactive',
cpdelstamp = current_timestamp,
cpdeldate = current_date,
cpdeltime = current_time,
cpdeluser = CURRENT_USER
from mylib.tabcp tp
where cpstatus = 'Active'
and cpactnum in
(select e.cpactnum from tabcp e
inner join tabc c on e.cpactnum = c.actnum
inner join tabt k on e.cpactnum = k.actnum
and e.cptagid = k.tagid
where c.actsts in ('A','D') and k.tagsts = 'P')
I'm attempting to update the LAST_INSPECTION_FW field for all records in the VEHICLES_FW table with the last JOB_DATE_FW for records with the REASON_CODE_FW = 35. However, what's happening is that once the below code is executed, it's not taking into consideration the WHERE clause. This causes all of the records to update when it should just be updating those with the REASON_CODE_FW = 35.
Is there a way to restructure this code to get it working correctly? Please help, thanks!
UPDATE VEHICLES_FW
SET VEHICLES_FW.LAST_INSPECTION_FW = JOB_HEADERS_FW.FIELD2MAX
FROM VEHICLES_FW
INNER JOIN (SELECT VEHICLE_ID_FW, MAX(JOB_DATE_FW) AS FIELD2MAX
FROM JOB_HEADERS_FW
GROUP BY VEHICLE_ID_FW) AS JOB_HEADERS_FW
ON VEHICLES_FW.VEHICLE_ID_FW = JOB_HEADERS_FW.VEHICLE_ID_FW
INNER JOIN JOB_DETAILS_FW
ON JOB_NUMBER_FW = JOB_NUMBER_FW
WHERE REASON_CODE_FW = '35'
Common Table Expressions are your friend here. SQL Server's strange UPDATE ... FROM syntax is not. EG
with JOB_HEADERS_FW_BY_VEHICLE_ID as
(
SELECT VEHICLE_ID_FW, MAX(JOB_DATE_FW) AS FIELD2MAX
FROM JOB_HEADERS_FW
GROUP BY VEHICLE_ID_FW
), q as
(
Select VEHICLES_FW.LAST_INSPECTION_FW, JOB_HEADERS_FW_BY_VEHICLE_ID.FIELD2MAX NEW_LAST_INSPECTION_FW
FROM VEHICLES_FW
INNER JOIN JOB_HEADERS_FW_BY_VEHICLE_ID
ON VEHICLES_FW.VEHICLE_ID_FW = JOB_HEADERS_FW_BY_VEHICLE_ID.VEHICLE_ID_FW
INNER JOIN JOB_DETAILS_FW
ON JOB_NUMBER_FW = JOB_NUMBER_FW
WHERE REASON_CODE_FW = '35'
)
UPDATE q set LAST_INSPECTION_FW = NEW_LAST_INSPECTION_FW
I suspect this does what you want:
update v
set last_inspection_fw = (
select max(j.job_date_fw)
from job_headers_fw j
inner join job_details_fw jd on jd.job_number_fw = j.job_number_fw
where j.vehicle_id_fw = v.vehicle_id_fw and jd.reason_code_fw = 35
)
from vehicles_fw v
SELECT
Email_address, COUNT(Order_date)
FROM
(SELECT
cust.Email_address, COUNT(ol.Variant_name), ord.Order_date
FROM
DMW_Order_Line_v3 ol
JOIN
DMW_Order_v3 ord ON ol.Unique_transaction_identifier = ord.Unique_transaction_identifier
AND ol.Brand_country = ord.Brand_country
JOIN
DMW_Customer_v3 cust ON ord.Email_address = cust.Email_address
AND ord.Brand_country = cust.Brand_country
WHERE
ord.Brand_country = 'kiehls-emea_CZ'
AND cust.Address_country = 'CZ'
AND cust.Optin_email != 'False'
AND ol.Line_status = 'SHIPPED'
AND ol.Variant_name = 'Sample'
GROUP BY
cust.Email_address, ord.Order_date
HAVING
COUNT(ol.Variant_name) >= 4)
GROUP BY
Email_address
Please, forgive me that I'm posting the whole body of the code. But it might be helpful somehow, who knows. As you can see it is a query on subquery containing joins. I'm using Salesforce SQL. When I run the code, I get this error:
Error saving the query field. Incorrect syntax near the keyword 'GROUP'.
What am I doing wrong? Besides being a noob ;-)
You don't need the count column in the subquery:
SELECT Email_address, COUNT(*)
FROM (SELECT cust.Email_address, ord.Order_date
FROM DMW_Order_Line_v3 ol JOIN
DMW_Order_v3 ord
ON ol.Unique_transaction_identifier = ord.Unique_transaction_identifier AND
ol.Brand_country = ord.Brand_country JOIN
DMW_Customer_v3 cust
ON ord.Email_address = cust.Email_address AND
ord.Brand_country = cust.Brand_country
WHERE ord.Brand_country = 'kiehls-emea_CZ' AND
cust.Address_country = 'CZ' AND
cust.Optin_email <> 'False' AND
ol.Line_status = 'SHIPPED' AND
ol.Variant_name = 'Sample'
GROUP BY cust.Email_address, ord.Order_date
HAVING COUNT(ol.Variant_name) >= 4
) e
GROUP BY Email_Address
I want to fetch the following sql query, used in SQL transformation, using INFA repo tables.
In mappings --> sql transformation --> SQL ports --> SQL query
The data you are looking for is in column OPB_METAEXT_VAL.PM_VALUE on the table OPB_METAEXT_VAL
SELECT *
FROM OPB_METAEXT_VAL
WHERE METAEXT_NAME='SQL_Query'
Large Statements may be spread across multiple rows so order by OPB_METAEXT_VAL.LINE_NO.
You can join to OPB_SUBJECT on OPB_SUBJECT.SUBJ_ID = OPB_METAEXT_VAL.SUBJECT_ID to get the folder name.
You can also join to OPB_WIDGET_INST on OPB_WIDGET_INST.WIDGET_ID = OPB_METAEXT_VAL.OBJECT_ID AND OPB_WIDGET_INST.REF_VERSION_NUMBER = OPB_METAEXT_VAL.VERSION_NUMBER to get other details about the transformation.
You can then further join to other tables for example if you wanted the folder name, workflow/worklet, session, mapping, transformation, SQL, AND database connection then use the following:
WITH OPB_SESS_CNX_REFS_WRAPPER AS
(
SELECT OPB_SESS_CNX_REFS.*,
rank() over(
partition BY
WORKFLOW_ID,
SESSION_ID,
SESSION_INST_ID,
PROC_INSTANCE_ID
order by
VERSION_NUMBER DESC,
SESS_WIDG_INST_ID ASC
) AS THE_RANK
FROM OPB_SESS_CNX_REFS
)
SELECT OPB_SUBJECT.SUBJ_NAME AS FOLDER
, WORKFLOW.TASK_NAME AS WORKFLOW_WORKLET_NAME
, OPB_TASK.TASK_NAME AS SESSION_NAME
, OPB_MAPPING.MAPPING_NAME
, OPB_WIDGET_INST.INSTANCE_NAME
, OPB_METAEXT_VAL.PM_VALUE
, OPB_METAEXT_VAL.LINE_NO
,(CASE WHEN OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_VALUE IN ('$Target','$Source') THEN OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_VALUE ||'-->' ||OPB_TASK_ATTR.ATTR_VALUE
ELSE NVL(OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_VALUE,OPB_CNX.OBJECT_NAME) END) AS CNX_NAME
FROM OPB_MAPPING
INNER JOIN OPB_SUBJECT ON (OPB_MAPPING.SUBJECT_ID = OPB_SUBJECT.SUBJ_ID
AND OPB_MAPPING.IS_VISIBLE=1)
INNER JOIN OPB_WIDGET_INST ON (OPB_WIDGET_INST.MAPPING_ID = OPB_MAPPING.MAPPING_ID
AND OPB_WIDGET_INST.VERSION_NUMBER = OPB_MAPPING.VERSION_NUMBER)
LEFT JOIN OPB_WIDGET ON (OPB_WIDGET_INST.WIDGET_ID = OPB_WIDGET.WIDGET_ID
AND OPB_WIDGET.IS_VISIBLE = OPB_MAPPING.IS_VISIBLE)
INNER JOIN OPB_METAEXT_VAL ON (OPB_METAEXT_VAL.OBJECT_ID = OPB_WIDGET_INST.WIDGET_ID
AND OPB_METAEXT_VAL.VERSION_NUMBER = OPB_WIDGET_INST.REF_VERSION_NUMBER
AND OPB_METAEXT_VAL.METAEXT_NAME='SQL_Query')
INNER JOIN OPB_SESSION ON (OPB_SESSION.MAPPING_ID = OPB_MAPPING.MAPPING_ID)
INNER JOIN OPB_TASK ON (OPB_SESSION.SESSION_ID = OPB_TASK.TASK_ID
AND OPB_TASK.IS_VISIBLE = OPB_MAPPING.IS_VISIBLE
AND OPB_SESSION.VERSION_NUMBER = OPB_TASK.VERSION_NUMBER)
INNER JOIN OPB_TASK WORKFLOW ON (OPB_TASK.RU_PARENT_ID = WORKFLOW.TASK_ID
AND WORKFLOW.IS_VISIBLE = OPB_MAPPING.IS_VISIBLE)
INNER JOIN OPB_SWIDGET_INST ON (OPB_SESSION.SESSION_ID = OPB_SWIDGET_INST.SESSION_ID
AND OPB_SESSION.VERSION_NUMBER = OPB_SWIDGET_INST.VERSION_NUMBER
AND OPB_SWIDGET_INST.INSTANCE_ID = OPB_WIDGET_INST.INSTANCE_ID )
LEFT JOIN OPB_SESS_EXTNS ON (OPB_SWIDGET_INST.SESSION_ID = OPB_SESS_EXTNS.SESSION_ID
AND OPB_SWIDGET_INST.VERSION_NUMBER = OPB_SESS_EXTNS.VERSION_NUMBER
AND OPB_SWIDGET_INST.SESS_WIDG_INST_ID = OPB_SESS_EXTNS.SESS_WIDG_INST_ID)
LEFT JOIN OPB_SESS_CNX_REFS_WRAPPER ON (OPB_SESS_CNX_REFS_WRAPPER.THE_RANK = 1
AND OPB_SESS_EXTNS.SESSION_ID = OPB_SESS_CNX_REFS_WRAPPER.SESSION_ID
AND OPB_SESS_EXTNS.PROC_INSTANCE_ID = OPB_SESS_CNX_REFS_WRAPPER.PROC_INSTANCE_ID)
LEFT JOIN OPB_CNX ON (OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_TYPE = OPB_CNX.OBJECT_TYPE
AND OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_SUBTYP = OPB_CNX.OBJECT_SUBTYPE
AND OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_ID = OPB_CNX.OBJECT_ID)
LEFT JOIN OPB_MMD_TASK_ATTR ON (OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_VALUE = SUBSTR(OPB_MMD_TASK_ATTR.ATTR_NAME,1,7)
AND OPB_SESS_CNX_REFS_WRAPPER.REF_OBJECT_VALUE IN ('$Target','$Source'))
LEFT JOIN OPB_TASK_ATTR ON (OPB_TASK_ATTR.TASK_TYPE = OPB_MMD_TASK_ATTR.OBJECT_TYPE_ID
AND OPB_TASK_ATTR.ATTR_ID = OPB_MMD_TASK_ATTR.ATTR_ID
AND OPB_TASK_ATTR.TASK_ID = OPB_TASK.TASK_ID
AND OPB_TASK_ATTR.VERSION_NUMBER = OPB_SWIDGET_INST.VERSION_NUMBER)
WHERE OPB_SUBJECT.SUBJ_NAME = '<YOUR FOLDER NAME>'
ORDER BY OPB_SUBJECT.SUBJ_NAME
, WORKFLOW.TASK_NAME
, OPB_TASK.TASK_NAME
, OPB_MAPPING.MAPPING_NAME
, OPB_WIDGET_INST.INSTANCE_NAME
, OPB_METAEXT_VAL.LINE_NO
I am new to SQLDeveloper. Please help me in correcting the merge syntax.I want to merge the data from act_sl tavle into act_sls_0 table
I am using 2 joins in From Clause.
But I am Getting Errors :
Error(13,13): PL/SQL: ORA-00969: missing ON keyword
Error(4,1): PL/SQL: SQL Statement ignored
merge into act_sls_0 using(
( select * from
(select a_0.asp, gadim.uic as ga, pmm_styleid, week, colorcode , sizecode, storenum, units_asly,retail_asly,
cost_asly ,units_asregly,retail_asregly,units_asmkdly,retail_asmkdly,units_as_pln,retail_as_pln
from act_sls
join dimension w on w.externalkey = 'W'||substr(WEEK,3,2)||'_'||substr(WEEK,5,2)
join a_0 on ( w.externalkey between startweek and endweek)
join dimension strdim on strdim.externalkey = (case when length(storenum) <= 4 then RPAD('STR-', 8 - length(storenum), '0') else 'STR-' END) || storenum
join store_info_0 str on store = strdim.uic
join dimension gadim on gadim.externalkey = decode(store_type, 'RETAIL', 'GA-01', 'ECOM', 'GA-02', '')
where trendweeks < 6)t1
join(select distinct asp, product, ga, color, sstyl_shade, pmm_styleid from aplc_1 aplc
join apc_1 apc using (asp,product,color)
where activeitem = 1 and ga!=0 and color != 0)t2
on (t1.asp = t2.asp and
t1.pmm_styleid = t2.pmm_styleid
and (case when length(t1.colorcode) <= 4 then RPAD('SHD-', 8 - length(t1.colorcode), '0') else 'SHD-' END) || t1.colorcode = t2.sstyl_shade
and t1.ga = t2.ga))src
on (trg.asp = src.asp and trg.pmm_styleid = src.pmm_styleid and trg.colorcode = src.colorcode and trg.ga = src.ga)
when matched THEN
update SET
when matched THEN
update SET
trg.UNITS_ASLY = src.UNITS_ASLY,
trg.RETAIL_ASLY = src.RETAIL_ASLY,
trg.COST_ASLY = src.COST_ASLY,
trg.UNITS_ASREGLY = src.UNITS_ASREGLY,
trg.RETAIL_ASREGLY = src.RETAIL_ASREGLY,
trg.UNITS_ASMKDLY = src.UNITS_ASMKDLY,
trg.RETAIL_ASMKDLY = src.RETAIL_ASMKDLY,
trg.UNITS_AS_PLN = src.UNITS_AS_PLN,
trg.RETAIL_AS_PLN = src.RETAIL_AS_PLN
when not matched then insert
(trg.asp,trg.ga, trg.pmm_styleid, trg.colorcode,trg.sizecode,trg.storenum,trg.week,trg.UNITS_ASLY,trg.RETAIL_ASLY ,trg.COST_ASLY , trg.UNITS_ASREGLY ,trg.RETAIL_ASREGLY ,
trg.UNITS_ASMKDLY ,trg.RETAIL_ASMKDLY ,trg.UNITS_AS_PLN ,trg.RETAIL_AS_PLN )
values
(src.asp,src.ga, src.pmm_styleid, src.colorcode,src.sizecode,src.storenum,src.week,src.UNITS_ASLY,src.RETAIL_ASLY,src.COST_ASLY,src.UNITS_ASREGLY,
src.RETAIL_ASREGLY, src.UNITS_ASMKDLY, src.RETAIL_ASMKDLY, src.UNITS_AS_PLN, src.RETAIL_AS_PLN);
The format for a merge statement is:
merge into <target_table> tgt
using <table_name or subquery> src
on (<join conditions between the target and source datasets>)
when matched then
update set ...
when not matched then
insert (...)
values (...);
Quite apart from the fact that your source subquery is incorrect (there are errors around where the t1 and t2 are; too many brackets, inappropriately trying to alias something etc), whilst you have join conditions inside your subquery, you're completely missing the ON clause for the merge itself.
You need to define the join conditions that match the data returned by your source subquery to your target table.
Now the error is : src.ga - Invalid Identifier
Although I have ga table in Trg table and src table .
merge into act_sls_0 trg using( select * from
(select a_0.asp, gadim.uic as ga, pmm_styleid, week, colorcode , sizecode, storenum, units_asly,retail_asly,
cost_asly ,units_asregly,retail_asregly,units_asmkdly,retail_asmkdly,units_as_pln,retail_as_pln
from act_sls
join dimension w on w.externalkey = 'W'||substr(WEEK,3,2)||'_'||substr(WEEK,5,2)
join a_0 on ( w.externalkey between startweek and endweek)
join dimension strdim on strdim.externalkey = (case when length(storenum) <= 4 then RPAD('STR-', 8 - length(storenum), '0') else 'STR-' END) || storenum
join store_info_0 str on store = strdim.uic
join dimension gadim on gadim.externalkey = decode(store_type, 'RETAIL', 'GA-01', 'ECOM', 'GA-02', '')
where trendweeks < 6)t1
join(select distinct asp, product, ga, color, sstyl_shade, pmm_styleid from aplc_1 aplc
join apc_1 apc using (asp,product,color)
where activeitem = 1 and ga!=0 and color != 0)t2
on (t1.asp = t2.asp and
t1.pmm_styleid = t2.pmm_styleid
and (case when length(t1.colorcode) <= 4 then RPAD('SHD-', 8 - length(t1.colorcode), '0') else 'SHD-' END) || t1.colorcode = t2.sstyl_shade
and t1.ga = t2.ga))src
on (trg.asp = src.asp and trg.pmm_styleid = src.pmm_styleid and trg.colorcode = src.colorcode and trg.ga = src.ga)
when matched THEN
update SET
trg.UNITS_ASLY = src.UNITS_ASLY,
trg.RETAIL_ASLY = src.RETAIL_ASLY,
trg.COST_ASLY = src.COST_ASLY,
trg.UNITS_ASREGLY = src.UNITS_ASREGLY,
trg.RETAIL_ASREGLY = src.RETAIL_ASREGLY,
trg.UNITS_ASMKDLY = src.UNITS_ASMKDLY,
trg.RETAIL_ASMKDLY = src.RETAIL_ASMKDLY,
trg.UNITS_AS_PLN = src.UNITS_AS_PLN,
trg.RETAIL_AS_PLN = src.RETAIL_AS_PLN
when not matched then insert
(trg.asp,trg.ga, trg.pmm_styleid, trg.colorcode,trg.sizecode,trg.storenum,trg.week,trg.UNITS_ASLY,trg.RETAIL_ASLY ,trg.COST_ASLY ,trg.UNITS_ASREGLY ,trg.RETAIL_ASREGLY ,
trg.UNITS_ASMKDLY ,trg.RETAIL_ASMKDLY ,trg.UNITS_AS_PLN ,trg.RETAIL_AS_PLN )
values
(src.asp,src.ga, src.pmm_styleid, src.colorcode,src.sizecode,src.storenum,src.week,src.UNITS_ASLY,src.RETAIL_ASLY,src.COST_ASLY,src.UNITS_ASREGLY,
src.RETAIL_ASREGLY, src.UNITS_ASMKDLY, src.RETAIL_ASMKDLY, src.UNITS_AS_PLN, src.RETAIL_AS_PLN);
commit;