MySQL: How can where clause be invalid for delete statement but work fine for select statement?

MySQL: How can where clause be invalid for delete statement but work fine for select statement?



I am trying to run a delete statement in mysql - I get an error. To test I tried running it as "select *" instead of "delete". Nothing else changed, and it runs fine. Any idea why?



here is the full delete statement


DELETE
from timeclock_raw tr
where tr.rectype = 'active'
and tr.recdate > '2018-08-17'
and tr.seconds < (select max(tr1.seconds) as secs
from timeclock_raw tr1
where tr1.env = tr.env and tr1.intid = tr.intid and tr1.studycode = tr.studycode and tr1.recdate = tr.recdate)
and tr.seconds > (select min(tr2.seconds) as secs
from timeclock_raw tr2
where tr2.env = tr.env and tr2.intid = tr.intid and tr2.studycode = tr.studycode and tr2.recdate = tr.recdate);



I get this error


[2018-08-19 20:46:51] [42000][1064] You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'tr
[2018-08-19 20:46:51] where tr.rectype = 'active'
[2018-08-19 20:46:51] and tr.recdate > '2018-08-17'
[2018-08-19 20:46:51] and tr.' at line 2



but this runs fine...


select *
from timeclock_raw tr
where tr.rectype = 'active'
and tr.recdate > '2018-08-17'
and tr.seconds < (select max(tr1.seconds) as secs
from timeclock_raw tr1
where tr1.env = tr.env and tr1.intid = tr.intid and tr1.studycode = tr.studycode and tr1.recdate = tr.recdate)
and tr.seconds > (select min(tr2.seconds) as secs
from timeclock_raw tr2
where tr2.env = tr.env and tr2.intid = tr.intid and tr2.studycode = tr.studycode and tr2.recdate = tr.recdate);



Any ideas?



EDIT: based on first response I tried this but got another error... any ideas?


sql> delete tr
from timeclock_raw tr
where tr.rectype = 'active'
and datediff(now(),tr.recdate) < 3
and tr.seconds < (select max(tr1.seconds) as secs
from timeclock_raw tr1
where tr1.env = tr.env and tr1.intid = tr.intid and tr1.studycode = tr.studycode and tr1.recdate = tr.recdate)
and tr.seconds > (select min(tr2.seconds) as secs
from timeclock_raw tr2
where tr2.env = tr.env and tr2.intid = tr.intid and tr2.studycode = tr.studycode and tr2.recdate = tr.recdate)
[2018-08-20 01:07:24] [HY000][1093] You can't specify target table 'tr' for update in FROM clause
[2018-08-20 01:07:24] [HY000][1093] You can't specify target table 'tr' for update in FROM clause





I thought we don't need from in the delete statement, it's just DELETE table_name WHERE..., no?
– John Law
Aug 20 at 0:52



from


delete


DELETE table_name WHERE...





docs says 'If you declare an alias for a table, you must use the alias when referring to the table' see, then only put the alias before from or dont use it
– kip
Aug 20 at 0:53



from





@JohnLaw From MySQL Documentation, the FROM is still required: dev.mysql.com/doc/refman/8.0/en/delete.html
– John Stark
Aug 20 at 0:55


FROM





@JohnStark ah ok, new syntax for me to learn then. Thanks. :-)
– John Law
Aug 20 at 0:56




2 Answers
2



MySQL does not allow you to use the table being deleted (or updated) in the rest of the query. The normal solution is to use joins:


join


delete tr
from timeclock_raw tr join
(select tr1.env, tr1.intid, tr1.studycode, tr1.recdate, min(tr1.seconds) as minsecs, max(tr1.seconds) as maxsecs
from timeclock_raw tr1
group by tr1.env, tr1.intid, tr1.studycode, tr1.recdate
) x
on tr1.env = tr.env and
tr1.intid = tr.intid and
tr1.studycode = tr.studycode and
tr1.recdate = tr.recdate
where tr.rectype = 'active' and
tr.recdate > '2018-08-17' and
tr.seconds < x.maxsecs and
tr.seconds > x.minsecs;





Thanks! This is perfect - one small tweak. in the following section all the "tr1." should be "x.". Other than that, this seems to be doing exactly what I want. Thanks so much! on tr1.env = tr.env and tr1.intid = tr.intid and tr1.studycode = tr.studycode and tr1.recdate = tr.recdate
– Ben
Aug 20 at 5:23




The error is not complaining about the WHERE clause, it is complaining about the use of a table alias that was not previously declared before the FROM. You need to rewrite the query as


WHERE


FROM


DELETE tr FROM timeclock_raw tr WHERE ...



Check out the very end of the manual page.





Thanks!! I am used to DB2 syntax... I need to get more familiar with MySQL. You are a life saver!
– Ben
Aug 20 at 2:23





@Nick . . . Although that is one problem with the query, I would not consider that to be the main issue.
– Gordon Linoff
Aug 20 at 2:29





@GordonLinoff Indeed, I was just answering OPs question as posted.
– Nick
Aug 20 at 2:47





@nick . . . This is only one problem with the query. I don't object to your answer (which correctly identifies one issue), just the upvotes.
– Gordon Linoff
Aug 20 at 2:48





@GordonLinoff Fair enough but I can't do anything about them short of deleting the answer.
– Nick
Aug 20 at 2:49






By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Popular posts from this blog

ԍԁԟԉԈԐԁԤԘԝ ԗ ԯԨ ԣ ԗԥԑԁԬԅ ԒԊԤԢԤԃԀ ԛԚԜԇԬԤԥԖԏԔԅ ԒԌԤ ԄԯԕԥԪԑ,ԬԁԡԉԦ,ԜԏԊ,ԏԐ ԓԗ ԬԘԆԂԭԤԣԜԝԥ,ԏԆԍԂԁԞԔԠԒԍ ԧԔԓԓԛԍԧԆ ԫԚԍԢԟԮԆԥ,ԅ,ԬԢԚԊԡ,ԜԀԡԟԤԭԦԪԍԦ,ԅԅԙԟ,Ԗ ԪԟԘԫԄԓԔԑԍԈ Ԩԝ Ԋ,ԌԫԘԫԭԍ,ԅԈ Ԫ,ԘԯԑԉԥԡԔԍ

How to change the default border color of fbox? [duplicate]

Henj