web-dev-qa-db-fra.com

Exclure les publications de la page d'accueil ayant une balise spécifiée

Je suis assez nouveau dans le développement de WordPress et j'essaie d'implémenter ce thème personnalisé qui gère les messages décrits

Comme vous pouvez le voir dans la zone des messages de la page d'accueil, j'ai le sous-domaine Articoli in evidenza qui contient mes messages en vedette et en dessous le Ultimi Articoli sous-domaine contenant les derniers messages.

Pour implémenter ceci, j'utilise le tag posts et dans la zone des posts futurs, je montre les posts ayant la condition tag=featured.

Donc voici mon code:

<section id="blog-posts">

<header class="header-sezione">
        <h2>Articoli in evidenza</h2>
</header>

<?php query_posts('tag=featured');?>
<?php if (have_posts()) : while (have_posts()) : the_post(); ?>
  <div id="featured-posts">

    <h1><a href="<?php the_permalink() ?>"><?php the_title(); ?></a></h1>
      <div class="meta">
Scritto da <span class="author"><?php the_author_link(); ?></span> &nbsp;//&nbsp;  <?php the_category(', ') ?>  &nbsp;//&nbsp;  <?php comments_popup_link('Nessun Commento', '1 Commento ', '% Commenti'); ?> 
      </div>
      <div class="featured-details"><?php the_excerpt()?>
      <?php $featured_img = get_post_meta($post->ID, 'featured_img', $single = true); ?>
      <a href="<?php the_permalink(); ?>"><img src="<?php echo $featured_img ?>" alt="<?php the_title(); ?>" /></a>
      </div>
    </div>

<?php endwhile; ?>
<?php else : ?>
<?php endif; ?>



    <header class="header-sezione">
        <h2>Ultimi Articoli</h2>
    </header>

    <?php
    if (have_posts()) :
        // Start the Loop.
        while (have_posts()) : the_post();

            /*
             * Include the post format-specific template for the content. If you want to
             * use this in a child theme, then include a file called called content-___.php
             * (where ___ is the post format) and that will be used instead.
             */
            get_template_part('content', get_post_format());

        endwhile;
    else :
        // If no content, include the "No posts found" template.
        get_template_part('content', 'none');

    endif;
    ?>

</section>

Comme vous pouvez le voir en premier, je montre les articles ayant un tag featured en utilisant la fonction query-posts():

<?php query_posts('tag=featured');?>

Maintenant, mon problème est que, si une publication a la balise featured, je ne veux pas que celle-ci soit affichée dans la zone de publication la plus récente (à ce stade, elle est affichée). J'ai donc essayé d'utiliser ce code:

<header class="header-sezione">
    <h2>Ultimi Articoli NOT FEATURED</h2>
</header>

<?php query_posts('tag != featured');?>

<?php if (have_posts()) : while (have_posts()) : the_post(); ?>
  <div id="featured-posts">

    <h1><a href="<?php the_permalink() ?>"><?php the_title(); ?></a></h1>
      <div class="meta">
Scritto da <span class="author"><?php the_author_link(); ?></span> &nbsp;//&nbsp;  <?php the_category(', ') ?>  &nbsp;//&nbsp;  <?php comments_popup_link('Nessun Commento', '1 Commento ', '% Commenti'); ?> 
      </div>
      <div class="featured-details"><?php the_excerpt()?>
      <?php $featured_img = get_post_meta($post->ID, 'featured_img', $single = true); ?>
      <a href="<?php the_permalink(); ?>"><img src="<?php echo $featured_img ?>" alt="<?php the_title(); ?>" /></a>
      </div>
    </div>

<?php endwhile; ?>
<?php else : ?>
<?php endif; ?>

Mais cela ne fonctionne pas et les messages en vedette sont toujours affichés sur la page d'accueil. Comme vous pouvez le constater, j'ai essayé de spécifier qu'un post ne peut pas avoir la balise featured:

<?php query_posts('tag != featured');?>

Pourquoi ça ne marche pas? Qu'est-ce que je rate?

1
AndreaNobili

Il y a quelques erreurs que je veux aborder

