2017-07-13 4 views
0

Ich arbeite durch den Export einiger Daten von einem lokalen WordPress (bbPress) installieren und doppelte Daten in meinen GROUP_CONCAT Spalten (die nicht in der Datenbank vorhanden ist).MySQL GROUP_CONCAT verhindern unnötige Duplikate

Hier ist die Abfrage:

SELECT 
    a.`ID`, a.`post_date`, a.`post_content`, a.`post_title`, 
    a.`post_status`, a.`post_name`, a.`post_type`, a.`post_parent`, 
    GROUP_CONCAT(d.`meta_key` SEPARATOR '{|}') AS `post_meta_keys`, 
    GROUP_CONCAT(d.`meta_value` SEPARATOR '{|}') AS `post_meta_values`, 
    b.`user_login`, b.`user_pass`, b.`user_nicename`, b.`user_email`, 
    b.`user_registered`, b.`display_name`, 
    GROUP_CONCAT(c.`meta_key` SEPARATOR '{|}') AS `user_meta_keys`, 
    GROUP_CONCAT(c.`meta_value` SEPARATOR '{|}') AS `user_meta_values` 
FROM 
    `wp_posts` a 
INNER JOIN 
    `wp_users` b ON a.`post_author` = b.`ID` 
INNER JOIN 
    `wp_usermeta` c ON a.`post_author` = c.`user_id` 
INNER JOIN 
    `wp_postmeta` d ON a.`ID` = d.`post_id` 
WHERE 
    `post_type` = 'forum' OR 
    `post_type` = 'topic' OR 
    `post_type` = 'reply' 
GROUP BY 
    a.`ID` 

Ich versuche, eine Großansicht zu erhalten, die der Post hat, seine Meta-Informationen und Informationen der seinen Autor in jeder Zeile. Alles ist gut, außer dass die GROUP_CONCAT-Spalten mehrere Duplikate haben. Zum Beispiel: von der ersten Zeile der Ergebnismenge - die Spalte user_meta_keys die Werte:

[0] => nickname 
[1] => first_name 
[2] => last_name 
[3] => description 
[4] => rich_editing 
[5] => comment_shortcuts 
[6] => admin_color 
[7] => use_ssl 
[8] => show_admin_bar_front 
[9] => locale 
[10] => wp_capabilities 
[11] => wp_user_level 
[12] => dismissed_wp_pointers 
[13] => show_welcome_panel 
[14] => session_tokens 
[15] => wp_dashboard_quick_press_last_post_id 
[16] => community-events-location 
[17] => managenav-menuscolumnshidden 
[18] => metaboxhidden_nav-menus 
[19] => nav_menu_recently_edited 
[20] => users_per_page 
[21] => wp__bbp_topic_count 
[22] => wp__bbp_reply_count 
[23] => nickname 
[24] => first_name 
[25] => last_name 
[26] => description 
[27] => rich_editing 
[28] => comment_shortcuts 
[29] => admin_color 
[30] => use_ssl 
[31] => show_admin_bar_front 
[32] => locale 
[33] => wp_capabilities 
[34] => wp_user_level 
[35] => dismissed_wp_pointers 
[36] => show_welcome_panel 
[37] => session_tokens 
[38] => wp_dashboard_quick_press_last_post_id 
[39] => community-events-location 
[40] => managenav-menuscolumnshidden 
[41] => metaboxhidden_nav-menus 
[42] => nav_menu_recently_edited 
[43] => users_per_page 
[44] => wp__bbp_topic_count 
[45] => wp__bbp_reply_count 
[46] => nickname 
[47] => first_name 
[48] => last_name 
[49] => description 
[50] => rich_editing 
[51] => comment_shortcuts 
[52] => admin_color 
[53] => use_ssl 
[54] => show_admin_bar_ 

Nickname 3 mal dupliziert und viele der anderen Felder sind auch. Ich habe ein wenig gesucht und es sieht so aus, als hätten andere das auch schon erlebt. Einige lösen es durch Verwendung von "DISTINCT" in der gruppierten Spalte - aber das funktioniert nicht für mich, weil einige der Werte tatsächlich dupliziert sind.

Also meine Fragen sind:

1) Kann mir jemand erklären, warum die GROUP_CONCAT Spalte so viele Duplikate hat und wenn die Abfrage falsch geschrieben ist - ich würde zumindest die Zählungen Figur zwischen den ‚Schlüssel‘ entsprechen Spalten und die Spalten "Werte" - aber auch nicht.

