0

I have the following mySQL Query which returns a list of ID's. I want to delete the rows with each ID of the list from the table "serverking_user"

SELECT serverking_user.id FROM (serverking_user
INNER JOIN serverking_logins
ON serverking_user.id=serverking_logins.uid)
WHERE serverking_logins.time < 3600
GROUP BY serverking_user.id
HAVING COUNT(serverking_logins.login) = 1

One possibility would be to loop through each ID by using "in". But since "in" is deactivated on my Sql Server I need to solve this with a "join".

Any ideas ?

3 Answers 3

2

It has been a while since I have done MySQL development, but if I remember correctly this should work for you:

DELETE su
FROM serverking_user su
INNER JOIN serverking_logins sl
ON su.id=sl.uid
WHERE sl.time < 3600
GROUP BY su.id
HAVING COUNT(sl.login) = 1

In general, if you want to delete records from a single table in a JOIN, you just specify that table (or its alias) after DELETE

UPDATED QUERY
It seems that MySQL isn't fond of deleting where a grouped query is involved, so another possibility is to use an anti-join. However, I'm sure that the performance characteristics of this query will be suboptimal. It may be better to use two separate queries instead. Nonetheless, here is a solution using anti-joins:

DELETE su
FROM serverking_user su
INNER JOIN serverking_logins sl
ON su.id=sl.uid
LEFT JOIN serverking_logins antisl
ON sl.uid = antisl.uid
AND sl.id <> antisl.id
WHERE sl.time < 3600
AND antisl.id IS NULL
Sign up to request clarification or add additional context in comments.

4 Comments

#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 'GROUP BY su.id HAVING COUNT(sl.login) = 1' at line 6
You could use an anti-join but I'm not sure if that will perform better than two separate queries as described in @Luaan's answer below.
and how would that look like ?
@user1474444 I have updated my answer with another query. My assumption is that serverking_logins has a primary key field called id.
1

Perhaps you could store the results of the select inside of a table variable and then join that?

declare @Ids table
(
  Id int
);

insert into @Ids (Id)
SELECT serverking_user.id FROM (serverking_user
INNER JOIN serverking_logins
ON serverking_user.id=serverking_logins.uid)
WHERE serverking_logins.time < 3600
GROUP BY serverking_user.id
HAVING COUNT(serverking_logins.login) = 1;

delete yt from YourTable yt
inner join @Ids Ids on Ids.Id = yt.id;

Note that the consistency of this depends on your transaction configuration, since you're doing two separate queries here.

3 Comments

@user1474444 Oh, I've only noticed now you're asking for a MySQL solution. Is this really so slow?
I don't know how slow that will be, but it looks a bit complicated for me since i am not really good in sql...
@user1474444 Yeah, that's often a very bad metric. Try running it (without the delete, if you need so) and measure. Also, I'm not sure if MySql has table variables, you might have to use a temporary table, but it shouldn't be a big dfference.
1
DELETE FROM serverking_user
WHERE EXISTS
(SELECT *
FROM (serverking_user
INNER JOIN serverking_logins
ON serverking_user.id=serverking_logins.uid)
WHERE serverking_logins.time < 3600
GROUP BY serverking_user.id
HAVING COUNT(serverking_logins.login) = 1) a

4 Comments

#1093 - You can't specify target table 'serverking_logins' for update in FROM clause
Sorry, I had a typo that didn't match your table names. Try again, double checking that the table names are accurate.
thx, but still: #1093 - You can't specify target table 'serverking_user' for update in FROM clause
@user1474444, This is my fault. The query provided will work in SQL Server, but not MySQL. MySQL does not allow updates or deletes on the same table as what's in the WHERE clause. Please use Luaan's solution for a MySQL workaround.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.