Tout d’abord, vous ne devriez jamais utiliser query_posts pour créer des requêtes personnalisées. Ce n'est pas seulement mon emphase, mais le codex aussi. Le seul gros problème avec query_posts est que, dans de nombreuses circonstances, la pagination échoue

Remarque: Cette fonction n'est pas destinée à être utilisée par des plugins ou des thèmes. Comme expliqué plus tard, il existe de meilleures options plus performantes pour modifier la requête principale. query_posts () est une façon trop simpliste et problématique de modifier la requête principale d'une page en la remplaçant par une nouvelle instance de la requête. Il est inefficace (ré-exécute les requêtes SQL) et échouera carrément dans certaines circonstances (particulièrement lorsqu'il s'agit de pagination de publications).

Deuxièmement, ne lancez jamais de requêtes inutiles là où cela n’est pas nécessaire. La requête principale peut très facilement être modifiée à l’aide de pre_get_posts , ce qui évite les requêtes inutiles dans la base de données effectuées à l’aide de requêtes personnalisées

Ce raccordement est appelé après la création de l'objet de variable de requête, mais avant l'exécution de la requête.

Troisièmement, si vous n'avez pas le choix et que vous devez exécuter des requêtes personnalisées, faites-le avec WP_Query ou get_posts au lieu de query_posts

En outre, vous abusez des balises php. Il n'est pas nécessaire d'ouvrir et de fermer les balises php après chaque morceau de code, sauf si vous basculez entre php et html. Par exemple

 </div>
    </div>

<?php endwhile; ?>
<?php else : ?>
<?php endif; ?>

</div>

peut être réécrit comme

</div>
    </div>

<?php 
   endwhile;
   else :
   endif;
?>

</div>

Voici comment je vais aborder le problème. Je ne dis pas que c'est la meilleure solution, mais c'est une méthode plus efficace et plus propre pour atteindre votre objectif.

Votre première requête pour votre contenu en vedette devrait ressembler à ceci

<section id="blog-posts">

<header class="header-sezione">
        <h2>Articoli in evidenza</h2>
</header>

<?php 

$featured = new WP_Query('tag=featured');

if ($featured->have_posts()) : 
  while ($featured->have_posts()) : $featured->the_post(); ?>

   <---YOUR LOOP ELEMENTS--->

<?php 
  endwhile; 

  wp_reset_postdata();

endif; 
?>

Votre boucle principale est correcte telle quelle, je ne changerai rien pour cela. NE PAS utiliser une requête personnalisée ici pour exclure une balise. Utilisez pre_get_posts pour le faire. Voici comment

Dans le fichier functions.php, ajoutez le code suivant pour supprimer les publications de la balise sélectionnée de la requête principale de votre page d'accueil. Vous utiliserez la balise conditionnelle is_home() pour cibler la page d'accueil

MODIFIER

J'ai oublié d'inclure ceci. Il est toujours impossible d’inclure une vérification pour vérifier si vous ne vous trouvez pas sur une page d’administrateur (!is_admin()). La raison en est que pre_get_posts modifie la requête principale qui est utilisée à la fois en amont et en aval, ainsi toutes les modifications seront vues en amont et en aval. Vous voulez juste faire des modifications sur le front-end, donc le code modifié sera

function exclude_featured_tag( $query ) {
    if ( !is_admin() && $query->is_home() && $query->is_main_query() ) {
        $query->set( 'tag__not_in', array('ID OF THE FEATURED TAG') );
    }
}
add_action( 'pre_get_posts', 'exclude_featured_tag' );
3
Pieter Goosen
<?php
$args = array(
'posts_per_page' => 5,
'cat' => 2,
'tag__not_in' => array(5), // Assuming 5 is the ID for the tag
'order' => 'asc'
 );

 $query = new WP_Query($args);
 while ($query->have_posts()) :
 $query->the_post();

 ...

  endwhile;
   // don't forget to reset/restore the query
   wp_reset_postdata();

 ?>

assurez-vous que vous devez donner le numéro d'identification de tag à tag_not_in. ne donnez pas le nom de balise à it.it ne fonctionnera pas avec le nom de balise.

1
Zammuuz