2) Kann die Abfrage angepasst werden, um das zu erreichen, wonach ich suche?

Vielen Dank für Ihre Zeit!

- EDIT # 1 - Nun der einzige Fehler ist, ich habe vergessen, die GROUP_CONCAT Grenze viel höher in MySQL zu setzen - so jetzt, dass ich up bin, denke ich, dass ich näher komme.

- BEARBEITEN # 2 - Es sieht so aus, als wären die GRUPPEN für so viele Zeilen dupliziert, wie es in jeder alternativen Tabelle gibt? Das heißt, es gibt 8 Zeilen in der postmeta-Tabelle, die mit der Post-ID übereinstimmen, also gibt es 8 doppelte Gruppen in den usermeta-Ergebnissen ... alternativ gibt es 23 Zeilen in der usermeta-Tabelle, die der Benutzer-ID entsprechen, sodass es 23 doppelte Gruppen gibt in den postmeta-Ergebnissen ... Ich bin immer noch auf der Suche nach einer Möglichkeit, dies zu korrigieren.

- EDIT # 3 -

Hier ist ein zusätzlicher MCVE:

- Original Abfrage: http://sqlfiddle.com/#!9/386b98/2

- Aktualisiert Abfrage: http://sqlfiddle.com/#!9/386b98/3

+0

Siehe auch: [? Warum soll ich einen MCVE für das, was ich scheint eine sehr einfache SQL-Abfrage zu sein] (https://meta.stackoverflow.com/questions/333952/Warum-sollte-ich-bieten-eine-MCVE-für-was-scheint-mir-zu-eine-sehr-einfache-SQL-Abfrage) – Strawberry

+0

@Strawberry - du hast Recht - ich werde auf fügen Sie MCVE allen zukünftigen SQL-Fragen hinzu - und sobald ich kann, füge ich hier einen hinzu, damit Besucher den Unterschied zwischen den beiden Abfragen sehen können –

Antwort

0

Das doppelte Problem tritt auf, weil Ich wusste nicht, wie JOINS in SQL verarbeitet werden (was ich noch lerne) - diese Stack-Overflow-Antwort hat mir wirklich geholfen (von Martin Smith) sql joins as venn diagram

Es sieht so aus, als wenn die Daten über die mehreren Zeilen der Tabelle user_meta zusammengefügt werden, wird jede post_meta Tabellenzeile so oft verkettet und umgekehrt. Also meine aktuelle Lösung ist die INNER JOIN aus diesen beiden Tabellen zu entfernen und einfach fügen Sie sie in der SELECT-Teil der Anweisung - wie folgt aus:

SELECT 
    a.`ID`, a.`post_date`, a.`post_content`, a.`post_title`, 
    a.`post_status`, a.`post_name`, a.`post_type`, a.`post_parent`, 
    (SELECT GROUP_CONCAT(d.`meta_key` SEPARATOR '{|}') FROM `wp_postmeta` d 
     WHERE d.`post_id` = a.`ID`) AS `post_meta_keys`, 
    (SELECT GROUP_CONCAT(d.`meta_value` SEPARATOR '{|}') FROM `wp_postmeta` d 
     WHERE d.`post_id` = a.`ID`) AS `post_meta_values`, 
    b.`user_login`, b.`user_pass`, b.`user_nicename`, b.`user_email`, 
    b.`user_registered`, b.`display_name`, 
    (SELECT GROUP_CONCAT(c.`meta_key` SEPARATOR '{|}') FROM `wp_usermeta` c 
     WHERE c.`user_id` = a.`post_author`) AS `user_meta_keys`, 
    (SELECT GROUP_CONCAT(c.`meta_value` SEPARATOR '{|}') FROM `wp_usermeta` c 
     WHERE c.`user_id` = a.`post_author`) AS `user_meta_values` 
FROM 
    `wp_posts` a 
INNER JOIN 
    `wp_users` b ON a.`post_author` = b.`ID` 
WHERE 
    `post_type` = 'forum' OR 
    `post_type` = 'topic' OR 
    `post_type` = 'reply' 
GROUP BY a.`ID` 

Ich wusste nicht, dass Sie das tun könnten - dies erzeugt eine viel schnelleres/saubereres Ergebnis.

- Arbeitsbeispiel: http://sqlfiddle.com/#!9/386b98/3