Interrogare il Database di WordPress (WP_Query, pre_get_posts, get_posts)

Cosa succede quando un visitatore richiede una pagina del vostro sito?

Si attiva una complessa procedura che vede coinvolto il client (il browser dell’utente), il server, il CMS e infine di nuovo il client, che riporterà all’utente la risorsa richiesta oppure, se qualcosa non è andato come avrebbe dovuto, un messaggio di errore del server.

A seguito dell’invio di una richiesta da parte del client, WordPress carica svariati file del core, tra cui wp-config.php, wp-settings.php, wp-includes/functions.php, ecc. (per una descrizione dettagliata, si veda Query Overview).
Ad un certo punto, cioè quando è stato caricato l’oggetto $wp, in WordPress si attiva una sequenza di operazioni:

  1. WordPress analizza l’URL della richiesta e lo scompone in una serie di parametri. Questi parametri costituiscono la query specification.
  2. Vengono definite le variabili is_ utilizzate dai conditional tag, ossia quelle funzioni di WordPress che verificano la sussistenza di determinate condizioni (ad es. la funzione is_home() verifica se la pagina richiesta dall’utente sia la home page del sito). Queste funzioni dipendono dalle variabili presenti nella query specification.
  3. La query specification viene convertita in una query MySQL, che viene eseguita sul database. All’interno di un Loop, la risposta viene memorizzata in un oggetto $wp_query, mentre se la richiesta viene dalla funzione get_posts(), la risposta sarà memorizzata in un array di oggetti $post.
  4. WordPress gestisce, quindi, gli errori 404, invia gli header HTTP, inizializza alcune variabili del Loop e seleziona il template da utilizzare per visualizzare la risorsa richiesta in base alle variabili della query specification
  5. WordPress carica il Template secondo l’ordine della gerarchia dei template.
  6. WordPress esegue il Loop.

Insomma, le operazioni svolte ad ogni richiesta sono davvero tante. Tutto comincia dalla trasmissione di un URL di richiesta che in WordPress assume la veste di permalink.

Prima di analizzare la richiesta del browser, è necessario soffermarsi su ciò che può essere richiesto. In pratica bisogna rispondere alle domande: Cosa sono i contenuti di WordPress e come sono organizzati?

Ecco il percorso che seguiremo in questo articolo:

Il database di WordPress

Un sito creato con WordPress è un sito dinamico, il che vuol dire che le pagine web di cui si compone non sono fisicamente presenti sul disco del server come file HTML, ma vengono generate dinamicamente dal software a partire dai dati presenti nel database.

WordPress database description
Lo schema del database di WordPress (fonte: Database Description)

Al momento il database di una nuova installazione di WordPress si compone di 12 tabelle:

  • wp_commentmeta
  • wp_comments
  • wp_links
  • wp_options
  • wp_postmeta
  • wp_posts
  • wp_termmeta
  • wp_terms
  • wp_term_relationships
  • wp_term_taxonomy
  • wp_usermeta
  • wp_users

Di tutte, quella che qui ci interessa maggiormente è la tabella wp_posts, che tiene in memoria le principali informazioni relative ai contenuti di WordPress. Questa tabella dispone dei seguenti campi:

  • comment_count
  • comment_status
  • guid
  • ID
  • menu_order
  • pinged
  • ping_status
  • post_author
  • post_content
  • post_content_filtered
  • post_date
  • post_date_gmt
  • post_excerpt
  • post_mime_type
  • post_modified
  • post_modified_gmt
  • post_name
  • post_parent
  • post_password
  • post_status
  • post_title
  • post_type
  • to_ping

Dunque la tabella wp_posts è il posto dove vengono memorizzati i contenuti del sito, ed è principalmente da questa tabella che WordPress seleziona i record che servono a costruire la risposta da inviare all’utente.

Ma di che tipo di dati si tratta?

I post di WordPress

Tutti i contenuti del blog o del sito WordPress vengono memorizzati nella tabella wp_posts del database. Non si tratta solo degli articoli del blog, ma anche delle pagine statiche, dei custom post type e di altri tipi di post, alcuni visibili all’utente, altri nascosti e utilizzati per altri fini dal software (per un’analisi più dettagliata rinvio a questo articolo).

