MySQL Group Concat Function By Will Mayall 19-December-2014 Contents Overview ................................................................................................................................................... 1 Understanding Your Data ............................................................................................................... 1 Making Sense of Your Data ........................................................................................................... 3 Summary ...................................................................................................................................................... 4 Overview This document is intended to explain how and when to use the distinct and group concat functions in MySQL. Understanding Your Data There are cases when your data has “one to many” relationships, but you only want to see distinct values of “one to many.” Getting “one to many” values returned can be accomplished using the distinct and group concat functions. Below is the table definition: mysql> desc ec3; +------------------+----------------------+------+-----+---------------------+-------+ | Field | Type | Null | Key | Default | Extra | +------------------+----------------------+------+-----+---------------------+-------+ | pers_id | int(10) unsigned | NO | PRI | 0 | | | co_id | int(10) unsigned | NO | MUL | NULL | | | email | varchar(100) | NO | MUL | NULL | | 1 | domain | varchar(100) | YES | MUL | NULL | | | checked | datetime | YES | MUL | NULL | | | ok_syntax | tinyint(1) | YES | | NULL | | | ok_domain | tinyint(1) | YES | | NULL | | | code | varchar(45) | YES | MUL | NULL | | | message | varchar(100) | YES | MUL | NULL | | | seconds | smallint(3) unsigned | YES | | | | working | datetime | YES | MUL | 0000-00-00 00:00:00 | | | reason_code | varchar(45) | YES | MUL | NULL | | | reason_message | varchar(100) | YES | MUL | NULL | | | certified | datetime | YES | | NULL | | | hygiene | varchar(100) | YES | | NULL | | | netprotect | tinyint(1) | YES | | 0 | | | netprotectby | varchar(100) | YES | | NULL | | | domainknowledge | text | YES | | NULL | | | addressknowledge | text | YES | | NULL | | | version | varchar(25) | NO | | EmailVerify5 | | | tag | varchar(64) | NO | | | | | primary | tinyint(1) | YES | | 1 | | | retry | int(11) | YES | MUL | 0 | | | NULL +------------------+----------------------+------+-----+---------------------+-------+ 23 rows in set (0.00 sec) mysql> To get an idea of the problem, executing the below query will turn one co_id and many messages with the same value. mysql> select co_id,message from ec3 where co_id = 5; +-------+------------------+ | co_id | message | +-------+------------------+ | 5 | Domain Confirmed | 2 | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | | 5 | Domain Confirmed | +-------+------------------+ 11 rows in set (0.00 sec) mysql> Making Sense of Your Data The query in the last example makes no sense, and furthermore, what if there are more than one message? In comes the functions distinct and group concat! mysql> select co_id,group_concat(distinct ec3.message) from ec3 where message is not NULL group by co_id having count(distinct message) > 1 order by co_id limit 10; +-------+----------------------------------------------------------------------+ | co_id | group_concat(distinct ec3.message) | +-------+----------------------------------------------------------------------+ | 2 | Domain Confirmed,Email Valid | | 13 | Email Valid,Domain Confirmed | | 15 | Domain Confirmed,Internal Error | | 18 | Domain Confirmed,Domain Confirmed. Potentially Dangerous | | 19 | Domain Confirmed,Domain Confirmed. Potentially Dangerous,Email Valid | | 20 | Email Valid,Domain Confirmed,Email Valid Potentially Dangerous | | 21 | Domain Confirmed,Domain Confirmed. Potentially Dangerous | | 27 | Email Valid,Email Not Valid | 3 | 28 | Domain Confirmed. Potentially Dangerous,Domain Confirmed | | 35 | Domain Confirmed,Not Verified, Dangerous Domain | +-------+----------------------------------------------------------------------+ 10 rows in set (0.68 sec) mysql> Summary Sometimes the data in your database makes no sense. Using functions to filter the data helps you understand trends and can make valuable use of the data. 4