MySQL - 将行转为逗号分隔值

MySQL - Pivot rows to comma separated values

我有 3 张桌子。

1. user
2. user_role
3. user_role_mapping

样本记录,

用户

+--------+----------+---------------+
| userid | username | email         |
+--------+----------+---------------+
|      1 | user1    |user1@test.com |
|      2 | user2    |user2@test.com |
+--------+----------+---------------+

user_role

+--------+----------+
| roleid | rolename |
+--------+----------+
|      1 | user     |
|      2 | manager  |
|      3 | director |
|      4 | admin    |
+--------+----------+

User_role_mapping

+--------+------+
| roleid |userid|
+--------+------+
|      1 | 1    |
|      2 | 1    |
|      3 | 1    |
+--------+------+

查询

select u.userid, u.username, u.email,
  count(case when ur.rolename = 'user' THEN 1 END) user,
  count(case when ur.rolename = 'manager' THEN 1 END) manager,
  count(case when ur.rolename = 'director' THEN 1 END) director,
  count(case when ur.rolename = 'admin' THEN 1 END) admin
from user_role ur
left join userrole_mapping urm
  on ur.roleid = urm.roleid
left join user u
  on urm.userid = u.userid
group by u.userid, u.username, u.email

结果:-

+--------+----------+---------------+------|---------|----------|-------|
| userid | username | email         | user | manager | director | admin |
+--------+----------+---------------+------------------------------------
|      1 | user1    |user1@test.com | 1    |   1     |  1       |  1    |
+--------+----------+---------------+------------------------------------

在这里,我正在对查询中的角色进行硬编码,将来可以添加新角色,我不想更改代码。有没有更好的方法?我对结果中的角色使用逗号分隔的结果很好。

对于逗号分隔,您可以使用 group_concat:

select u.user_id, u.user_name, u.email,
       Group_concat(ur.role_name) roles
from user u
left join user_role_mapping urm
  on urm.user_id = u.user_id
left join user_role ur
  on ur.role_id = urm.role_id
where u.user_id = ?
group by u.user_id;

另一种可能更好的方法 w/o 硬编码是分别查询角色:

select u.user_id, u.user_name, u.email, ur.role_name
from user u
left join user_role_mapping urm
  on urm.user_id = u.user_id
left join user_role ur
  on ur.role_id = urm.role_id
where u.user_id = ?;