Di default WordPress suddivide i contenuti del sito in 5 tipi di post:

  • articoli – gli articoli del blog
  • pagine – le pagine statiche
  • allegati – le pagine degli allegati
  • revisioni
  • menu di navigazione

Dal punto di vista del software, ciò che distingue un tipo di post da un altro è il valore di uno specifico campo della tabella wp_post, ossia post_type. I precedenti tipi di post vengono, quindi, contraddistinti dai seguenti valori del campo post_type:

  • post
  • page
  • attachment
  • revision
  • nav_menu_item

Altri tipi di post hanno funzioni di amministrazione e non riguardano i contenuti del sito. Si tratta di

  • CSS personalizzati
  • Changeset
  • Richieste dati utente

Oltre a questi tipi di post, lo sviluppatore può aggiungere tipi di post personali, i custom post type

A questo punto siamo alla domanda centrale di questo articolo: come si passa dal database alla pagina? In altri termini, come fa WordPress a generare la pagina a partire dai dati registrati nel database?

Interrogare il database di WordPress: WP_Query, query_posts(), get_posts()

Diciamolo subito: dimentichiamoci di SQL!

Per interrogare il database di WordPress non è necessario essere dei GURU di SQL. E, oltre a non essere necessario, è assolutamente sconsigliato mettersi a creare delle query, semplici o avanzate che siano, mettendo mano direttamente al codice. Tener conto di tutte le best practice che riguardano la sicurezza e le prestazioni delle query non è lavoro da poco, e si corre sempre il rischio di dimenticare qualche variabile importante e di lasciare la porta aperta a intrusioni indesiderate.

Allora come accedere al database di WordPress?

Le soluzioni a disposizione degli sviluppatori di temi e plugin sono diverse:

  • WP_Query è la classe PHP che svolge tutte le funzioni legate alla costruzione e all’esecusione della query. Creando una nuova istanza di WP_Query, possiamo creare delle query personalizzate da utilizzare all’interno di plugin, temi e child themes. La classe è documentata nel Codex.
  • get_posts() è una funzione di WordPress che fa da contenitore per un’istanza di WP_Query e permette di creare degli elenchi di post in modo più semplice rispetto ad una nuova istanza di WP_Query. Anche questa funzione è pienamente documentata nel Codex.
  • query_posts() sovrascrive completamente la query principale e non andrebbe mai utilizzata in temi e/o plugin. Lo stesso Codex sconsiglia l’utilizzo di questa funzione e per questo non ne parleremo. Al suo posto si consiglia, nella generalità dei casi in cui si vuole modificare la query principale, di utilizzare l’action hook pre_get_posts.
  • pre_get_posts fa parte della famiglia dei cosiddetti action hook di WordPress (più semplicemente “azioni”). pre_get_posts permette di modificare le variabili della query dopo la creazione dell’oggetto query, ma prima che la query venga effettivamente eseguita sul database. Questa azione è estremamente utile quando si ha la necessità di modificare alcuni parametri della query per selezionare o filtrare i risultati in base a criteri personali.

Analizziamo tutte le opzioni a disposizione.

La Classe WP_Query e il Loop di WordPress

Con la classe WP_Query WordPress offre un rapido e sicuro accesso al database. Una volta interrogato il database, il dataset restituito potrà essere utilizzato in un ciclo iterativo (comunemente noto come Loop) per la visualizzazione dei contenuti del sito.

Ecco come si presenta un Loop nella sua forma più semplice:

<?php if ( have_posts() ) : while ( have_posts() ) : the_post(); ?>
    <!-- codice -->
<?php endwhile; else : ?>
    <!-- codice -->
<?php endif; ?>

Questo è il Loop nel suo aspetto standard. Nella realtà in luogo dei commenti si trova il codice HTML che costituisce la struttura della pagina.

Avrete notato che non c’è traccia della query. Ma perché?

Perché WordPress crea automaticamente un’istanza della query e la memorizza nell’oggetto globale $wp_query. Sarà la classe stessa a impostare la query da eseguire in base alla pagina richiesta dall’utente.

