WordPress Multisite - catégories mondiales

21

Configuration d'une instance WP multisite - le client possède une ontologie / un ensemble de catégories existant qu'il souhaite classer tout le contenu dans l'ensemble des blogs. Le souhait est également que de nouvelles catégories soient ajoutées au niveau du «blog du réseau» et synchronisées avec les autres blogs.

Quelle est la meilleure façon de procéder?

anu
la source
je suppose que faire des catégories assignées à une variable globale et ensuite importer sur le thème init.
kaiser
4
Je pense que cette question est la même que Partager une taxonomie sur plusieurs blogs en 3.0 . Cette question n'a cependant pas obtenu de bonne réponse. C'est une question intéressante, je vais offrir une prime pour elle.
Jan Fabry

Réponses:

14
function __add_global_categories( $term_id )
{
    if ( get_current_blog_id() !== BLOG_ID_CURRENT_SITE || ( !$term = get_term( $term_id, 'category' ) ) )
        return $term_id; // bail

    if ( !$term->parent || ( !$parent = get_term( $term->parent, 'category' ) ) )
        $parent = null;

    global $wpdb;

    $blogs = $wpdb->get_col( "SELECT blog_id FROM {$wpdb->blogs} WHERE site_id = '{$wpdb->siteid}'" );
    foreach ( $blogs as $blog ) {
        $wpdb->set_blog_id( $blog );

        if ( $parent && ( $_parent = get_term_by( 'slug', $parent->slug, 'category' ) ) )
            $_parent_ID = $_parent->term_id;
        else
            $_parent_ID = 0;

        wp_insert_term( $term->name, 'category',  array(
            'slug' => $term->slug,
            'parent' => $_parent_ID,
            'description' => $term->description
        ));
    }

    $wpdb->set_blog_id( BLOG_ID_CURRENT_SITE );
}
add_action( 'created_category', '__add_global_categories' );

