Merge Source Table Into Target Table using subjoins - sql

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;

Related

How to use exists for a complete list of a product?

This is the query to find out if a particular car has W1, W2, WA, WH conditions. How can I modify my query so that I can get a list of all the cars as yes or no for these conditions?
NOTE: Here, I have put v.[carnumber] = 't8302' but I need a complete list.
SELECT
CASE
WHEN EXISTS (
SELECT co.[alias]
FROM [MTI_TAXI].[vehicle] v
LEFT JOIN [MTI_SYSTEM].[Conditions] co with (nolock) on v.DispatchSystemID = co.DispatchSystemID and (v.Conditions & co.conditionvalue > 0)
WHERE co.[alias] in ('W1', 'W2', 'WA', 'WH') and v.[DispatchSystemID] = 6 and v.[CarNumber] = 't8302')
THEN cast ('Yes' as varchar)
ELSE cast ('No' as varchar)
END AS [WATS]
OUTPUT - ( WATS - No )
But, here are all the cars but I am getting yes to WATS condition which is incorrect
enter image description here
Simply utilizing your provided filters and moving the EXISTS to be used in an OUTER APPLY statement:
SELECT
CASE
WHEN [find_wats].[Found] = 1
THEN 'Yes'
ELSE 'No'
END AS [WATS]
FROM
[MTI_TAXI].[vehicle] AS v
OUTER APPLY (SELECT TOP (1)
1 AS [Found]
FROM
[MTI_SYSTEM].[Conditions] AS co
WHERE
v.DispatchSystemID = co.DispatchSystemID
AND
(v.Conditions & co.conditionvalue > 0)
AND
co.[alias] IN ('W1', 'W2', 'WA', 'WH')
AND
v.[DispatchSystemID] = 6) AS [find_wats];
Using this set up, you can then use [find_wats].[Found] = 1 to determine that your record within the table [MTI_TAXI].[vehicle] found a match in [MTI_TAXI].[Conditions] (using your provided criteria) while still maintaining a single record in your final result set for each record originally in the table [MTI_TAXI].[vehicle].
Use count(*) to assert that there was exactly 1 row found by adding:
group by co.[alias]
having count(*) = 1
So the whole query becomes:
SELECT
CASE
WHEN EXISTS (
SELECT co.[alias]
FROM [MTI_TAXI].[vehicle] v
LEFT JOIN [MTI_SYSTEM].[Conditions] co with (nolock)
on v.DispatchSystemID = co.DispatchSystemID
and (v.Conditions & co.conditionvalue > 0)
WHERE co.[alias] in ('W1', 'W2', 'WA', 'WH')
and v.[DispatchSystemID] = 6
and v.[CarNumber] = 't8302'
group by co.[alias]
having count(*) = 1
) THEN cast ('Yes' as varchar)
ELSE cast ('No' as varchar)
end AS [WATS]

Pl sql get x character of a string in a query