Ad esempio, se l’utente chiede un archivio autore, la classe genererà una query che recupera dal database un certo numero di articoli provenienti dall’autore specificato. Lo stesso avviene per gli archivi delle categorie, dei tag e così via. Il funzionamento è esattamente lo stesso, sia per archivi con più contenuti, sia per singoli post, per i quali, ovviamente, il ciclo viene eseguito una sola volta.

Veniamo ai metodi della classe. Nella normalità dei casi, in un Loop standard vengono utilizzati solo due metodi:

  • have_posts() verifica se nel dataset corrente esiste almeno un risultato utile.
  • the_post() recupera il post successivo e imposta il post corrente.

Tuttavia la classe WP_Query dispone di numerosi metodi, tra cui:

  1. in_the_loop()
  2. rewind_posts()
  3. have_comments()
  4. the_comment()
  5. set()
  6. setup_postdata()

Tra questi, particolare rilevanza assume il metodo $wp_query->setup_postdata(), di cui parlerò più avanti.

Fin qui nella teoria. Ora facciamo un esempio concreto e diamo un’occhiata al Loop del file index.php del tema TwentyTwenty:

if ( have_posts() ) {

    $i = 0;

    while ( have_posts() ) {
        $i++;
        if ( $i > 1 ) {
            echo '<hr class="post-separator styled-separator is-style-wide section-inner" aria-hidden="true" />';
        }
        the_post();

        get_template_part( 'template-parts/content', get_post_type() );

    }
} elseif ( is_search() ) {
    ?>

    <div class="no-search-results-form section-inner thin">

        <?php
        get_search_form(
            array(
                'label' => __( 'search again', 'twentytwenty' ),
            )
        );
        ?>

    </div><!-- .no-search-results -->

    <?php
}

Qui incontriamo altri due tipi di funzioni: conditional tag e template tag.

Conditional tag

I conditional tag (ad esempio is_search()) sono funzioni che testano una condizione e restituiscono true o false a seconda che la condizione sia verificata o meno. Si tratta di funzioni da utilizzare nei template file dei temi e dei child theme per stabilire quale codice visualizzare a seconda di una determinata condizione. Queste funzioni vanno utilizzate solo dopo che la query sia già stata eseguita, quindi i template file sono il posto perfetto dove inserire i conditional tag.

Tra i conditional tag maggiormente utilizzati, ricordo:

  • is_home()
  • is_front_page()
  • is_admin()
  • is_single()
  • is_singular()
  • is_page()
  • is_category()

Per uno sguardo approfondito, si legga il Codex, dove è anche disponibile l’elenco completo dei conditional tag.

Template tag

I template tag (ad esempio get_template_part()) sono particolari funzioni utilizzate, come i conditional tag, all’interno dei template file dei temi (e dei child theme), ma hanno una funzione diversa. Questi ultimi, infatti, vengono utilizzati per recuperare dal database informazioni relative ai contenuti e mostrarli a video o restituirli in forma di valori per l’utilizzo nel codice PHP.

Alcuni template tag incorporano il contenuto di template file. Ad esempio, il template tag get_header() dice a WordPress di includere il contenuto del template file header.php.

Il template tag the_title(), invece, manda a video il titolo dell’articolo corrente recuperato dal database. In molti casi è necessario passare al template tag dei parametri che specifichino l’oggetto della richiesta. Ad esempio, il template tag bloginfo() manda a video l’informazione richiesta dal parametro stringa passato come argomento. Ad esempio:

bloginfo( 'name' );

Questo chiede a WordPress di mandare a video il titolo del post corrente. get_bloginfo() recupera gli stessi dati della funzione precedente, ma li restituisce senza mandarli a video, per essere utilizzati nel codice PHP.

Torniamo all’esempio del file index.php di TwentyTwenty. L’istruzione

get_template_part( 'template-parts/content', get_post_type() );

incorpora all’interno del Loop un template file diverso a seconda del tipo di post. Nel caso degli articoli del blog, il template file incorporato sarà template-parts/content.php. Vediamone solo un frammento:

