Domanda

Say I have the following defined tables:

Table `content`:
===============
id unsigned int(11)
title varchar(500)

Table `satellite`:
===============
id unsigned int(11)
label varchar(250)

Table `content_satellite`:
===============
content_id unsigned int(11)
satellite_id unsigned int(11)

If I wanted to get a list of content rows that contain a GROUP_CONCAT()'ted list of associated satellites, FILTERED on a particular satellite type, what would the query be?

Using the following query:

SELECT 
c.title,
GROUP_CONCAT(s.id) as satellite_ids
FROM content c
LEFT JOIN content_satellite cs ON cs.content_id = c.id
LEFT JOIN satellite s ON cs.satellite_id = s.id
WHERE satellite = 2
GROUP BY c.id;

The resulting rows would have satellite_ids containing ONLY a single value "2" whether or not a particular content row is associated to multiple satellite types...

How can I query these tables to retrieve a column that contains ALL satellite ids associated with each content rows that come back while filtering on a particular satellite type?

EDIT - MySQL 5.5 is the Database type (didn't realize that mattered for a common basic SQL query such as this)

EDIT2 - Left the GROUP by off my sql query

È stato utile?

Soluzione

Your query concatenates all IDs and gives you a random title. And of course when you only select satellite ID #2 then you only see #2.

First of all, you don't want to aggregate all records. You want groups. You want one record per content, so group by content. As there may be duplicate titles, better group by content id.

SELECT 
  c.id,
  c.title,
  GROUP_CONCAT(distinct cs.satellite_id order by cs.satellite_id) as satellite_ids
FROM content c
LEFT JOIN content_satellite cs ON cs.content_id = c.id
GROUP BY c.id;

EDIT: To get those contents that have satellite #2 in their list use HAVING with an appropriate case expression:

SELECT 
  c.id,
  c.title,
  GROUP_CONCAT(distinct cs.satellite_id order by cs.satellite_id) as satellite_ids
FROM content c
LEFT JOIN content_satellite cs ON cs.content_id = c.id
GROUP BY c.id
HAVING MAX( CASE WHEN cs.satellite_id = 2 THEN 1 ELSE 0 END ) = 1;
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top