Aujourd’hui je reviens à la programmation du blog. Un peu d’exercice PHP et HTML pour garder la forme! J’ai l’habitude de placer en fin d’article, un index des articles de la même catégorie. Quand une catégorie ne comporte que quelques articles, ajouter une ligne dans l’index de chaque article ne prend que peu de temps. Quand le nombre d’articles d’une même catégorie devient important cela devient vite fastidieux. On oublie des lignes, le classement est aléatoire. La solution pour me libérer de ce travail est de le faire faire par un plug-in. Il en existe beaucoup sur ce sujet. Mais selon l’adage « On n’est jamais si bien servi que par soi-même» je saisis l’occasion pour réaliser mon propre plug-in. C’est une bonne occasion d’approfondir ma connaissance de WordPress et d’apprendre à réaliser un plug-in.

1. Cahier des charges

Je veux ce plug-in le plus simple possible. Qu’il fasse simplement pour moi ce que je fais actuellement à la main. Néanmoins, l’édition de l’index sera entièrement paramétrable.

2. Contenu

  • une ligne titre de l’index,
  • n lignes hyperlien pointant sur le titre de l’article.

3. Mode opératoire – Critères de sélection

On obtient le résultat en plaçant par une simple balise ou « Shortcode » selon le vocabulaire de WordPress, dans l’article à l’endroit où l’on souhaite afficher l’index, en général pour moi, à la fin de l’article. La balise peut être placée en plusieurs endroits de l’article si nécessaire.

4. Description de la balise

Deux formats possibles:

  • [format 1]: où format1 = f8eoz_post_index : 
    affiche l 'index des articles 
    de la même catégorie que l'article courant,
  • [format 2]: où format 2 = f8eoz_post_index category="category_name" : 
    affiche l' index des articles 
    de la catégorie=category_name.

Ceci permet de répondre à tous les cas. Pour la bonne organisation de mon blog, un article appartient à une catégorie et une seule. Le format 1 suffit. En cas d’ entorse à cette règle, en plaçant plusieurs balises de formats 2, il est est possible de réaliser un index par catégorie.

5. Edition de l’index

5.1. Le titre

Il est facultatif, s’il est vide il n’est pas affiché. Le plug-in est livré avec le contenu suivant :
‘<p><B>Index des articles de la cat&eacute;gorie ${category}</B></p>’

Description:
<p><b></p></b> balises HTML facultatives, simple exemple au choix l’utilisateur,
Index des articles de… = texte libre facultatif,
${category} = tag facultatif remplacé par le nom de la catégorie de sélection.

exemple : ‘<p><B>Index des articles de la cat&eacute;gorie ${category}</B></p>’ affiche, si category_name = « Blog » :

Index des articles de la catégorie Blog

exemple : ‘<p>Index des articles></p>’ affiche :

Index des articles

5.2. L’index

Contrôlé par 3 éléments modifiables. Le plug-in est livré avec les valeurs suivantes :

  • before = <ul>
  • after = </ul> before et after contiennent les balises HTML encadrant les lignes de l’index,
  • line = <li><a href= »${permalink} » target= »_blank »>${title}</a></li> : format de la ligne à afficher, le tag ${permalink} est remplacé par le permalink du post, le tag ${title} est remplacé par le titre du post.

6. Présentation

Deux critères définis par l’utilisateur. Le plug-in est livré avec les valeurs suivantes :

  • critère de tri: orderby = titre,
  • ordre de tri: order = ASC,
  • nombre de lignes :postsPerPage = -1 (illimité).

7. Administration

Vu la simplicité du plug-in, je n’ai pas réalisé de module d’administration pour l’instant (futur projet). Les éléments paramétrables sont placés en début de programme dans des constantes qu’il est possible de modifier facilement.

8. Description du programme

8.1. Entête

L’entête d’un plug-in WordPress respecte les conventions suivantes:

/*
Plugin Name: F8EOZ Post Index
Plugin URI: http://www.f8eoz.com
Description: Related posts index plugin. Filter: category name.
Author: F8EOZ Bernard Decaestecker
Version: 1.0 03/02/2013 19:00
Author URI: http://www.f8eoz.com
*/

8.2. Constantes

Ci-dessous les constantes. Le premier groupe appelé « Editable constant » contient les constantes de présentation et d’édition de l’index. Voir description paragraphes ci-dessus. Elles peuvent être adaptées par l’utilisateur. Le second groupe de constantes appelé « Not editable constant » ne doit pas être changé. Il fixe les éléments de base, répertoires, nom du plug-in, selon les conventions de WordPress.

//Editable constant
define('F8EOZPOSTINDEX_TITLE', '<p><B>Index des articles de la cat&eacute;gorie ${category}</B></p>');
define('F8EOZPOSTINDEX_LINE', '<li><a href="${permalink}" target="_blank">${title}</a></li>');
define('F8EOZPOSTINDEX_BEFORE_LINES', '<ul>');
define('F8EOZPOSTINDEX_AFTER_LINES', '</ul>');
define('F8EOZPOSTINDEX_ORDER', 'ASC');
define('F8EOZPOSTINDEX_ORDERBY', 'title');
define('F8EOZPOSTINDEX_POSTS_PER_PAGE', -1); //all posts, no limit

//Not editable constant
define('F8EOZPOSTINDEX_PLUGIN_NAME', 'f8eoz_post_index');
define('F8EOZPOSTINDEX_PLUGIN_BASENAME', plugin_basename(__FILE__));
define('F8EOZPOSTINDEX_PLUGIN_DIR', dirname(F8EOZPOSTINDEX_PLUGIN_BASENAME));
define("F8EOZPOSTINDEX_SHORTCODE", 'f8eoz_post_index');

8.3. Classe PostIndex