<div class="entry-content">

    <?php
    if ( is_search() || ! is_singular() && 'summary' === get_theme_mod( 'blog_content', 'full' ) ) {
        the_excerpt();
    } else {
        the_content( sprintf( '<span class="faux-button">%1$s</span> <span class="screen-reader-text">"%2$s"</span>', __( 'Continue reading', 'twentytwenty' ), get_the_title() ) );
    }
    ?>

</div><!-- .entry-content -->

In questo frammento di codice sono evidenti sia i conditional tag che i template tag di cui si è discusso.

Per una descrizione più dettagliata dei template tag, si faccia riferimento al Codex. Sempre nel Codex è disponibile l’elenco (quasi) completo dei template tag correnti.

In questa lunga sezione ho descritto il funzionamento generale del Main Loop, ossia il Loop che manda a video i contenuti principali delle pagine di WordPress, e ci servirà come premessa per quanto descriverò di seguito.

Nella prossima sezione vediamo come creare una nuova istanza dell’oggetto query per creare Loop secondari all’interno della pagina.

Come creare una query secondaria con WP_Query

Su ogni singola pagina, WordPress genera ed esegue svariate query. Per farci un’idea di quante query possano essere eseguite su una data pagina, possiamo far ricorso al plugin gratuito Query Monitor.

Uno strumento di diagnosi delle query: il plugin Query Monitor

Si tratta di un ottimo strumento di diagnosi che permette di analizzare un numero incredibile di aspetti di ogni singola pagina di un sito WordPress. Per quel che riguarda le query, una pagina di esempio di questo sito esegue ben 44 query. La sola funzione get_option(), utilizzata in diversi contesti (tema e plugin), esegue ben 10 query.

La scheda “Query per chiamante” di Query Monitor

La scheda di analisi delle query mostra le funzioni e i metodi di classe che eseguono query e ne indica il numero. Le query di ogni singola funzione possono essere analizzate cliccando sul link corrispondente

Analisi delle query per singola funzione chiamante in Query Monitor

Come si vede dall’immagine qui sopra, il metodo che abbiamo selezionato genera 3 istruzioni SELECT per visualizzare i commenti ad un post.

Installate, quindi, il plugin e passate alla lettura della prossima sezione.

Creare una nuova istanza di WP_Query

Se abbiamo definito come query principale (Main Query) la query che genera i contenuti centrali di una pagina, siano essi singoli post, elenchi di articoli del blog o archivi di vario tipo, le query secondarie sono query che si aggiungono alla query principale e vengono eseguite sulla stessa pagina per mostrare elenchi di articoli in contesti differenti.

I contesti in cui può essere necessaria una nuova query vanno dall’utilizzo in un template file custom, all’utilizzo in plugin che mostrano contenuti o parti di contenuti a video, come nel caso dei plugin che mostrano elenchi di post correlati o elenchi di articoli/categorie/tassonomie, ecc.

Ecco come creare una nuova istanza di WP_Query:

// Un array di argomenti
$args = array( 'arg_1' => 'val_1', 'arg_2' => 'val_2' );

// La Query
$the_query = new WP_Query( $args );

// Il Loop
if ( $the_query->have_posts() ) {

    while ( $the_query->have_posts() ) : $the_query->the_post(); 
        // Codice
    endwhile;

} else {
        // Nessun post trovato
}
/* Reimposta l'oggetto $post */
wp_reset_postdata();

Analizziamo punto per punto:

  • $args è un array di argomenti che determina i risultati che devono essere recuperati dal database. Si tratta delle cosiddette query var, e ne darò una descrizione più dettagliata nel prossimo paragrafo. Per adesso diciamo solo che le query var sono coppie chiave/valore che stabiliscono i criteri di selezione, filtro e ordinamento dei contenuti del result set.
  • $the_query è la nuova istanza della classe.
  • Segue il ciclo iterativo del Loop. Si noti che in questo caso non utilizziamo le funzioni have_posts e the_post, ma invochiamo direttamente i metodi della classe.
  • Nelle query secondarie, una volta usciti dal Loop, è necessario effettuare una chiamata alla funzione wp_reset_postdata(). Questa funzione ripristina la variabile globale $post dopo l’esecuzione della query ed è necessario invocarla perché ogni nuova query sovrascrive l’oggetto $post. Su questa funzione c’è un’interessante discussione su Stack Exchange che merita una lettura.
    Ecco cosa ci dice al riguardo la documentazione ufficiale del Codex:
    The global $post variable is used by template tags by default. wp_reset_postdata() restores the global $post variable to the current post in the main query (contained in the global $wp_query variable as opposed to the $sec_query variable), so that the template tags refer to the main query loop by default again.

