Php 选择属于某个组的所有用户,复杂查询

Php 选择属于某个组的所有用户,复杂查询,php,mysql,join,group-concat,Php,Mysql,Join,Group Concat,我正在处理一个查询,这个查询目前运行得很好(我使用前端的输入生成WHERE子句),但我希望能够搜索另一个参数,这确实让我感到困惑 表组包含id、名称 Tablepersons是我要检索的人员所在的表 表group\u memberships是我的groupperson多对多关系表。列为参与者(person.id)和组(groups.id) 检索到的结果集的最后一列是组成员身份的串联,但其中“1、2、3”已通过JOIN替换为组的真实名称 今天的问题是: SELECT `persons`.`id

我正在处理一个查询,这个查询目前运行得很好(我使用前端的输入生成WHERE子句),但我希望能够搜索另一个参数,这确实让我感到困惑

  • 包含id、名称
  • Table
    persons
    是我要检索的人员所在的表
  • group\u memberships
    是我的groupperson多对多关系表。列为参与者(person.id)和组(groups.id)
  • 检索到的结果集的最后一列是组成员身份的串联,但其中“1、2、3”已通过JOIN替换为组的真实名称

    今天的问题是:

    SELECT
      `persons`.`id`,
      CONCAT_WS(\' \', `fname`, `lname`) AS `full_name`,
      `job_title`,
      `email`,
      `phone`,
      `participant_group_memberships`.`memberships`
    FROM
      `persons`
      LEFT JOIN (SELECT
                   `participant`, `name`,
                   GROUP_CONCAT(`groups`.`name` ORDER BY `groups`.`name`
                                SEPARATOR  \', \') AS `memberships`
                 FROM
                   `group_memberships` JOIN `groups`
                    ON (`groups`.`id` = `group_memberships`.`group`)
                 GROUP BY `participant`) AS `participant_group_memberships`
      ON (`participant_group_memberships`.`participant` = `persons`.`id`)
    WHERE TRUE . $where . '
    ORDER BY `full_name`
    
    如果我添加WHERE name='search\u query\u group',那么连接的列表只会显示我不想要的组。我仍然想显示此人所属的所有组

    我还希望通过1个查询来实现这一点,并尽可能避免在()中使用


    如您所见,最后一列(使用GROUP_CONCAT生成)将仅显示我搜索的组,而不是该人员所属的所有组。

    您可以在子查询的HAVING子句中使用SUM和CASE语句来包含搜索结果。您还需要将对子查询的联接更改为内部联接。这将返回某个组中的所有人员,并显示他们所属的所有组

    SELECT  `persons`.`id`,
            CONCAT_WS(\' \', `fname`, `lname`) AS `full_name`,
            `job_title`,
            `email`,
            `phone`,
            `participant_group_memberships`.`memberships`
    
    FROM    `persons` 
    
            JOIN `pers_department`
            ON (`pers_department`.`pers_rid` = `persons`.`id`)
    
            JOIN 
            (SELECT `participant`, `name`,
                    GROUP_CONCAT(`groups`.`name` ORDER BY `groups`.`name`
                                SEPARATOR  \', \') AS `memberships`
             FROM   `group_memberships` 
                    JOIN `groups` ON (`groups`.`id` = `group_memberships`.`group`)
             GROUP BY `participant`
             HAVING SUM(CASE WHEN name = 'search_query_group' THEN 1 ELSE 0 END) > 0
            ) AS `participant_group_memberships`
            ON (`participant_group_memberships`.`participant` = `persons`.`id`)
    
    WHERE TRUE . $where . '
    
    ORDER BY `full_name`
    

    谢谢,我试试看。这是一种常见的做法还是SUM/CASE只是一个肮脏的黑客行为?以前从未见过。在我的书中,这是一个巧妙的把戏。:)我不会称之为黑客。它工作得很好,我经常使用它。在很多情况下(比如这样),我相信这是最好的选择。好吧,我试过了,不幸的是没有什么不同。返回所有用户,但正确显示组成员身份。我还想知道这将如何影响我的$where变量?因为我把它放在ORDER BY之前,我不能在两个地方使用它们:)您是否将连接更改为内部连接?如果是这样,则应将记录限制为仅匹配。您可以同时具有WHERE和HAVING子句。不管怎样,一个在子查询中,一个在主查询中。你真是个天才!非常感谢你,这是我错过的。但我更喜欢加入,里面的关键词让我困惑。现在我可以有一个$where变量和一个$having变量。非常感谢。