Contents
Introducción
En SEO, la etiqueta rel=canonical indica a los motores de búsqueda cuál es la URL canónica (preferida) para una página concreta, evitando problemas de contenido duplicado y consolidando señales de enlace. WordPress añade una canonical por defecto en muchas instalaciones, pero en entornos con contenido personalizado, paginación avanzada, parámetros, taxonomías o búsquedas, a menudo conviene generar y normalizar manualmente la URL canonical mediante PHP.
Objetivos de este tutorial
- Explicar cuándo y por qué añadir una canonical personalizada en WordPress.
- Proveer un ejemplo simple y un ejemplo avanzado (cubriendo singulars, taxonomías, archivos, paginación, attachments y parámetros).
- Mostrar cómo evitar conflictos con plugins SEO (Yoast, Rank Math) y cómo normalizar urls (https, www, trailing slash, parámetros de tracking).
Conceptos clave y buenas prácticas
- Canonical por defecto: WordPress core tiene una función rel_canonical() que se engancha a wp_head. En muchos casos basta con esto, pero cuando necesitas control total conviene reemplazarla.
- Normalización: Decide una única forma de URL (https vs http, www vs no-www, trailing slash) y asegúrate de que la canonical la refleje.
- Paginación: Puedes apuntar la canonical a la propia URL paginada (recomendado por muchos desarrolladores hoy) o al primer volumen lo importante es ser consistente y usar rel=prev/next si corresponde.
- Parametros: Quitar parámetros de tracking (utm_) de la canonical para no crear duplicados.
- Compatibilidad con plugins SEO: No dupliques etiquetas si Yoast/RankMath ya generan la canonical detecta y evita añadir otra.
Lista rápida de funciones útiles de WordPress
| Condición | Función para obtener URL |
|---|---|
| Entrada/Página/CPT | get_permalink() |
| Home / Front page | home_url(/) |
| Archivo de taxonomy | get_term_link() |
| Archivo de post type | get_post_type_archive_link() |
| Autor | get_author_posts_url() |
| Paginas con paginación | get_pagenum_link() |
| Quitar parámetros | remove_query_arg() |
Implementación: Ejemplo simple
Esta primera versión cubre los casos más comunes: singulares, home, taxonomías y autor. También elimina parámetros UTM y normaliza con user_trailingslashit.
ID )
} elseif ( is_front_page() is_home() ) {
canonical = home_url( / )
} elseif ( is_category() is_tag() is_tax() ) {
term = get_queried_object()
canonical = get_term_link( term )
} elseif ( is_author() ) {
author = get_queried_object()
canonical = get_author_posts_url( author->ID )
} else {
// Fallback a la URL actual
canonical = home_url( add_query_arg( NULL, NULL ) )
}
// Quitar parámetros comunes de tracking
canonical = remove_query_arg( array( utm_source, utm_medium, utm_campaign, utm_term, utm_content ), canonical )
// Normalizar trailing slash según la instalación
canonical = user_trailingslashit( canonical )
echo n
}
?>
Notas sobre este ejemplo
- remove_action() evita que WordPress inyecte su canonical por defecto si quieres la tuya.
- La detección de plugins es básica (WPSEO_VERSION para Yoast y la existencia de la clase RankMathPlugin para Rank Math). Si tu plugin SEO es otro, añade su comprobación.
Implementación avanzada: cubrir paginación, attachments, parámetros dinámicos y normalización HTTPS/WWW
El siguiente ejemplo es robusto: maneja paginación (opción para canonical a self o al first page), attachments (canonical a parent o a sí misma si no hay parent), taxonomías, archives de CPT, autor, búsqueda y 404 y normaliza parámetros y esquemas.
post_parent ) {
canonical = get_permalink( post->post_parent )
} else {
canonical = get_permalink( post->ID )
}
} else {
canonical = get_permalink( post->ID )
}
} elseif ( is_front_page() is_home() ) {
canonical = home_url( / )
} elseif ( is_category() is_tag() is_tax() ) {
term = get_queried_object()
canonical = get_term_link( term )
} elseif ( is_post_type_archive() ) {
post_type = get_query_var( post_type )
canonical = get_post_type_archive_link( post_type )
} elseif ( is_author() ) {
author = get_queried_object()
canonical = get_author_posts_url( author->ID )
} elseif ( is_search() ) {
// Opcional: decidir si indexas búsquedas. Frecuente: noindex evitar canonical.
// Si quieres canonicalizar búsquedas a home o a sí misma, ajusta aquí.
return
} else {
// Fallback a la URL actual
canonical = home_url( add_query_arg( NULL, NULL ) )
}
// Paginación: decidir política
paged = get_query_var( paged ) ? intval( get_query_var( paged ) ) : 0
use_self_for_paged = true // si true -> cada página paginada se canonicaliza a sí misma
if ( paged > 1 ) {
if ( use_self_for_paged ) {
canonical = get_pagenum_link( paged )
} else {
// canonical al primer volumen (sin paginación)
if ( is_singular() ) {
canonical = get_permalink()
} else {
// para archives usa la versión sin paged
canonical = remove_query_arg( paged, canonical )
}
}
}
// Quitar parámetros de tracking y algunos parámetros innecesarios
canonical = remove_query_arg( array( utm_source, utm_medium, utm_campaign, utm_term, utm_content, fbclid ), canonical )
// Forzar https y/o no-www si tu sitio está configurado así. Ejemplo: forzar scheme y host de home_url()
home = parse_url( home_url( / ) )
parsed = wp_parse_url( canonical )
if ( isset( home[scheme] ) isset( home[host] ) ) {
parsed[scheme] = home[scheme]
parsed[host] = home[host]
}
// Reconstruir la URL normalizada
norm = ( isset( parsed[scheme] ) ? parsed[scheme] . :// : ) .
( isset( parsed[host] ) ? parsed[host] : ) .
( isset( parsed[path] ) ? parsed[path] : ) .
( isset( parsed[query] ) ? ? . parsed[query] : ) .
( isset( parsed[fragment] ) ? # . parsed[fragment] : )
// Aplicar trailing slash según la configuración de WP
norm = user_trailingslashit( norm )
echo n
}
?>
Explicaciones importantes del ejemplo avanzado
- get_pagenum_link() devuelve la URL correcta para páginas paginadas y respeta la estructura de enlaces permanentes.
- remove_query_arg() elimina parámetros de tracking que no aportan significado al contenido.
- El bloque que fuerza scheme/host al valor de home_url() evita inconsistencias entre http/https o www/no-www en la canonical.
- La variable use_self_for_paged te permite elegir la estrategia de paginación la documentación de Google ha variado con el tiempo, pero lo más importante es ser consistente y no generar duplicados.
Compatibilidad con plugins SEO
Si tu sitio usa Yoast SEO, Rank Math u otros plugins, normalmente éstos ya generan la etiqueta canonical (y añaden otras metaetiquetas importantes). Recomendación:
- Comprobar si el plugin ya añade canonical. Si es así, no añadir una segunda etiqueta para evitar duplicados.
- Si el plugin lo genera pero quieres customizar sólo ciertos casos, detecta la presencia del plugin y aplica tu lógica sólo cuando sea necesario.
- Para Yoast puedes comprobar defined(WPSEO_VERSION) o la existencia de funciones/clases propias. Para Rank Math, la existencia de la clase RankMathPlugin.
Pruebas y verificación
- Inspeccionar el código fuente en el front (ctrl U) y comprobar que sólo hay una etiqueta rel=canonical y que su href coincide con la URL normalizada deseada.
- Probar tipos de páginas: home, posts, páginas, attachments, categorías, etiquetas, taxonomías personalizadas, archivos de post type, autor, búsqueda, 404, y páginas paginadas.
- Verificar con la Google Search Console (inspección de URLs) y herramientas de crawling (Screaming Frog, Sitebulb) que las canonicales se leen correctamente.
- Comprobar redirecciones y versiones www/no-www y https para que la canonical coincida con la versión que devuelve 200 y no con la que redirige.
Errores y problemas comunes
- Añadir múltiples canonicales (core plugin tu código). Evitar duplicados detectando plugins o no llamando a remove_action si confías en Core/plugin.
- Canonical que apunta a la página 1 desde todas las páginas paginadas, provocando pérdida de indexación de contenido paginado si no se usa rel=prev/next correctamente.
- Dejar parámetros de tracking en la canonical (utm_, fbclid) creando URLs distintas para el mismo contenido.
- Canonical a una URL que devuelve redirección en lugar de 200 — siempre canonicalizar a la URL final (200).
Resumen / Checklist de implementación
- Decide si usarás la canonical que genera WordPress core, un plugin SEO o tu propio código.
- Si implementas tu propia canonical, elimina la que no quieras (remove_action) para evitar duplicados.
- Gestiona casos: singular, attachment, taxonomy, author, archives y paginación.
- Quita parámetros de tracking y normaliza esquema/host/trailing-slash.
- Comprueba compatibilidad con Yoast/RankMath antes de inyectar tu etiqueta.
- Verifica con herramientas y Google Search Console.
Enlaces útiles
Conclusión
Implementar una etiqueta rel=canonical correcta en WordPress con PHP requiere entender los distintos tipos de página, decidir una política de normalización (scheme/host/trailing slash) y manejar paginación y parámetros. Con los ejemplos provistos (simple y avanzado) tienes una base sólida para personalizar la canonical según las necesidades de tu proyecto y evitar problemas de contenido duplicado. Aplica las comprobaciones de plugins SEO, prueba en todas las plantillas y verifica en Search Console para asegurarte de que Google entiende la URL preferida.
|
|
Acepto donaciones de BAT's mediante el navegador Brave 🙂 |