Insomma, una query secondaria non è molto diversa da una Main Query. Ora facciamo un altro passo in avanti e andiamo a conoscere i parametri della query, le cosiddette query vars.

I parametri delle query di WordPress

Questi parametri sono disponibili, con poche varianti, indipendentemente dal metodo da noi scelto per accedere al database e recuperare contenuti. Utilizziamo questi argomenti, quindi, nella personalizzazione di una Main Query, nella creazione di nuove istanze di classe, quando filtriamo l’oggetto $query, infine quando utilizziamo la funzione get_posts() per creare elenchi di articoli.

Le variabili della query sono anche note come Query Vars e vengono distinte in due categorie più una:

  • Variabili pubbliche (Public Query Vars)
  • Variabili private (Private Query Vars)
  • Variabili personali (Custom Query Vars)

Le Public Query Vars sono le variabili della query che possono essere trasmesse a WordPress attraverso una query string.

Ma di cosa parliamo? Prendiamo il seguente URL:

http://example.com/?p=123

Questo si divide in due parti, separate dal punto interrogativo:

  • la prima parte individua il nome di dominio,
  • la seconda parte è la query string e si compone di una serie di coppie chiave=valore che sono le variabili della query string.

In WordPress queste variabili sono visibili quando i Pretty Permalink sono disattivati. Eccone un esempio:

https://frammentidicodice.com/?post_type=definizioni
  • post_type è il nome della query var pubblica;
  • definizioni è il valore della variabile.

In WordPress possiamo trasformare gli URL in cui vengono visualizzate le coppie chiave/valore delle query var, spesso incomprensibili alla lettura di un essere umano, in stringhe con valore semantico, ossia dotate di significato comprensibile alle persone.

Impostazioni – Permalink

WordPress, quindi, individuerà la risorsa richiesta dall’utente trasformando il permalink leggibile agli esseri umani (Pretty Permalink) nella serie di chiavi e valori che serviranno a generare la risposta da restituire all’utente.

Le Private Query Vars possono essere trasmesse a WordPress attraverso uno script PHP.

Per gli sviluppatori più ambizioni, infine, la Query API permette di registrare Custom Query Vars per le finalità più diverse. Su questo argomento rinvio ad un articolo su WPMU Dev (Building Customized URLs in WordPress: Permalinks, Query Vars and URL Rewriting).

Nel loro insieme, i parametri della query vengono raggruppati in ben 15 categorie:

  • Author Parameters
  • Category Parameters
  • Tag Parameters
  • Taxonomy Parameters
  • Search Parameters
  • Post & Page Parameters
  • Password Parameters
  • Post Type Parameters
  • Order & Orderby Parameters
  • Date Parameters
  • Custom Field (post meta) Parameters
  • Permission Parameters
  • Mime Type Parameters
  • Caching Parameters
  • Return Fields Parameter

Una lettura rapida di questi gruppi di parametri suggerisce che possono essere recuperati dal database contenuti in base al tipo, all’autore, alle categorie, ai tag, ale tassonomie, alla data, ai custom field, ecc. ecc.

Vediamo, ad esempio, quali sono i parametri categoria:

  • cat (int) – pubblico
  • category_name (string) – pubblico
  • category__and (array) – privato
  • category__in (array) – privato
  • category__not_in (array) – privato

Le prime due variabili sono pubbliche, le altre tre private. In una query string, quindi, potremmo utilizzare gli argomenti cat e category_name, ma nessuno degli altri parametri di categoria, che invece potremmo utilizzare liberamente, come vedremo a breve, all’interno di uno script.