La classe PostIndex contient les propriétés et les méthodes (fonctions) pour créer l’index.

La méthode __construct est exécutée quand on crée une instance de cet objet. Elle initialise les propriétés avec les constantes de présentation et d’édition.

La méthode parse($category_name) traite le cas du format 1 ou du format 2 du Shortcode. En l’absence d’un nom de catégorie, c’est la catégorie de l’article qui est utilisée en référence. Si l’article contient plusieurs catégories, c’est la première de la liste qui sert de référence.

Dans la méthode PrintIndex la fonction
echo str_replace( ‘${category}’, $this->categoryName, $this->title );
remplace le tag ${category} s’il existe par le nom de la catégorie et affiche le titre ainsi édité.
De la même façon, la fonction
echo str_replace( ‘${permalink}’, get_Permalink() , str_replace( ‘${title}’ , get_the_title(),  $this->line )  );
remplace les tags ${permalink} et ${title} par leur valeur et affiche une ligne de l’index ainsi éditée. Ces fonctions imbriquées, utilisent le principe du pipeline au sens UNIX du terme. Le pipeline exécute une série de fonctions dont le résultat de l’une sert d’argument à la suivante.

class PostIndex {
    private $title;
    private $categoryName;
    private $line;
    private $beforeLines;
    private $afterLines;
    private $order;
    private $orderby;
    private $postsPerPage;

function __construct($title, $line, $beforeLines, $afterLines, $order, $orderby, $postsPerPage) {
    $this->title = $title;
    $this->line = $line;
    $this->beforeLines = $beforeLines;
    $this->afterLines = $afterLines;
    $this->order = $order;
    $this->orderby = $orderby;
    $this->postsPerPage = $postsPerPage;
}

function getCategoryName() {
    return $this->categoryName;
}

function getIndexTitle() {
    return $this->title;
}

function setIndexTitle($title) {
    $this->$title = $title;
}

function parse($category_name) {
    if(empty($category_name)) {
        $categories = get_the_category( get_the_ID() ); //get catagories of current post
        if( !empty($categories) ) {
            $this->categoryName = $categories[0]->cat_name; //default = get 1st catagory_name
            return;
        }
    }
    $this->categoryName = $category_name; //other = specified category
}

function printIndex() {
    if(is_null($this->categoryName)) //no category, no index
        return;

    echo "\n<!-- INDEX GENERATED BY f8eoz_post-index --> \n";

    if(!empty($this->title)) {
        echo str_replace( '${category}', $this->categoryName, $this->title );
    }

    $args = array(  'order'=> $this->order,
                    'orderby' => $this->orderby,
                    'posts_per_page' => $this->postsPerPage,
                    'category_name' => $this->getCategoryName());

    echo $this->beforeLines;
    // The Query
    query_posts( $args );
    // The Loop
    while ( have_posts() ) : the_post();
        echo str_replace( '${permalink}'
                         , get_Permalink()
                         , str_replace( '${title}'
                         , get_the_title(), $this->line )
                         );
    endwhile;
    // Reset Query
    wp_reset_query();
    echo $this->afterLines;

    echo "\n<!-- END INDEX GENERATED BY f8eoz_post-index --> \n";
    }
}

8.4. Exécution du plug-in

La fonction f8eoz_post_index() est accrochée à WordPress au moyen de la fonction add_action().

// ==========================================================================
// Runs after WordPress has finished loading but before any headers are sent.
add_action('init', 'f8eoz_post_index');
// ==========================================================================

*/

La fonction f8eoz_post_index()

  • crée une instance de PostIndex avec les constantes de présentation et d’édition,
  • décode le shortcode,
  • lance l’affichage de l’index en utilisant la bufferisation PHP.
function f8eoz_post_index() {
    //should be made during init
    load_plugin_textdomain( F8EOZPOSTINDEX_PLUGIN_NAME, false, F8EOZPOSTINDEX_PLUGIN_DIR );

    if(!is_admin()) {
        function f8eoz_post_index_func( $atts ) {
            //create a new instance of object PostIndex with initial properties
            $pi = new PostIndex(F8EOZPOSTINDEX_TITLE,
                                F8EOZPOSTINDEX_LINE,
                                F8EOZPOSTINDEX_BEFORE_LINES,
                                F8EOZPOSTINDEX_AFTER_LINES,
                                F8EOZPOSTINDEX_ORDER,
                                F8EOZPOSTINDEX_ORDERBY,
                                F8EOZPOSTINDEX_POSTS_PER_PAGE);
            /*
            Combines user shortcode attributes with known attributes and fills in defaults when needed.
            The result will contain every key from the known attributes,
            merged with values from shortcode attributes.
            Usage
            shortcode_atts( $pairs , $atts );
            Parameters
            $pairs :( array) (required) Entire list of supported attributes and their defaults
            Default: None
            $atts : (array) (required) User defined attributes in shortcode tag
            Default: None
            Return Values (array) Combined and filtered attribute list.
            */
            extract( shortcode_atts( array ( 'category' => null ) , $atts ) ); //extract tag
            $pi->parse($category); //parse tag

            ob_start();    //store post data in buffer
            $pi->printIndex();
            $content = ob_get_contents();
            ob_end_clean();
            return $content;
        }
        add_shortcode(F8EOZPOSTINDEX_SHORTCODE, 'f8eoz_post_index_func');

    }
}

*/

9. Installation

Download  Télécharger le plug-in.

Décompresser le fichier.
Copier le répertoire f8eoz-post-index dans le répertoire /wp-content/plugins/.
Dans la fenêtre d’aministration choisir Extensions et activer le plug-in F8EOZ Post Index.

10. Test

L’index ci-dessous est affichée par ce plug-in.

Index des articles de la catégorie Blog