SELECT MR.MUSTERI_ROL_AD AS ACENTE_AD , ////HERE\\\\
(SELECT mrrt.musteri_rol_ad
FROM calisan ct, musteri_rol mrrt, musteri mmt
where ct.bagli_rol_id = a.acente_id
AND ct.calisan_rol_id = mrrt.musteri_rol_id
AND mrrt.musteri_id = mmt.musteri_id
AND ct.teknik_personel='H'
AND ct.calisan_rol_id is not null
and rownum < 2)Bayi_Yetkili_Kisi,
( case when M.TCK_NO is null then M.VKN_NO
else null end)VKN_NO,
(Select (SELECT taa.adresi
FROM tobb_acente ta, tobb_acente_adres taa
WHERE ta.levhano = a.levha_no
AND ta.tobb_acente_sorgu_id = taa.tobb_acente_sorgu_id
AND rownum < 2)
FROM musteri_adres mat, musteri_rol mrt, musteri mt, adres ad
WHERE mrt.musteri_rol_id = a.acente_id
AND mt.musteri_id = mrt.musteri_id
AND mat.musteri_id(+) = mt.musteri_id
AND ad.adres_id(+) = mat.adres_id AND rownum < 2) adress,
(SELECT mi.aciklama
FROM musteri_iletisim mi, musteri_rol_iletisim mri
where mi.musteri_id = m.musteri_id
AND mi.iletisim_tip_kod =
pck_const_iletisim_tip.cep_telefon()
AND mri.musteri_rol_id = mr.musteri_rol_id
and mi.musteri_iletisim_id = mri.musteri_iletisim_id
and rownum < 2) as CEpTELEFON ////// HERE \\\\\
FROM MUSTERI_ROL MR, MUSTERI M, ACENTE A,SATIS_KANALI SK
WHERE MR.MUSTERI_ID = M.MUSTERI_ID
AND MR.MUSTERI_ROL_ID = A.ACENTE_ID
AND A.SATIS_KANALI_ID = SK.SATIS_KANALI_ID
AND MR.ROL_ID = 1
AND A.Uretim_Kaynagi = 'E'
AND A.UST_ACENTE_ID is null
AND MR.Ust_Musteri_Rol_Id is null
AND M.VKN_NO != 'x'
AND TO_CHAR(TRUNC(MR.Bitis_Tarih), 'DD/MM/YYYY') is null or MR.Bitis_Tarih = SYSDATE
Hi guys i need some help about split in Oracle's SQL i get ACENTE_AD x character and i wanna see only first 5 character. and i get CEpTELEFON like 012345678 and i wanna split first 3 character(012) in a column and last 6 character(345678) the in other column. thanks.
You can use substr() string manipulation function to split your phone value in the outer select statement by considering your original query as a subquery.
SELECT t.Bayi_Yetkili_Kisi, t.Vkn_No, t.Adres,
substr(CepTelefonu,1,3) as AlanKodu, substr(CepTelefonu,-6) as CepTelefonu
FROM
(
SELECT MR.MUSTERI_ROL_AD AS ACENTE_AD,
(SELECT mrrt.musteri_rol_ad
FROM musteri_rol mrrt
JOIN calisan ct ON ct.calisan_rol_id = mrrt.musteri_rol_id
JOIN musteri mmt ON mmt.musteri_id = mrrt.musteri_id
WHERE ct.bagli_rol_id = a.acente_id
AND ct.teknik_personel = 'H'
AND ct.calisan_rol_id is not null
AND rownum < 2) as Bayi_Yetkili_Kisi,
(CASE
WHEN M.TCK_NO is null THEN
M.VKN_NO
ELSE
null
END) as Vkn_No,
(SELECT (SELECT taa.adresi
FROM tobb_acente ta
JOIN tobb_acente_adres taa
ON taa.tobb_acente_sorgu_id = ta.tobb_acente_sorgu_id
WHERE ta.levhano = a.levha_no
AND rownum < 2)
FROM musteri mt
JOIN musteri_rol mrt ON mrt.musteri_id = mt.musteri_id
LEFT JOIN musteri_adres mat ON mat.musteri_id = mt.musteri_id
LEFT JOIN adres ad ON ad.adres_id = mat.adres_id
WHERE mrt.musteri_rol_id = a.acente_id
AND rownum < 2) as Adres,
(SELECT mi.aciklama
FROM musteri_iletisim mi
JOIN musteri_rol_iletisim mri ON mri.musteri_iletisim_id = mi.musteri_iletisim_id
WHERE mi.musteri_id = m.musteri_id
AND mi.iletisim_tip_kod = pck_const_iletisim_tip.cep_telefon() -- I think the right hand side implies a stored function, doesn't it?
AND mri.musteri_rol_id = mr.musteri_rol_id
AND rownum < 2) as CepTelefonu
FROM MUSTERI_ROL MR
JOIN MUSTERI M ON M.MUSTERI_ID = MR.MUSTERI_ID
JOIN ACENTE A ON A.ACENTE_ID = MR.MUSTERI_ROL_ID
JOIN SATIS_KANALI SK ON SK.SATIS_KANALI_ID = A.SATIS_KANALI_ID
WHERE MR.ROL_ID = 1
AND A.Uretim_Kaynagi = 'E'
AND A.UST_ACENTE_ID is null
AND MR.Ust_Musteri_Rol_Id is null
AND M.VKN_NO != 'x'
AND to_char(trunc(MR.Bitis_Tarih), 'dd/mm/yyyy') is null
OR MR.Bitis_Tarih = sysdate
) t;
Btw, Consider using ANSI-92 style SQL rather than former ANSI-89 with comma-seperated tables written like the above one. It's easier to write, understand and maintain.

