patternsqlMinor
Problem translating MySQL to PostgreSQL
Viewed 0 times
postgresqlproblemmysqltranslating
Problem
We're using Trac for issue tracking. I migrated it from MySQL to PostgreSQL, but some of the ticket queries no longer work.
In the below, all I did this far is replace
I don't know what the error means. The query worked just fine in MySQL, and I'm not sure, after looking at pages discussing differences between it and PostgreSQL, what the problem is (I also don't know what to replace the SEC_TO_TIME line with, but removing that line doesn't fix the error).
Edit: I tried changing the
Also, I don't know what to replace
Edit 2: What I'm trying to end up with, which was the case with MySQL:
Edit 3: Thanks to a_horse_w
In the below, all I did this far is replace
IFNULL() with COALESCE() and UNIX_TIMESTAMP() with TO_TIMESTAMP()::TIMESTAMPI don't know what the error means. The query worked just fine in MySQL, and I'm not sure, after looking at pages discussing differences between it and PostgreSQL, what the problem is (I also don't know what to replace the SEC_TO_TIME line with, but removing that line doesn't fix the error).
SELECT IFNULL(CONCAT('Component ', t.component), 'Total for all Components') AS __group__,
(CASE
WHEN t.id > 0 THEN (CASE t.status WHEN 'closed' THEN 'color: #777; background: #ddd; border-color: #ccc;' END)
ELSE 'font-weight: bold'
END) AS __style__,
t.id AS ticket,
IF(t.id > 0, t.summary, 'Total') AS summary,
SEC_TO_TIME(SUM(IF(w.endtime, w.endtime, TO_TIMESTAMP(NOW())::TIMESTAMP) - w.starttime)) AS total
FROM ticket t
INNER JOIN work_log w
WHERE t.id = w.ticket
GROUP BY t.component, t.id, t.summary, t.status
WITH ROLLUP HAVING IFNULL(id, -1) = -1 OR (t.summary IS NOT NULL AND t.status IS NOT NULL);
ERROR: syntax error at or near "WHERE"
LINE 11: WHERE t.id = w.ticketEdit: I tried changing the
WHERE to ON, and that seemed to fix that error; however, I don't know if this is the correct solution. Also, now I get an error with the "WITH ROLLUP HAVING" part. What's the way to do it in PostgreSQL?Also, I don't know what to replace
SEC_TO_TIME with above, or the SUM / IF combo (as IF() is MySQL only--if I swap to CASE, do I need to test separately for 0 and null?). Using TO_CHAR as per http://www.verious.com/qa/sec-to-time-function-in-postgre-sql/ doesn't work because the minutes are always zero with the code given there (i.e. 90 seconds ends up as 00:00:30...)Edit 2: What I'm trying to end up with, which was the case with MySQL:
Edit 3: Thanks to a_horse_w
Solution
Something like this:
The
I'm not entirely sure what the rollup does, but something along the lines:
might get you started.
SELECT coalesce(CONCAT('Component ', t.component), 'Total for all Components') AS __group__,
CASE
WHEN t.id > 0 THEN CASE t.status WHEN 'closed' THEN 'color: #777; background: #ddd; border-color: #ccc;' END
ELSE 'font-weight: bold'
END AS __style__,
t.id AS ticket,
case when t.id > 0 then t.summary else 'Total' end AS summary,
SUM( coalesce(w.endtime, current_timestamp) - w.starttime) AS total
FROM ticket t
INNER JOIN work_log w ON t.id = w.ticket
GROUP BY t.component, t.id, t.summary, t.statusThe
sum() will sum up the difference in milliseconds between endtime and starttime not sure what the intention behind that is.I'm not entirely sure what the rollup does, but something along the lines:
with base_data as (
... the above query goes here ...
)
select __group__, ticket, __style__, summary, total
from base_data
union all
select null, null, null, null, sum(total)
from base_data
group by __group__, ticket, __style__, summarymight get you started.
Code Snippets
SELECT coalesce(CONCAT('Component ', t.component), 'Total for all Components') AS __group__,
CASE
WHEN t.id > 0 THEN CASE t.status WHEN 'closed' THEN 'color: #777; background: #ddd; border-color: #ccc;' END
ELSE 'font-weight: bold'
END AS __style__,
t.id AS ticket,
case when t.id > 0 then t.summary else 'Total' end AS summary,
SUM( coalesce(w.endtime, current_timestamp) - w.starttime) AS total
FROM ticket t
INNER JOIN work_log w ON t.id = w.ticket
GROUP BY t.component, t.id, t.summary, t.statuswith base_data as (
... the above query goes here ...
)
select __group__, ticket, __style__, summary, total
from base_data
union all
select null, null, null, null, sum(total)
from base_data
group by __group__, ticket, __style__, summaryContext
StackExchange Database Administrators Q#62496, answer score: 4
Revisions (0)
No revisions yet.