2011-02-06 2 views
0

Dans mon fichier d'index je reçois des données de la base de données à l'aide de cette fonction (qui est dans un autre fichier):Tagging et explose en php

function get_all_threads($link, $start) 
{ 
    $threads = select_Query("SELECT thread.title, thread.id as t_id, 
          thread.content, author.username, author.id as a_id, 
          GROUP_CONCAT(DISTINCT tags.name ORDER BY tags.name DESC SEPARATOR ',') AS tags 
          FROM thread JOIN thread_tags ON thread.id = thread_tags.thread_id 
          JOIN tags ON thread_tags.tag_id = tags.id 
          INNER JOIN author on author.id = thread.author_id 
          GROUP BY thread.id DESC 
          LIMIT $start, 30", $link);  

    return $threads; 
} 

Le code dans mon fichier d'index est comme suit:

$threads = get_all_threads($link, $start); 
    include FORUM_ROOT . 'html/main/threads.html.php'; 

Dans threads.html.php

<?php foreach ($threads as $thread): ?> 

<h1><?php echo $thread['title']; ?></h1> 
<?php echo $thread['content']; ?> 
<?php echo $thread['tags']; ?> <!-- All of these appear as one --> 

<?php endforeach; ?> 

Comme vous pouvez le voir, je reçois les fils, leurs auteurs et leurs tags. Cependant, j'utilise GROUP_CONCAT pour les balises, quand je veux faire chaque balise individuelle un lien, comme dans threads.html.php:

<a href="?tag=<?php echo $thread['tags']; ?>" > 
    <?php echo $thread['tags']; ?> 
</a> 

Toutes les balises apparaissent comme un lien, (par exemple, si les étiquettes étaient la pomme , orange, banane ils apparaissent comme apple, orange, banana et non apple, orange, banana):

Je sais de diviser ces balises je peux utiliser exploser et itérer sur chacun comme suit:

<?php $tags = array(); 
$tags = explode(',', $thread['tags']); 
?> 


(Tagged: 
<?php foreach ($tags as $tag): ?> 
<a href="/tag?=<?php echo $tag;?>"><?php echo $tag; ?></a> 
<?php endforeach; ?>) 

Cependant, je aurait Ensuite, il faut le faire dans threads.html.php et je veux garder le code de présentation séparé.

Existe-t-il une façon plus simple de faire cela dans index.php? De plus à itérer sur chaque fil et exploser chaque balise prendra trop de temps pour les fils qui sont plus de 30

Edit:

Ma structure de table est la suivante:

fil

, author_threads, auteur , étiquette, thread_tags, réponse et author_replies

1: http://apple, orange, banane

+0

pouvez-vous ajouter votre structure de table db –

+0

Je préférerais une simplification du problème ... si possible. – Kissaki

+0

Je ne pense pas que 'GROUP_CONCAT' est une norme SQL ... quelle DBS utilisez-vous? – Kissaki

Répondre

0

Traiter get_all_threads dans le cadre du modèle - boîte noire - vous n'avez pas besoin de savoir comment les données sont récupérées (est-ce une requête SQL, des fichiers XML ou appel api externe). Vous êtes intrested dans les données, rien de plus.

Jusqu'à présent, il n'est pas possible d'obtenir plusieurs tags pour un thread via une requête SQL. Même si vous enlevez GROUP_CONCAT vous obtiendrez un tas d'enregistrements pour un thread, qui aura également besoin d'analyse d'une certaine manière. Mais selon le premier paragraphe, vous devriez analyser les données dans votre fonction.

function get_all_threads($link, $start) 
{ 
    $threads = select_Query("SELECT thread.title, thread.id as t_id,.."); 

    //PHP 5.3 
    array_walk($threads, function(&$thread) { 
     $thread['tags'] = explode(',', $thread['tags']); 
    }); 

    //PHP < 5.3 
    foreach ($threads as &$thread) { 
     $thread['tags'] = explode(',', $thread['tags']); 
    } 


    return $threads; 
} 

Lorsque vous le faites de cette façon, votre code de présentation sera propre.

+0

Erreur d'analyse: erreur de syntaxe, inattendue T_FUNCTION sur la ligne 4 –

+0

Ce code requiert PHP 5.3 car il utilise une fonction anonyme. Version ajoutée sans elle. Mais mise à niveau vers PHP 5.3 recommandé;) – singles

+0

J'utilise Ubuntu Karmic Koala, donc je vais devoir mettre à niveau avant que je puisse obtenir 5.3 –

0

Vous souhaitez obtenir et imprimer plusieurs étiquettes pour chaque fil. Alors pourquoi le faites-vous dans une requête? Au lieu de faire une requête massif vous le feriez:

SELECT thread.title, thread.id as t_id, thread.content, 
     author.username, author.id as a_id, 
INNER JOIN author ON author.id = thread.author_id 
ORDER BY thread.id DESC 
LIMIT $start, 30 

et pour chaque fil un

SELECT tags.name 
FROM thread_tags 
WHERE thread_tags.thread_id == $id 

stocker ces données dans une structure de données et le transmettre à vos modèles de présentation (comme vous le faites avec votre fils de conversation).

(Bordel, qui était une question compliquée ... est beaucoup mieux maintenant aussi bien, non? Et beaucoup plus facile à lire et à comprendre!)

BTW, ce qui est le GROUP BY thread.id DESC? J'espère que votre ID est UNIQUE, ou mieux encore une CLÉ PRIMAIRE! Aucun GROUP BY nécessaire alors!

+0

Je ne sais pas vraiment pourquoi le groupe par est là, j'utilise des clés primaires, en supprimant maintenant –

+0

Le problème que j'ai, c'est que je ne saurai pas toujours combien de threads je vais obtenir, voir la limite. –

+0

Et quel est le problème à ce sujet? Obtenez les tags pour tous les sujets que vous obtenez. – Kissaki