Update a join tables using SQL

This is my select query
select s.enabled,
s.totalpoints,
transaction_diff_dates
from loyalty_scheme l
join subscribe_merchant s on (l.scheme_id = s.schemerefid)
join transaction t on (s.unipoint_customer_ref_id = t.unipoint_customer_ref_id)
where (s.transaction_diff_dates = to_char(current_date, 'yyyy-MM-dd'))
and (s.merchant_ref_id = 11)
and (s.schemerefid = (select scheme_id
from loyalty_scheme
where (minimum_purchase_amount = (select min(minimum_purchase_amount)
from loyalty_scheme
where merchant_id = 11))
group by scheme_id))
group by s.unipoint_customer_ref_id,
s.enabled,
s.totalpoints,
s.transaction_diff_dates
This query returns two rows.
I need to update this enabled filed = 'false' , and totalPoint = 0 filed , instead of selecting
So I tried to write an update query
UPDATE subscribe_merchant
SET enabled = 'true'
FROM loyalty_scheme L
JOIN subscribe_merchant S ON (L.scheme_id = S.schemerefid)
JOIN transaction T ON (S.unipoint_customer_ref_id = T.unipoint_customer_ref_id)
WHERE (s.transaction_diff_dates = to_char(CURRENT_DATE, 'yyyy-MM-dd'))
AND (s.merchant_ref_id = 11)
AND (s.schemerefid = (SELECT scheme_id
FROM loyalty_scheme
WHERE (minimum_purchase_amount = (SELECT MIN(minimum_purchase_amount)
FROM loyalty_scheme
WHERE merchant_id = 11))
GROUP BY scheme_id))
GROUP BY
s.unipoint_customer_ref_id, s.enabled,
s.totalpoints, s.transaction_diff_dates
but this update query dose not work.
Please help me to write the update query

SQL Load Fact with Merge Statement Slow

I'm loading a fact table using MERGE and it's taking 44 minutes for 1 million records. Is there a way I can improve this?
My query:
MERGE INTO dbo.FactProjMarketCode AS target
USING (
SELECT
SourceSystem = 'ORACLE_ERP',
ProjMarketCodeSourceId = jmc.XT_JOB_MARKETING_CODE_ID,
p.ProjectId,
MarketCodeId = ISNULL(mc.MarketingCodeId,-1),
Weight = 0.01 * ISNULL(jmc.WEIGHT,100),
WasMissing = CASE WHEN jmc.WEIGHT IS NULL THEN 1 ELSE 0 END,
jmc.LAST_UPDATE_DATE
FROM
dimProject p
LEFT JOIN stage.XT_JOB_MARKETING_CODE jmc
ON p.ProjectSourceId = jmc.XT_PROJECT_ID
LEFT JOIN DimMarketingCode mc
ON jmc.MARKETING_CODE = mc.MarketingCode -- should create column MarketingCodeSourceId
AND mc.SourceSystem = 'ORACLE_ERP'
WHERE
p.SourceSystem = 'ORACLE_ERP'
) AS source
ON target.SourceSystem = source.SourceSystem
AND target.ProjMarketCodeSourceId = source.ProjMarketCodeSourceId
WHEN MATCHED AND source.LAST_UPDATE_DATE > target.LAST_UPDATE_DATE
THEN UPDATE SET
target.ProjectId = source.ProjectId,
target.MarketCodeId = source.MarketCodeId,
target.Weight = source.WEIGHT,
target.WasMissing = source.WasMissing,
target.LAST_UPDATE_DATE = source.LAST_UPDATE_DATE
WHEN NOT MATCHED BY target
THEN INSERT (
SourceSystem,
ProjMarketCodeSourceId,
ProjectId,
MarketCodeId,
Weight,
WasMissing,
LAST_UPDATE_DATE
) VALUES (
source.SourceSystem,
source.ProjMarketCodeSourceId,
source.ProjectId,
source.MarketCodeId,
source.Weight,
source.WasMissing,
source.LAST_UPDATE_DATE
)
WHEN NOT MATCHED BY source
THEN DELETE;

