Reputation: 44
I'm using mysql.
I have a messages table with userid, message_id, opened (true or false), timestamp.
I want all users who did not open a message in there last 5 messages received
This is what I have right now:
SELECT mnc.userid
FROM `messages` mnc
WHERE (select count(*) from messagesas m where m.userid = mnc.userid
and m.message_sendtime_timestamp >= mnc.message_sendtime_timestamp
and m.opened = 'FALSE') >= 6
But, this give me users with more than 6 unopened messages not necessarily consecutive
Here are sample data
CREATE TABLE messages
(`user_id` int, `timestamp` datetime, `opened` varchar(5))
;
INSERT INTO messages
(`user_id`, `timestamp`, `opened`)
VALUES
(1, '2016-01-01 00:00:00', 'false'),
(1, '2016-02-01 00:00:00', 'false'),
(1, '2016-03-01 00:00:00', 'false'),
(1, '2016-04-01 00:00:00', 'false'),
(1, '2016-05-01 00:00:00', 'false'),
(1, '2016-06-01 00:00:00', 'false'),
(2, '2016-01-01 00:00:00', 'false'),
(2, '2016-02-01 00:00:00', 'false'),
(2, '2016-03-01 00:00:00', 'false'),
(3, '2015-01-01 00:00:00', 'false'),
(3, '2016-01-01 00:00:00', 'false'),
(3, '2016-02-01 00:00:00', 'false'),
(3, '2016-03-01 00:00:00', 'false'),
(3, '2016-04-01 00:00:00', 'false'),
(3, '2016-05-01 00:00:00', 'true'),
(3, '2016-06-01 00:00:00', 'false'),
(4, '2015-01-01 00:00:00', 'true'),
(4, '2015-02-01 00:00:00', 'true'),
(4, '2016-01-01 00:00:00', 'false'),
(4, '2016-02-01 00:00:00', 'false'),
(4, '2016-03-01 00:00:00', 'false'),
(4, '2016-04-01 00:00:00', 'false'),
(4, '2016-05-01 00:00:00', 'false'),
(4, '2016-06-01 00:00:00', 'false')
Expected result :
userid
1
4
Upvotes: 0
Views: 117
Reputation: 2775
SELECT
MAX(CASE WHEN (t.ct = 5 and t.op=5) THEN t.user_id END) AS userid
FROM
(
SELECT
user_id,
opened,timestamp ,
@opened := opened,
IF ( (@opened = 'false' && @prev = user_id) ,@o := @o + 1,@o := 1),
IF(@opened='true',@o:=0,@o) op,
IF (@prev = user_id ,@c := @c + 1,(@c := 1)) ct,
@prev := user_id
FROM (SELECT @prev := 0 ,@c := 1,@opened :='0',@o := 0) var,
messages
order by user_id asc,timestamp desc
) t
GROUP BY t.user_id
check herehttp://sqlfiddle.com/#!9/8447a3/1
Upvotes: 0
Reputation: 48197
to answer this question
I want all users who did not open a message in last 5 messages received ?
First you need create a row_id
for each user_id
SELECT @rowid := IF(@prev_value = user_id, @rowid + 1, 1) as row_id,
m.*
@prev_value := user_id
FROM messages m,
(SELECT @row_num := 1) x,
(SELECT @prev_value := '') y
ORDER BY `timestamp` DESC
Then check how many open message you have on that subquery
SELECT user_id, COUNT(*), SUM(opened = 'false')
FROM (
SELECT @rowid := IF(@prev_value = user_id, @rowid + 1, 1) as row_id,
m.*,
@prev_value := user_id
FROM messages m,
(SELECT @row_num := 1) x,
(SELECT @prev_value := '') y
ORDER BY user_id, `timestamp` DESC
) T
WHERE row_id <= 5 -- only check last 5 or less messages
GROUP BY user_id
HAVING COUNT(*) = SUM(opened = 'false') -- Check all messages are NOT opened
Upvotes: 0