Reputation: 3548
I want to get the sum of several entities from several tables using a query. Specifically, I want the devices and messages count of a user. In addition, the timestamp of the last received message for that user. I have 3 tables:
Users
id name (other fields)
1 Mike ...
2 John ...
3 Yay ...
4 Jim ...
Devices
id user_id (other fields)
1 1 ...
2 1 ...
3 1 ...
4 2 ...
Messages
id device_id message time (other fields)
1 1 Hi 2019-04-07 12:06:44 ...
2 1 Hey 2019-04-06 12:06:44 ...
3 2 Sup 2019-04-05 12:06:44 ...
4 3 Ok 2019-04-04 12:06:44 ...
5 4 Yay 2019-04-08 12:06:44 ...
... and, for example, for user Mike
I want to end up with:
Result
nDevices nMessages time
3 4 2019-04-07 12:06:44
Any ideas? Thanks in advance.
Upvotes: 0
Views: 63
Reputation: 133360
You could try using a join between user and device and a inner join with the subquery for message and device
select a.name, a.id, count(d.user_id), t.nDevice, t.max_time
from Users a
inner join device d on a.id = d.user_id
inner join (
select m.device_id, count(m.device_id) nDevice, max(m.time) max_time
from Messages m
group by m.device_id
) t on t.device_id = d.id
group by a.name, a.id
Upvotes: 0
Reputation: 164089
Join the 3 tables and count distinct values of the columns:
select
count(distinct d.id) devicescounter,
count(distinct m.id) messagescounter,
max(m.time) lastmessagetime
from users u
left join devices d on u.id = d.user_id
left join nessages m on m.device_id = d.id
where u.name = 'Mike'
If you want the results for all users:
select
u.id, u.name,
count(distinct d.id) devicescounter,
count(distinct m.id) messagescounter,
max(m.time) lastmessagetime
from users u
left join devices d on u.id = d.user_id
left join nessages m on m.device_id = d.id
group by u.id, u.name
Upvotes: 1
Reputation: 1116
The easiest way to do this would be to get the number of messages and most recent message time for each device in a subquery.
SELECT u.id,
COUNT(d.id) AS num_devices,
SUM(messages) AS num_messages,
MAX(most_recent) AS most_recent_message
FROM users u
JOIN devices d ON d.user_id = u.id
JOIN (SELECT device_id,
COUNT() AS messages,
MAX(TIME) AS most_recent_message
FROM messages
GROUP BY device_id) m ON m.device_id = d.id
GROUP BY u.id
Upvotes: 1