multiple errors in using with function in select statement

I'm having some problems with my select statement. When I try to execute it, it gives 3 errors
Must specify table to select from
An object or column name is missing or empty for SELECT INFO statements. verify each column
has a name. For other statements, look for empty alias names. Aliases defined...
Column name or number of supplied values does not match table definition.
WITH A AS
(SELECT ROW_NUMBER() OVER (ORDER BY
CASE
WHEN #pOrderBy = 'SortByName' THEN colPortAgentVendorNameVarchar
WHEN #pOrderBy = 'SortByCOuntry' THEN colCountryNameVarchar
WHEN #pOrderBy = 'SortByCity' THEN colCityNameVarchar
END,
colPortAgentVendorNameVarchar
) xRow, A.*
FROM
(
SELECT DISTINCT
V.colPortAgentVendorIDInt,
colPortAgentVendorNameVarchar = RTRIM(LTRIM(V.colPortAgentVendorNameVarchar)),
C.colCountryNameVarchar,
Y.colCityNameVarchar,
V.colContactNoVarchar,
V.colFaxNoVarchar,
V.colEmailToVarchar,
V.colWebsiteVarchar,
BR.colBrandIdInt,
PR.colPriorityTinyint,
colBrandCodeVarchar = RTRIM(LTRIM(BR.colBrandCodeVarchar))
FROM dbo.TblVendorPortAgent V
LEFT JOIN TblCountry C ON C.colCountryIDInt = V.colCountryIDInt
LEFT JOIN TblCity Y ON Y.colCityIDInt = V.colCityIDInt
LEFT JOIN tblBrandAirportPortAgent PR ON PR.colPortAgentVendorIDInt = V.colPortAgentVendorIDInt
AND PR.colIsActiveBit = 1
LEFT JOIN TblBrand BR ON BR.colBrandIdInt = PR.colBrandIdInt
AND BR.colIsActiveBit = 1
WHERE V.colIsActiveBit = 1
AND V.colPortAgentVendorNameVarchar LIKE '%'+ #pPortAgentVendor +'%'
AND (PR.colBrandIdInt = #pBrandID OR #pBrandID = 0)
) A
)
INSERT INTO #tempPortAgent
SELECT A.*, IsWithContract = CASE WHEN colContractIdInt IS NULL THEN CAST(0 AS BIT) ELSE CAST(1 AS BIT) END FROM A LEFT JOIN TblContractPortAgent B ON A.colPortAgentVendorIDInt = B.colPortAgentVendorIDInt
AND B.colIsActiveBit = 1
;WITH QQ AS
(
SELECT ROW_NUMBER() OVER(PARTITION BY Q.colPortAgentVendorIDInt ORDER BY xRow,
ContractStatusOrder,
colDateCreatedDate DESC
)ContractRow,*
FROM
(
SELECT DISTINCT GG.*, B.colContractIdInt, B.colContractStatusVarchar, B.colDateCreatedDate ,
ContractStatusOrder = CASE WHEN B.colContractStatusVarchar = 'Approved' THEN 1 ELSE '2' END
FROM #tempPortAgent GG LEFT JOIN TblContractPortAgent B ON GG.colPortAgentVendorIDInt = B.colPortAgentVendorIDInt
AND B.colIsActiveBit = 1
) Q
)SELECT * INTO #tempPortAgentWithContract
SELECT * FROM #tempPortAgentWithContract
I don't really know where its showing, because the errors are saying that these are inside the select statements inside.
1- Use Select Into instead of Insert into select
SELECT A.*, IsWithContract = CASE WHEN colContractIdInt IS NULL THEN CAST(0 AS BIT) ELSE CAST(1 AS BIT) END
Into #tempPortAgent
FROM A
LEFT JOIN TblContractPortAgent B ON A.colPortAgentVendorIDInt = B.colPortAgentVendorIDInt
AND B.colIsActiveBit = 1
2- SELECT * INTO #tempPortAgentWithContract is incorrect syntax. you must use following format:
SELECT * INTO #tempPortAgentWithContract From QQ