Facciamo un primo semplice esempio:

$the_query = new WP_Query( array( 'category_name' => 'webdesign' ) );

Un esempio appena più complesso:

$the_query = new WP_Query( array( 'category__in' => array( 5, 19 ) ) );

E, infine, un esempio con due parametri:

$the_query = new WP_Query( array( 'author_name' => 'carlo', 'category_name' => 'webdev,wordpress' ) );

I parametri della query possono essere utilizzati singolarmente o congiuntamente, e ciò permette di creare query semplici e query estremamente avanzate, come ad esempio le meta query basate sui meta dati dei custom field.

Per l’elenco completo dei parametri della query e delle rispettive descrizioni, faccio ampio rinvio alle seguenti risorse:

Torniamo al nostro esempio precedente e creiamo una vera query secondaria:

// Un array di argomenti
$args = array( 'author_name' => 'carlo', 'category_name' => 'webdev,wordpress' );

// La Query
$the_query = new WP_Query( $args );

// Il Loop
if ( $the_query->have_posts() ) {

    while ( $the_query->have_posts() ) : $the_query->the_post(); 
        // Codice
    endwhile;

} else {
        // Nessun post trovato
}
/* Reimposta l'oggetto $post */
wp_reset_postdata();

Modificare la Main Query di WordPress con pre_get_posts

pre_get_posts è un action hook, ossia una funzione di WordPress che viene eseguita in un istante preciso dell’esecuzione del core di WordPress. Lo sviluppatore di plugin (e di temi) può “agganciare” una funzione custom ad un action hook di WordPress per eseguire il codice che gli occorre.

In realtà gli hook sono di due tipi:

I filtri sono particolari funzioni, anche queste attivate in momenti specifici dell’esecuzione del core, attraverso cui passano dati che possono essere filtrati in base a criteri stabiliti dallo sviluppatore.

L’azione pre_get_posts viene attivata subito dopo la creazione della query, ma prima che questa venga eseguita sul database. In questo instante dell’esecuzione del core, quindi, è possibile eseguire una funzione di callback che permetta di apportare modifiche alla query prima della sua effettiva esecuzione.

Un plugin è il posto ideale per inserire questo hack, e per chi non avesse mai sviluppato un plugin, dico solo che basta creare un file PHP con un nome tipo mio-plugin.php e inserirlo in una cartella con lo stesso nome all’interno di wp-content/plugins:

wp-content/plugins/mio-plugin/mio-plugin.php

All’interno del file inseriamo il seguente codice:

<?php
/**
 * @package my_plugin
 * @version 1.0
 */
/*
Plugin Name: My Plugin
Plugin URI: http://wordpress.org/extend/plugins/#
Description: Example plugin
Author: My name
Version: 1.0
Author URI: https://ilmiosito.com/
*/

L’intestazione permette a WordPress di individuare e gestire correttamente il plugin. È tutto ciò che in questa sede ci occorre sapere per testare il codice di questo articolo.

Ora aggiungiamo il codice PHP:

<?php
/**
 * Customize the query
 *
 * @param $query obj The WP_Query instance (passed by reference)
 *
 * @link https://codex.wordpress.org/Plugin_API/Action_Reference/pre_get_posts
 */
function myplugin_pre_get_posts( $query ) {
    // check if the current page is an admin page 
    // or current query is not the main query
    if ( is_admin() || ! $query->is_main_query() ){
        return;
    }
    if ( $query->is_author( 'carlo' ) ){
        $query->set( 'category_name', 'webdesign' );
    }
}
add_action( 'pre_get_posts', 'myplugin_pre_get_posts', 1 );

In questo semplice esempio abbiamo creato un plugin che modifica i parametri della query al volo, prima che venga eseguita. Grazie al metodo set() dell’oggetto $query, impostiamo una categoria specifica alla query in modo che, nell’archivio dell’autore carlo vengano restituiti solo i post presenti nella categoria webdesign.