Cela s'exécutera chaque fois qu'une catégorie sera ajoutée sur le site principal. Quelques mises en garde / points qui méritent d'être mentionnés;

  • Si vous avez beaucoup de blogs, cette fonction peut devenir assez intensive.
  • En moyenne, nous exécutons entre 5 et 8 requêtes (éventuellement plus) par blog - en fonction de la vitesse de votre base de données, cette fonction peut avoir besoin d'être tronquée.
  • Seules les catégories nouvellement ajoutées sont «synchronisées». La mise à jour et la suppression des catégories ne le sont pas (le code devra être révisé).
  • Si une catégorie nouvellement ajoutée a un parent et que le parent est introuvable dans le blog multisite en question, la catégorie sera créée sans parent (cela ne devrait être le cas que si la catégorie parent a été créée avant l'installation de cette fonction).
TheDeadMedic
la source
1
Existe-t-il - ou pourrait-il y avoir - un plugin qui fait cela? Avec des modifications et des suppressions? Et une page de paramètres pour choisir à quelles taxonomies et à quels sites enfants l'appliquer?
Marcus Downing
En fait, vous opposeriez-vous si j'utilisais votre code comme point de départ pour écrire un plugin?
Marcus Downing
Pas de problème que ce soit - mes réponses sont sous licence d'échange de pile, le cc-wiki avec attribution requise :)
TheDeadMedic
11

Oh, la procrastination du dimanche ...

https://github.com/maugly/Network-Terminator

  • Permet d'ajouter des termes en masse sur le réseau
  • Vous pouvez sélectionner les sites qui seront affectés
  • Fonctionne avec les taxonomies personnalisées
  • Ne supprime pas
  • Ne se synchronise pas

C'est quelque chose que j'ai fait au cours des dernières heures et je n'ai plus le temps de faire d'autres tests maintenant. Quoi qu'il en soit - cela fonctionne pour moi! .)

Essaie. Il existe également une fonctionnalité de «test de fonctionnement» implémentée afin que vous puissiez vérifier le résultat avant de faire quelque chose.

Mise à jour -> Captures d'écran:

Avant l'action:

Avant l'action

Après le test:

Après le test

Le plugin lié ci-dessus ajoute une interface utilisateur mais à peu près tout ce qui est important se produit dans cette fonction:

        <?php function mau_add_network_terms($terms_to_add, $siteids, $testrun = false) {

        // check if this is multisite install
        if ( !is_multisite() )
            return 'This is not a multisite WordPress installation.';

        // very basic input check
        if ( empty($terms_to_add) || empty($siteids) || !is_array($terms_to_add) || !is_array($siteids) )
            return 'Nah, I eat only arrays!';

        if ($testrun) $log = '<p><em>No need to get excited. This is just a test run.</em></p>';
        else $log = '';

        // loop thru blogs
        foreach ($siteids as $blog_id) :

            switch_to_blog( absint($blog_id) );

            $log .= '<h4>'.get_blog_details(  $blog_id  )->blogname.':</h4>';
            $log .= '<ul id="ntlog">';

            // loop thru taxonomies
            foreach ( $terms_to_add as $taxonomy => $terms ) {

                // check if taxonomy exists
                if ( taxonomy_exists($taxonomy) ) {
                    // get taxonomy name
                    $tax_name = get_taxonomy($taxonomy);
                    $tax_name = $tax_name->labels->name;

                    //loop thru terms   
                    foreach ( $terms as $term ) {

                        // check if term exists
                        if ( term_exists($term, $taxonomy) ) {
                            $log .= "<li class='notice' ><em>$term already exists in the $tax_name taxonomy - not added!</em></li>";

                        } else {

                            // if it doesn't exist insert the $term to $taxonomy
                            $term = strip_tags($term);
                            $taxonomy = strip_tags($taxonomy);
                            if (!$testrun)
                                wp_insert_term( $term, $taxonomy );
                            $log .= "<li><b>$term</b> successfully added to the <b>$tax_name</b> taxonomy</li>"; 
                        }
                    }
                } else {
                    // tell our log that taxonomy doesn't exists
                    $log .= "<li class='notice'><em>The $tax_name taxonomy doesn't exist! Skipping...</em></li>"; 
                }
            }

            $log .= '</ul>';    

            // we're done here
            restore_current_blog();

        endforeach;
        if ($testrun) $log .= '<p><em>No need to get excited. This was just the test run.</em></p>';
        return $log;
    } ?>

Je reviendrai et modifierai cela avec plus d'informations plus tard (si nécessaire).

C'est loin d'être parfait (lire les problèmes connus dans la tête du plugin).
Toute rétroaction appréciée!

Michal Mau
la source
3
J'aime quand les gens créent des plugins en réponse à des questions! Vous méritez la prime!
Jan Fabry
Merci pour votre soutien @Jan Fabry. Je serai heureux si quelqu'un à côté de moi trouve cette chose utile.
Michal Mau
5

La réponse de TheDeadMedic semble bonne, mais j'ai fini par adopter une approche différente du problème. Au lieu de dupliquer les mêmes termes sur les nombreux sites, j'ai plutôt fait en sorte que les autres sites utilisent les tables du site d'accueil pour les termes.

add_action('init', 'central_taxonomies');

function central_taxonomies () {
  global $wpdb;

  $wpdb->terms = "wp_terms";
  $wpdb->term_taxonomy = "wp_term_taxonomy";
}

Cela remplace le nom de la table wp_2_termspar wp_terms, etc. Vous devez bien sûr vérifier dans votre base de données pour vous assurer du nom exact des tables, qui peut être différent si vous changez votre préfixe.

Vous pouvez l'exécuter à partir d'un plugin ou d'un thème (bien que je recommande un plugin). Je pourrais finir par publier un plugin pour le faire à un moment donné. Il y a deux inconvénients à cette approche:

  • Il n'est actif que sur les sites enfants dont le plugin est activé. Il n'y a aucun moyen d'imposer cela à partir du site parent.
  • Elle s'applique à toutes les taxonomies, pas seulement à certaines.

Cette approche est flexible - elle peut être adaptée pour extraire les catégories de n'importe quel blog, pas seulement celui central.


Mise à jour: j'en ai fait un plugin, qui peut être activé sur tout le site si vous en avez besoin: MU Central Taxonomies

Marcus Downing
la source
Il y a un gros problème avec cette approche: les relations entre les articles et les termes peuvent ne pas être correctes. La table term_relationships contient cette relation basée sur l'ID de poste et l'ID de terme. Mais il est toujours possible que les publications dans les sous-sites aient le même ID. La modification des termes d'un article peut avoir un effet imprévisible sur un autre article d'un autre blog.
Anh Tran
Correct, le term_relationshipstableau ne devrait pas être inclus. J'ai repéré et corrigé cela il y a longtemps dans le plugin, mais je n'ai jamais mis à jour cette réponse pour qu'elle corresponde.
Marcus Downing