en Snippet

Snippet: Entradas relacionadas ordenadas y por múltiples criterios

Uno de los proyectos personales que tengo entre manos es Libros Para Peques donde mi mujer escribe reseñas de los libros que les lee a nuestros hijos. Este blog está montado desde cero tanto en diseño como en programación, salvo diversos plugins que tiene habilitados. Algún día empezaré a contar como se fue programando este blog.

Una de las funcionalidades que aún no tenía implementadas era la de poder ofrecer una lista de libros relacionados con el que estuviéramos leyendo. Aquí no valía usar uno de tantos plugins como hay que te dan entradas relacionadas, ya que existen criterios distintos para poder hacer esa selección.

Por una parte, tenemos libros agrupados (por categoría) por Personaje, para aquellos de los que se ha hablado de un personaje concreto. Posteriormente, tenemos la categoría de Colección, ya que hay libros con distintos personajes pero que pertenecen a la misma colección de libros. Luego podemos relacionarlos por Temática, o por grupo de edad. No podemos usar la búsqueda post__in porque en este caso se busca aquellas entradas que pertenezcan a todas las categorías. Es prácticamente imposible que un libro se parezca a otro en tantas categorías.

Además, en este caso quería que la lista de libros estuviera “ordenada” en el sentido de que preferimos mostrar primero los libros relacionados por Personaje, luego Colección, Temática y por último Grupo de Edad.

Así que, sin buscar más por si ya estuviera hecho, hice un pequeño código que me permitiera obtener una lista de libros relacionados siguiendo esas premisas. El código es el siguiente:

function get_related_books($category_order) {
	global $post;

	// Exclude current post in the query
	$exclude_post = $post->ID;

	// Get category list for this post.
	$post_categories = wp_get_post_categories($post->ID);

	// Temp array
	$result = array();

	// Get the category order desired
	foreach ($category_order as $category) {

		// look for the post categories on the category order from user
		foreach($post_categories as $c){
			// Get the category metadata to get its parent
			$cat = get_category( $c );

			// Has this book a category parent on the desired order list?
			if ($cat->category_parent==$category){
				// Look for a list of related books for the book category (Personajes, Coleccion....)
				// And add it to a result array.

				// Adding using this method to an array permits that I will not have the same book twice in the list
				$result+=get_related_books_by_category($cat->cat_ID,$exclude_post);
			}
		}

	}

	return $result;

}

Este primer método get_related_books ($category_order) recibe un array con los identificadores de las categorías padre a tener en cuenta. En nuestro caso serán Personajes, Colección, Temática, Edad. De cada una de estas categorías cuelgan las que se asignan a cada libro entre otras.

Como véis, lo primero que hacemos es eliminar de la búsqueda el propio libro, ya que si no, nos lo podría devolver la búsqueda. Lo siguiente es obtener la propia lista de categorías de ese libro, para localizar de cual tenemos que buscar un libro relacionado. De esa lista, la tenemos que comparar con la lista de deseados. No todas las categorías de este libro las tendremos en cuenta, sino solo aquellas cuya categoría padre esté en la lista de deseados.

Una vez que localizamos una categoría así, le pasamos la información a otra función que será la encargada de hacer la query a WordPress.

function get_related_books_by_category($cat,$exclude_post) {
	global $post;

	$return = array();

	// Look for the same category, random sort, from this custom post type. 3 books and excluding current book.
	$args = array('cat'=>$cat,'orderby'=>'rand','post_type'=>'book','posts_per_page'=>3,'post__not_in'=>array($exclude_post) );
	$the_query = new WP_Query( $args );

	// The Loop
	while ( $the_query->have_posts() ) : $the_query->the_post();
		$return[$post->ID]=$post->post_title;
	endwhile;

	// Reset Post Data
	wp_reset_postdata();

	return $return;
}

Es autoexplicativo. Una query a WordPress para obtener una lista de 3 libros, por orden aleatorio para la categoría específicada y excluyendo el libro actual.

De la primera función, reseñable que el resultado de las distintas llamadas a get_related_books_by_category se fusionan con el operador +. Esto permite que un mismo libro no aparezca por duplicado en el array. Por tanto, el resultado es una yuxtaposición de las búsquedas de cada categoría.

Para poder ponerlo en el blog, podemos elegir el método que prefiramos. Podremos llamar directamente la función desde el tema:

<div id="related_books">
	<h2>Libros relacionados</h2>
	<div>
		<ul>
			<li>
			<?php $array = get_related_books(array("7","9","6")); ?>
			<?php foreach($array as $book=>$title) {

				if ($i>2) {$i=0; ?>
			</li>
			<li>
			<?php } ?>
			</li>
		</ul>
	</div>
</div>

Simplemente llamamos a la función con un array con los identificadores de categoría padre que queremos tener en cuenta, sabiendo que el orden del array es lo que se tendrá en cuenta.

¿Os ha parecido interesante? Por supuesto soys libres de coger el código, adaptarlo y usarlo como creáis oportuno. Y si crees que hay algo que corregir o mejorar, estaré encantado de saberlo.

Nota: Aún no está habilitado en el blog de Libros para peques porque estamos terminando el diseño de cómo los vamos a mostrar. En breves días estará disponible. Aún así, el código es este mismo

Escribe un comentario

Comentario