Come si vede, anche in questo caso abbiamo fatto uso degli stessi parametri della query di cui abbiamo discusso in precedenza, con l’unica differenza che qui il parametro category_name è stato impostato attraverso il metodo set() dell’oggetto $query.

La funzione get_posts()

L’ultima opzione a nostra disposizione per recuperare contenuti dal database di WordPress è data dalla funzione get_posts.

Si tratta di un wrapper per un’istanza di WP_Query che utilizza gli stessi argomenti della classe (con poche eccezioni).

Il Codex avverte che lo scopo di questa funzione è quello di creare degli elenchi di post basati su una serie di parametri. Anche se è possibile utilizzare get_posts per creare Loop secondari, è consigliata per generare liste di post in contesti diversi dal Loop, per i quali risulta preferibile creare una nuova istanza di WP_Query.

La funzione restituisce un array di oggetti $post tramite cui è possibile accedere alle variabili memorizzate nella tabella wp_posts del database:

La tabella wp_posts del database di WordPress

Ecco alcune delle proprietà disponibili:

  • ID
  • post_author
  • post_name
  • post_type
  • post_title
  • post_date
  • post_date_gmt
  • post_content
  • post_excerpt
  • post_status
  • comment_status
  • post_parent
  • post_modified
  • post_modified_gmt
  • comment_count

I valori delle variabili saranno accessibili con la normale sintassi degli oggetti PHP (es. $p->ID).

Per l’elenco competo, si fa rinvio al codice del file wp-includes/class-wp-post.php, disponibile anche nel trac.

Ed ecco, quindi, un esempio di utilizzo della funzione get_posts():

$args = array(
    'category'      => 9,
    'author_name'   => 'carlo'
);
$my_posts = get_posts( $args );

if( ! empty( $my_posts ) ){
    $output = '<ul>';
    foreach ( $my_posts as $p ){
        $output .= '<li><a href="' . get_permalink( $p->ID ) . '">' 
        . $p->post_title . '</a></li>';
    }
    $output .= '<ul>';
}

Il codice qui sopra visualizza un elenco di link agli articoli di un dato autore presenti in una specifica categoria. Invece del ciclo iterativo tipico del Loop, abbiamo iterato tra gli elementi dell’array $my_posts con un ciclo foreach.

Grazie al gran numero di parametri, get_posts permette di ottenere gli stessi dati che si possono ottenere con una nuova istanza di WP_Query, e quindi anche di creare query avanzate basate su coppie chiave/valore di tassonomie personalizzate, meta dati o anche combinazioni di entrambi.

Utilizzare i template tag con get_posts(): setup_postdata() e wp_reset_postdata().

Nei Main Loop di WordPress si fa ampiamente ricorso ai template tag come the_content() e the_permalink() per visualizzare i dati dei post. Tuttavia WordPress ci consente di utilizzare i template tag anche in altri contesti, come nelle query secondarie e nei cicli che iterano tra i risultati restituiti dalla funzione get_posts().

La modifica più importante riguarda la variabile globale $post. Per prima cosa, è necessario aggiungere una dichiarazione che dica a WordPress che stiamo utilizzando questa variabile:

global $post;

Dobbiamo poi aggiungere, all’interno del Loop, la funzione setup_postdata(), che popola l’oggetto $post:

setup_postdata( $post );

L’esempio che segue è tratto dal Codex e conclude la carrellata di esempi di questo lungo articolo:

<ul>
    <?php
    global $post;

    $myposts = get_posts( array(
        'posts_per_page' => 5,
        'offset'         => 1,
        'category'       => 1
    ) );

    if ( $myposts ) :
    foreach ( $myposts as $post ) :
        setup_postdata( $post ); ?>
            <li><a href="<?php the_permalink(); ?>"><?php the_title(); ?></a></li>
        endforeach; 
        wp_reset_postdata();
    endif;
    ?>
</ul>

Un’analisi più approfondita della funzione get_posts, con numerosi esempi di combinazioni di parametri e il codice di un plugin funzionante è disponibile sul blog di Kinsta.

Immagine di Negative Space su Pexels


Commenti

Lascia un commento

Il tuo indirizzo email non sarà pubblicato. I campi obbligatori sono contrassegnati *