Reputation: 437
I have a problem that seems similar to others posted before but the solutions to those don't really seem to work for me.
What I am trying to do is select rows from one database which relate to the particular user (found in another database) and then from a third database getting any attachments associated,so:
users
(id is all we take from this)membership
(staff_id and group_id are what I need form this)msg_group
(id, starts, expires and message are what im concerned with)msg_attach
(id, ident, type and file are what I need from here)SO. I have this query:
SELECT msg_group.message, msg_group.starts,
msg_group.expires,
GROUP_CONCAT(msg_attach.file SEPARATOR ',')
FROM `membership`
INNER JOIN `msg_group`
ON membership.group_id = msg_group.group_id
LEFT JOIN `msg_attach`
ON msg_group.id = msg_attach.ident AND msg_attach.type = "1"
WHERE membership.staff_id = "1"
AND msg_group.starts <= CURRENT_TIMESTAMP
AND msg_group.expires >= CURRENT_TIMESTAMP
ORDER BY msg_group.expires ASC LIMIT 0, 30
The problem with it is, there should be 5 rows being returned. One should, in the msg_attach.file columns have "file.jpg,file2.jpg". This is good, but then I should have 4 more rows under it with NULL in the msg_attach column.
To counter this I have tried using IFNULL(msg_attach.file, 'null') however all this returns is one row still but file.jpg, file2.jpg, null, null, null, null.
What I want is the row witch attachments to be file.jpg, file2.jpg and then 4 more rows will 'null' in that column.
I hope I have explained this well enough!#
Thanks for any assistance. Alex
edit: sample tables and data.
msg_group:
------------------------------------------------------------
| id | group_id | message | starts | expires |
| 1 | 1 | PIES | date 1 | date 2 |
| 2 | 1 | CAKES | date 1 | date 2 |
| 3 | 1 | BEERS | date 1 | date 2 |
| 4 | 1 | POMMEGRANITES | date 1 | date 2 |
------------------------------------------------------------
msg_attach:
---------------------------------
| id | type | ident| file |
| 1 | 1 | 3 | corona.jpg |
| 2 | 1 | 3 | peroni.png |
---------------------------------
So I would want my query to return:
------------------------------------------------------------
| message | starts | expires | file |
| PIES | date1 | date2 | null |
| CAKES | date1 | date2 | null |
| BEERS | date1 | date2 | corona.jpg,peroni.png |
| POMMEGRANITES | date1 | date2 | null |
------------------------------------------------------------
What i get is:
------------------------------------------------------------
| message | starts | expires | file |
| BEERS | date1 | date2 | corona.jpg,peroni.png |
------------------------------------------------------------
or with the use of ISNULL:
------------------------------------------------------------------------------
| message | starts | expires | file |
| BEERS | date1 | date2 | null, corona.jpg,peroni.png, null, null |
------------------------------------------------------------------------------
This is all omitting the membership and users stuff which I dont /think/ is relevant to the problem. Without GROUP_CONCAT (i.e. just msg_attach.file) I would get back 5 rows, just two for BEERS with the files listed individually.
Upvotes: 1
Views: 2240
Reputation: 263723
The simplified query should looked like this,
SELECT a.message, a.starts, a.expires,
GROUP_CONCAT(b.file) fileList
FROM msg_group a
LEFT JOIN msg_attach b
ON a.group_ID = b.type AND
a.id = b.ident
GROUP BY a.message, a.starts, a.expires
edited: by Bogomip as I dont know how to make a full comment to this:
Thanks, I have had to make a few changes to incorporate the users and stuff but this now works :)
SELECT msg_group.message, msg_group.starts, msg_group.expires, GROUP_CONCAT(msg_attach.file) attachments
FROM msg_group
INNER JOIN membership ON membership.group_id = msg_group.group_id
LEFT JOIN msg_attach ON msg_group.id = msg_attach.ident AND msg_attach.type = "1"
WHERE membership.staff_id = "1"
AND msg_group.starts <= CURRENT_TIMESTAMP
AND msg_group.expires >= CURRENT_TIMESTAMP
GROUP BY msg_group.expires, msg_group.starts, msg_group.message
ORDER BY msg_group.expires ASC LIMIT 0, 30
Upvotes: 1