I try to make a query which can INSERT data quickly, before I execute query with INSERT statement I build a query which contains SELECT SUM CASE and INNER JOIN.
And my code contains error. Here's my code :
SELECT pkg_guru.id_pkg ,
pkg_guru.id_guru ,
guru.nama_guru ,
guru.mapel_diampu ,
pkg_guru.id_penilai ,
penilai.nama_penilai ,
pkg_guru.tahun ,
pkg_guru.sem ,
pkg_guru.kompetensi
SUM(CASE WHEN pkg_guru.kompetensi = "1" THEN pkg_guru.jawaban
ELSE 0
END) AS nilaikp1 ,
SUM(CASE WHEN pkg_guru.kompetensi = "2" THEN pkg_guru.jawaban
ELSE 0
END) AS nilaikp2 ,
SUM(CASE WHEN pkg_guru.kompetensi = "3" THEN pkg_guru.jawaban
ELSE 0
END) AS nilaikp3 ,
SUM(CASE WHEN pkg_guru.kompetensi = "4" THEN pkg_guru.jawaban
ELSE 0
END) AS nilaikp4 ,
SUM(pkg_guru.jawaban) AS total_skor
FROM pkg_guru
INNER JOIN guru ON pkg_guru.id_guru = guru.id_guru
INNER JOIN penilai ON pkg_guru.id_penilai = penilai.id_penilai
GROUP BY pkg_guru.id_pkg ,
pkg_guru.id_guru ,
guru.nama_guru ,
guru.mapel_diampu ,
pkg_guru.id_penilai ,
penilai.nama_penilai
Can you tell me what's wrong in this query code?
There's a comma missing after pg.kompetensi and you haven't included all of the required columns in your GROUP BY:
SELECT pg.id_pkg ,
pg.id_guru ,
g.nama_guru ,
g.mapel_diampu ,
pg.id_penilai ,
p.nama_penilai ,
pg.tahun ,
pg.sem ,
pg.kompetensi ,
SUM(CASE WHEN pg.kompetensi = "1" THEN pg.jawaban
ELSE 0
END) AS nilaikp1 ,
SUM(CASE WHEN pg.kompetensi = "2" THEN pg.jawaban
ELSE 0
END) AS nilaikp2 ,
SUM(CASE WHEN pg.kompetensi = "3" THEN pg.jawaban
ELSE 0
END) AS nilaikp3 ,
SUM(CASE WHEN pg.kompetensi = "4" THEN pg.jawaban
ELSE 0
END) AS nilaikp4 ,
SUM(pg.jawaban) AS total_skor
FROM pkg_guru pg
INNER JOIN guru g ON pg.id_guru = g.id_guru
INNER JOIN penilai p ON pg.id_penilai = p.id_penilai
GROUP BY pg.id_pkg ,
pg.id_guru ,
g.nama_guru ,
g.mapel_diampu ,
pg.id_penilai ,
p.nama_penilai ,
pg.tahun ,
pg.sem ,
pg.kompetensi
You missed comma after pkg_guru.kompetensi at the third line. And pkg_guru.tahun,pkg_guru.sem,pkg_guru.kompetensi in GROUP BY section.
Related
With this example iformation table:
How can i output this information?
I'm trying this query,
but it's just returning me the total number of 'PART' rows for each 'NAMES'.
SELECT
NAMES
, SUM(PART = "F001") AS SUM_F001
, SUM(PART = "F002") AS SUM_F002
, SUM(PART = "F003") AS SUM_F003
FROM
MY_TABLE
GROUP BY NAMES ASC
You are pretty close with your current query.
But you need to use the query below to correctly pivot.
SELECT
NAMES
, MAX(CASE WHEN PART = 'F001' THEN QTY ELSE 0 END) AS F001
, MAX(CASE WHEN PART = 'F002' THEN QTY ELSE 0 END) AS F002
, MAX(CASE WHEN PART = 'F003' THEN QTY ELSE 0 END) AS F003
, SUM(QTY) AS alias
FROM
FROM
MY_TABLE
GROUP BY
NAMES # Don't use ASC OR DESC on GROUP BY because it's deprecated
ORDER BY
NAMES ASC
U can use the query as follows
SELECT NAMES , SUM(CASE WHEN PART = 'F001' THEN 1 ELSE 0 END) AS F001 , SUM(CASE WHEN PART = 'F002' THEN 1 ELSE 0 END) AS F002 , SUM(CASE WHEN PART = 'F003' THEN 1 ELSE 0 END) AS F003 , SUM(QTY) AS alias FROM FROM MY_TABLE GROUP BY NAMES ORDER BY NAMES ASC
I have a query below that should be totaling up numbers by CSR agent using their extension. Currently it's returning one line/record for one agent and her extension but it's showing the correct totals for all 15 agents on that one record.
However, what I want is for it to list each agent and their extension with their own respective totals for the day. I'm grouping by extension but it doesn't seem to fix the issue.
Is there something in my query that would stick out as a reason for it not breaking my totals up per extension/agent?
SELECT firstn
, lastn
, extension
, Recieved
, RecievedKnown
, Outbound
, outboundKnown
, Missed
, MissedKnown
, duration
, HOLDTIMESECS
FROM (
SELECT firstn
, lastn
, c.extension
, sum(CASE WHEN LEGTYPE1 = 2 AND ANSWERED = 1 THEN 1 ELSE 0 END) AS Recieved
, sum(case when LEGTYPE1 = 2 and answered = 1 and CALLINGPARTYNO = k.phone_number then 1 ELSE 0 end) as RecievedKnown
, sum(CASE WHEN ANSWERED = 1 AND LEGTYPE1 = 1 then 1 ELSE 0 end) AS Outbound
, sum(case when LEGTYPE1 = 1 and FINALLYCALLEDPARTYNO = k.phone_number then 1 ELSE 0 end) as outboundKnown
, sum(case when Answered = 0 then 1 ELSE 0 end) as Missed
, sum(case when ANSWERED = 0 and CALLINGPARTYNO = k.phone_number then 1 ELSE 0 end) as MissedKnown
, sum(b.duration) as duration
, sum(a.holdtimesecs) as holdtimesecs
FROM ambition.session a
INNER JOIN ambition.callsummary b ON a.NOTABLECALLID = b.NOTABLECALLID
right join jackson_id.users c on a.callingpartyno = c.extension or a.finallycalledpartyno = c.extension
LEFT JOIN ambition.known_numbers k ON a.callingpartyno = k.phone_number
WHERE a.ts >= curdate()
and(a.CALLINGPARTYNO in (select extension from ambition.ambition_users) OR a.finallycalledpartyno IN (select extension from ambition.ambition_users))
) x
group by extension;
Your GROUP BY clause is required inside the subquery. Also I suspect you can avoid the right join by using FROM jackson_id.users c. Also you are usingca left join to ambition.known_numbers k but many of the case expressions rely on a non-null value from that table. Either the join should be an inner join or you need to cater for NULLs from that table in those case expressions.
SELECT
firstn
, lastn
, extension
, Recieved
, RecievedKnown
, Outbound
, outboundKnown
, Missed
, MissedKnown
, duration
, HOLDTIMESECS
FROM (
SELECT
firstn
, lastn
, c.extension
, sum(CASE WHEN LEGTYPE1 = 2 AND ANSWERED = 1 THEN 1 ELSE 0 END) AS Recieved
, sum(case when LEGTYPE1 = 2 and answered = 1 and CALLINGPARTYNO = k.phone_number then 1 ELSE 0 end) as RecievedKnown
, sum(CASE WHEN ANSWERED = 1 AND LEGTYPE1 = 1 then 1 ELSE 0 end) AS Outbound
, sum(case when LEGTYPE1 = 1 and FINALLYCALLEDPARTYNO = k.phone_number then 1 ELSE 0 end) as outboundKnown
, sum(case when Answered = 0 then 1 ELSE 0 end) as Missed
, sum(case when ANSWERED = 0 and CALLINGPARTYNO = k.phone_number then 1 ELSE 0 end) as MissedKnown
, sum(b.duration) as duration
, sum(a.holdtimesecs) as holdtimesecs
FROM jackson_id.users c
INNER JOIN ambition.session a on c.extension = a.callingpartyno or c.extension = a.finallycalledpartyno
INNER JOIN ambition.callsummary b ON a.NOTABLECALLID = b.NOTABLECALLID
LEFT JOIN ambition.known_numbers k ON a.callingpartyno = k.phone_number
WHERE a.ts >= curdate()
AND(a.CALLINGPARTYNO in (select extension from ambition.ambition_users)
OR a.finallycalledpartyno IN (select extension from ambition.ambition_users)
)
GROUP BY
firstn
, lastn
, c.extension
) x
;
Personally I have never been keen on table aliases that rely on sequence (a,b,c ...) as that sequence may not remain steady. Instead, I much prefer first-letter-of-each-word where this is possible. users = u, callsummary = cs, sessions = s, known_numbers = kn etc.
Currently, my final working transform in MySQL is working as needed. See SQL Fiddle with query below:
SELECT idt.fldDRCClientID
, idt.fldLastName
, COALESCE(grp.fldCreditorName1, '') as fldCreditorName1
, COALESCE(grp.fldDebtAccountNumber1, '') as fldDebtAccountNumber1
, COALESCE(grp.fldEnrolledDebt1, '') as fldEnrolledDebt1
, COALESCE(grp.fldCreditorName2, '') as fldCreditorName2
, COALESCE(grp.fldDebtAccountNumber2, '') as fldDebtAccountNumber2
, COALESCE(grp.fldEnrolledDebt2, '') as fldEnrolledDebt2
, COALESCE(grp.fldCreditorName3, '') as fldCreditorName3
, COALESCE(grp.fldDebtAccountNumber3, '') as fldDebtAccountNumber3
, COALESCE(grp.fldEnrolledDebt3, '') as fldEnrolledDebt3
, COALESCE(grp.fldCreditorName4, '') as fldCreditorName4
, COALESCE(grp.fldDebtAccountNumber4, '') as fldDebtAccountNumber4
, COALESCE(grp.fldEnrolledDebt4, '') as fldEnrolledDebt4
, COALESCE(grp.fldCreditorName5, '') as fldCreditorName5
, COALESCE(grp.fldDebtAccountNumber5, '') as fldDebtAccountNumber5
, COALESCE(grp.fldEnrolledDebt5, '') as fldEnrolledDebt5
, COALESCE(grp.fldCreditorName6, '') as fldCreditorName6
, COALESCE(grp.fldDebtAccountNumber6, '') as fldDebtAccountNumber6
, COALESCE(grp.fldEnrolledDebt6, '') as fldEnrolledDebt6
FROM tblClients idt
LEFT JOIN (
SELECT d.IndividualNumber as IndividualNumber
, MAX(CASE WHEN row = 1 THEN d.fldCreditorName END) AS fldCreditorName1
, MAX(CASE WHEN row = 1 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber1
, MAX(CASE WHEN row = 1 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt1
, MAX(CASE WHEN row = 2 THEN d.fldCreditorName END) AS fldCreditorName2
, MAX(CASE WHEN row = 2 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber2
, MAX(CASE WHEN row = 2 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt2
, MAX(CASE WHEN row = 3 THEN d.fldCreditorName END) AS fldCreditorName3
, MAX(CASE WHEN row = 3 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber3
, MAX(CASE WHEN row = 3 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt3
, MAX(CASE WHEN row = 4 THEN d.fldCreditorName END) AS fldCreditorName4
, MAX(CASE WHEN row = 4 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber4
, MAX(CASE WHEN row = 4 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt4
, MAX(CASE WHEN row = 5 THEN d.fldCreditorName END) AS fldCreditorName5
, MAX(CASE WHEN row = 5 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber5
, MAX(CASE WHEN row = 5 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt5
, MAX(CASE WHEN row = 6 THEN d.fldCreditorName END) AS fldCreditorName6
, MAX(CASE WHEN row = 6 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber6
, MAX(CASE WHEN row = 6 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt6
FROM
(
SELECT #row := CASE WHEN tblClients_fldDRCClientID = #id
THEN #row + 1 ELSE 1 END as row
, #id := tblClients_fldDRCClientID as IndividualNumber
, inf.fldCreditorName
, inf.fldDebtAccountNumber
, inf.fldEnrolledDebt
FROM (SELECT #row := 0, #id := 0) v
, tblDebtAccountNumber as inf
ORDER BY inf.tblClients_fldDRCClientID
) d
GROUP BY d.IndividualNumber
) grp
ON grp.IndividualNumber = idt.fldDRCClientID
;
However, I want to take this one step further. I need to include/join two additional tables (T3 and T4) to the mix. These two tables are both foreign key tables to the tblClients where:
idt.fldDRCClientID is the PK of tblClients;
tblClients_fldDRCClientID is foreign key for both T3 and T4.
I have tried some additional inner joins and sub selects but they both fail. Looking for the proper places to add the syntax for T3 and T4 to get this functioning. Any ideas or suggestions would be appreciated.
I have two tables in a one to many relationship. In table 2, I have three columns I am looking to transform into row data. Why? these will be used to merge with another process (as a data source) for producing documents. Please see the attachment for the breakdown and the related output.
Here is the first successful query having the accurate information needed.
SELECT
tblClients.fldDRCClientID,
fldLastName,
e1.fldCreditorName,
e1.fldDebtAccountNumber,
e1.fldEnrolledDebt
From tblClients
Left Join tblDebtAccountNumber as e1 ON e1.tblClients_fldDRCClientID = tblClients.fldDRCClientID;
First query results:
(Posted on behalf of the question author to move it from the comments).
Here is my query:
SELECT idt.fldDRCClientID
, idt.fldLastName
, COALESCE(grp.fldCreditorName1, '') as fldCreditorName1
, COALESCE(grp.fldDebtAccountNumber1, '') as fldDebtAccountNumber1
, COALESCE(grp.fldEnrolledDebt1, '') as fldEnrolledDebt1
, COALESCE(grp.fldCreditorName2, '') as fldCreditorName2
, COALESCE(grp.fldDebtAccountNumber2, '') as fldDebtAccountNumber2
, COALESCE(grp.fldEnrolledDebt2, '') as fldEnrolledDebt2
, COALESCE(grp.fldCreditorName3, '') as fldCreditorName3
, COALESCE(grp.fldDebtAccountNumber3, '') as fldDebtAccountNumber3
, COALESCE(grp.fldEnrolledDebt3, '') as fldEnrolledDebt3
, COALESCE(grp.fldCreditorName4, '') as fldCreditorName4
, COALESCE(grp.fldDebtAccountNumber4, '') as fldDebtAccountNumber4
, COALESCE(grp.fldEnrolledDebt4, '') as fldEnrolledDebt4
, COALESCE(grp.fldCreditorName5, '') as fldCreditorName5
, COALESCE(grp.fldDebtAccountNumber5, '') as fldDebtAccountNumber5
, COALESCE(grp.fldEnrolledDebt5, '') as fldEnrolledDebt5
, COALESCE(grp.fldCreditorName6, '') as fldCreditorName6
, COALESCE(grp.fldDebtAccountNumber6, '') as fldDebtAccountNumber6
, COALESCE(grp.fldEnrolledDebt6, '') as fldEnrolledDebt6
FROM tblClients idt
LEFT JOIN (
SELECT d.IndividualNumber as IndividualNumber
, MAX(CASE WHEN row = 1 THEN d.fldCreditorName END) AS fldCreditorName1
, MAX(CASE WHEN row = 1 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber1
, MAX(CASE WHEN row = 1 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt1
, MAX(CASE WHEN row = 2 THEN d.fldCreditorName END) AS fldCreditorName2
, MAX(CASE WHEN row = 2 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber2
, MAX(CASE WHEN row = 2 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt2
, MAX(CASE WHEN row = 3 THEN d.fldCreditorName END) AS fldCreditorName3
, MAX(CASE WHEN row = 3 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber3
, MAX(CASE WHEN row = 3 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt3
, MAX(CASE WHEN row = 4 THEN d.fldCreditorName END) AS fldCreditorName4
, MAX(CASE WHEN row = 4 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber4
, MAX(CASE WHEN row = 4 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt4
, MAX(CASE WHEN row = 5 THEN d.fldCreditorName END) AS fldCreditorName5
, MAX(CASE WHEN row = 5 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber5
, MAX(CASE WHEN row = 5 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt5
, MAX(CASE WHEN row = 6 THEN d.fldCreditorName END) AS fldCreditorName6
, MAX(CASE WHEN row = 6 THEN d.fldDebtAccountNumber END) AS fldDebtAccountNumber6
, MAX(CASE WHEN row = 6 THEN d.fldEnrolledDebt END) AS fldEnrolledDebt6
FROM
(
SELECT #row := CASE WHEN tblClients_fldDRCClientID = #id
THEN #row + 1 ELSE 1 END as row
, #id := tblClients_fldDRCClientID as IndividualNumber
, inf.fldCreditorName
, inf.fldDebtAccountNumber
, inf.fldEnrolledDebt
FROM (SELECT #row := 0, #id := 0) v
, tblDebtAccountNumber as inf
ORDER BY inf.tblClients_fldDRCClientID
) d
GROUP BY d.IndividualNumber
) grp
ON grp.IndividualNumber = idt.fldDRCClientID
;
SQL Fiddle
I retrieve two sum of value:
SUM (CASE WHEN CAUSALI.AVAILABLECAUSA_1 LIKE ('%CAUSE-1%') THEN (mtscrap) ELSE 0 END ) as Cause1
and
SUM (CASE WHEN CAUSALI.AVAILABLECAUSA_1 LIKE ('%CAUSE-2%') THEN (mtscrap) ELSE 0 END ) as Cause2
I would like to set another SUM statement without %CAUSE-*, and that have WHERE clause independent from the principal WHERE. I had innested this subquery:
(CASE WHEN day BETWEEN '2014-01-09' AND '2014-06-13' THEN SUM(MTSCRAP) ELSE 0 END) AS XXXXXX
but I have wrong data. My global query is:
SELECT
SezioneID
, Desc_Prod
, sample.products.VETTURA AS VetturaID
, truncate((SUM(mtscrap_1) / SUM(MtProdotti_1)) * 100, 2) AS Scrap_1
, truncate((SUM(mtscrap_2) / SUM(MtProdotti_2)) * 100, 2) AS Scrap_2
, mtscrap_1
, MtProdotti_1
, mtscrap_2
, MtProdotti_2
FROM flB.flB_prod AS PROD
JOIN SAMPLE.PRODUCTS
ON (sample.products.SKU = PROD.SEZIONEID)
AND (sample.products.LINEA = 'FLB')
JOIN (
SELECT
IDSEZIONE
, IDTURNO
, ID_PROG
, SUM(CASE
WHEN AVAILABLECAUSA_1 LIKE ('%CHANGE-1%') THEN mtscrap ELSE 0
END) AS mtscrap_1
, SUM(CASE
WHEN AVAILABLECAUSA_1 LIKE ('%CHANGE-1%') THEN MtProdotti ELSE 0
END) AS MtProdotti_1
, SUM(CASE
WHEN AVAILABLECAUSA_1 LIKE ('%CHANGE-2%') THEN mtscrap ELSE 0
END) AS mtscrap_2
, SUM(CASE
WHEN AVAILABLECAUSA_1 LIKE ('%CHANGE-2%') THEN MtProdotti ELSE 0
END) AS MtProdotti_2
, MtProdotti
FROM FLB.flB_causali
WHERE DATASTARTPRG BETWEEN '2014-06-09' AND '2014-06-13'
GROUP BY
IDSEZIONE
IDTURNO
, ID_PROG
) AS CAUSALI
ON (PROD.SEZIONEID = CAUSALI.IDSEZIONE)
AND PROD.TURNO = CAUSALI.IDTURNO
AND PROD.ID_PROG = CAUSALI.ID_PROG
WHERE giorno BETWEEN '2014-06-09' AND '2014-06-13'
GROUP BY
SezioneID
I need this view:
I have done my best to put a table or alias beside EVERY field reference. At this point I really do not know what else I can do for you. I don't think any more words will help.
these 2 simple items will help:
1. sample data
2. expected result
Because you did not use table aliases on all fields in the very original query the following is a complete guess, but using the presence of DISTINCT in that original query was a clue for "too many rows" that indicated the need for grouping prior to the overall query. So, here's my first guess:
SELECT
PROD.SezioneID
, PROD.Desc_Prod
, sample.products.VETTURA AS VetturaID
, truncate((SUM(CAUSALI.mtscrap_1) / SUM(CAUSALI.MtProdotti_1)) * 100, 2) AS Scrap_1
, truncate((SUM(CAUSALI.mtscrap_2) / SUM(CAUSALI.MtProdotti_2)) * 100, 2) AS Scrap_2
, CAUSALI.mtscrap_1
, CAUSALI.MtProdotti_1
, CAUSALI.mtscrap_2
, CAUSALI.MtProdotti_2
FROM flB.flB_prod AS PROD
JOIN SAMPLE.PRODUCTS
ON (sample.products.SKU = PROD.SEZIONEID)
AND (sample.products.LINEA = 'FLB')
JOIN (
SELECT
flB_causali.IDSEZIONE
, flB_causali.IDTURNO
, flB_causali.ID_PROG
, SUM(CASE
WHEN flB_causali.AVAILABLECAUSA_1 LIKE ('%CHANGE-1%') THEN flB_causali.mtscrap ELSE 0
END) AS mtscrap_1
, SUM(CASE
WHEN flB_causali.AVAILABLECAUSA_1 LIKE ('%CHANGE-1%') THEN flB_causali.MtProdotti ELSE 0
END) AS MtProdotti_1
, SUM(CASE
WHEN flB_causali.AVAILABLECAUSA_1 LIKE ('%CHANGE-2%') THEN flB_causali.mtscrap ELSE 0
END) AS mtscrap_2
, SUM(CASE
WHEN flB_causali.AVAILABLECAUSA_1 LIKE ('%CHANGE-2%') THEN flB_causali.MtProdotti ELSE 0
END) AS MtProdotti_2
, flB_causali.MtProdotti
FROM FLB.flB_causali
WHERE flB_causali.DATASTARTPRG BETWEEN '2014-06-09' AND '2014-06-13'
GROUP BY
flB_causali.IDSEZIONE
flB_causali.IDTURNO
, flB_causali.ID_PROG
) AS CAUSALI
ON (PROD.SEZIONEID = CAUSALI.IDSEZIONE)
AND PROD.TURNO = CAUSALI.IDTURNO
AND PROD.ID_PROG = CAUSALI.ID_PROG
WHERE PROD.giorno BETWEEN '2014-06-09' AND '2014-06-13'
GROUP BY
PROD.SezioneID
;
Are you looking for this expression?
SUM(CASE WHEN day BETWEEN '2014-01-09' AND '2014-06-13' THEN MTSCRAP ELSE 0 END) AS XXXXXX
The CASE goes inside the SUM() for conditional aggregation.