查询父og子记录并返回父记录

时间:2016-01-26 08:58:47

标签: mysql

我正在开发一个产品数据库(PDB),既可用于网上商店,也可用作ERP系统中的文章。大多数数据直接来自我们的供应商作为CSV文件,我们添加了覆盖某些字段的选项,这导致了一个表结构,我无法弄清楚如何有效地查询。

本质上,表结构由两个表组成,article和extended_article,其中最后一个表包含一个名为parent_article_code的字段,用于将女性文章组合成男性用于显示目的。并非所有文章都包含extended_articles,并且并非所有包含extended_articles的文章都在parent_article_code中有值。

我需要执行一个查询,返回所有带匹配的文章,但只显示父文章,其中父文章或子文章与查询匹配。这是一个非常简单的表格版本,我还将添加一个查询来显示数据的实际结构。

文章表:

    -------------------------------------------------------------------------
    |  id  |  code    |  name          |  description                       |
    |  1   |  029320  |  T-shirt       |  Nice t-shirt with awsome logo     |
    |  2   |  029321  |  T-shirt Lady  |  Nice t-shirt with awsome logo     |
    |  3   |  029322  |  Sweatshirt    |  Nice sweatshirt with awsome logo  |
    |  4   |  029323  |  Pants         |  Nice pants with awsome logo       |
    -------------------------------------------------------------------------

extended_article表:

    -------------------------------------------------------------------------------------------------
    |  id  |  article_code  |  parent_article_code  |  name_override       |  description_override  |
    |  1   |  029320        |                       |  T-shirt with print  |                        |
    |  2   |  029321        |  029320               |                      |                        |
    |  3   |  029323        |                       |  Awsome pants!       |                        |
    -------------------------------------------------------------------------------------------------

示例SQL查询(返回所有匹配的记录 - 不仅是子项):

SELECT article.*, 
    article.id, 
    extended_article.parent_article_code, 
    extended_article.impressions, 
    extended_article.is_base_assortment, 
    extended_article.is_visible, 
    extended_article.name_override, 
    extended_article.description_override, 
    extended_article.additional_description, 
    extended_article.preferred_image_file_name, 
    supplier.name AS supplier_name, 
    brand.name AS brand_name
FROM article 
LEFT OUTER JOIN article_sort_order 
ON article_sort_order.article_code = article.code AND category_id IS NULL 
LEFT OUTER JOIN extended_article 
ON extended_article.article_code = article.code 
LEFT JOIN supplier 
ON supplier.id = article.supplier_id 
LEFT JOIN brand 
ON brand.id = article.brand_id  
WHERE (extended_article.is_base_assortment = 1) 
AND  (article.is_expired = 0) 
AND (extended_article.is_visible = 1) 
AND ((EXISTS 
(
    SELECT 1 
    FROM article_color_groups 
    WHERE article_color_groups.article_code = article.code 
    AND article_color_groups.color_group_id = 4
)
))

所以我的问题是: 如何有效地查询此表结构并具有仅包含父文章的结果集?

编辑:

我有一个想法是将查询部分移动到两个子查询中,只选择ID并使用UNION生成一个列表以从中选择适当的字段。这似乎有效,但可能不是最有效的解决方案?

SELECT article.*, article.id, extended_article.parent_article_code, extended_article.impressions, extended_article.is_base_assortment, extended_article.is_visible, extended_article.name_override, extended_article.description_override, extended_article.additional_description, extended_article.preferred_image_file_name, supplier.name AS supplier_name, brand.name AS brand_name
FROM article
LEFT OUTER JOIN article_sort_order ON article_sort_order.article_code = article.code AND category_id IS NULL
LEFT OUTER JOIN extended_article ON extended_article.article_code = article.code
LEFT JOIN supplier ON supplier.id = article.supplier_id
LEFT JOIN brand ON brand.id = article.brand_id
WHERE article.code IN (
                SELECT article.code
                FROM article
                LEFT OUTER JOIN article_sort_order ON article_sort_order.article_code = article.code AND category_id IS NULL
                LEFT OUTER JOIN extended_article ON extended_article.article_code = article.code
                LEFT JOIN supplier ON supplier.id = article.supplier_id
                LEFT JOIN brand ON brand.id = article.brand_id
                WHERE   (NULLIF(extended_article.parent_article_code, '') IS NULL)
                        AND
                        (extended_article.is_base_assortment = 1)
                        AND
                        (article.is_expired = 0)
                        AND
                        (extended_article.is_visible = 1)
                        AND
                        ((EXISTS (SELECT 1 FROM article_color_groups WHERE article_color_groups.article_code = article.code AND article_color_groups.color_group_id = 11)))

                UNION

                SELECT extended_article.parent_article_code
                FROM article
                LEFT OUTER JOIN article_sort_order ON article_sort_order.article_code = article.code AND category_id IS NULL
                LEFT OUTER JOIN extended_article ON extended_article.article_code = article.code
                LEFT JOIN supplier ON supplier.id = article.supplier_id
                LEFT JOIN brand ON brand.id = article.brand_id
                WHERE   (NULLIF(extended_article.parent_article_code, '') IS NOT NULL)
                        AND
                        (article.is_expired = 0)
                        AND
                        ((EXISTS (SELECT 1 FROM article_color_groups WHERE article_color_groups.article_code = article.code AND article_color_groups.color_group_id = 11)))
            )
ORDER BY -article_sort_order.sort_order DESC;

0 个答案:

没有答案