Abra o código-fonte do site (Ctrl+U no ambiente de trabalho, ou o menu do navegador em telemóvel). Na secção <head> vai encontrar dezenas de linhas que o tema não escreveu: feeds RSS, manifesto do Windows Live Writer, script de emoji, shortlink ?p=ID, meta generator com a versão do core. Em 2026 a maior parte deste ruído já não serve o produto. Este tutorial mostra o que wp_head() imprime, quais remove_action() são seguros, o que deve ficar intacto, a diferença entre script e estilos de emoji, shortlink versus canonical, e onde colocar o código (mu-plugin ou tema).
O que o wp_head emite
O WordPress não escreve o <head> de uma só vez. O tema chama wp_head() (normalmente em header.php). Essa função dispara o hook wp_head. O core e os plugins registam callbacks com add_action( 'wp_head', ... ). Cada callback imprime HTML, CSS inline ou tags <link> / <meta> / <script>.
Numa instalação limpa, sem SEO plugin agressivo, o inventário típico inclui:
| Callback | Saída habitual | Utilidade em 2026 |
|---|---|---|
feed_links | <link rel="alternate"> para o feed de artigos e o de comentários | Feed de artigos: às vezes; comentários: quase nunca |
feed_links_extra | Feeds de categorias, etiquetas, autores, pesquisas, anexos | Quase sempre ruído |
rsd_link | Really Simple Discovery para publicação remota | Legado |
wlwmanifest_link | Manifesto para Windows Live Writer | Morto desde 2017 |
wp_generator | meta name="generator" com a versão do core | Fuga de informação sem benefício |
print_emoji_detection_script | Script inline e pedido a s.w.org | Navegadores modernos desenham emoji nativamente |
print_emoji_styles | CSS de fallback de emoji | Frequentemente dispensável |
wp_shortlink_wp_head | <link rel="shortlink"> com ?p=ID | O canonical cobre o SEO |
rel_canonical | URL canónica da vista atual | Manter |
adjacent_posts_rel_link_wp_head | rel="prev" / rel="next" entre artigos | Benefício SEO residual |
Além do HTML, wp_shortlink_header pode enviar um cabeçalho HTTP Link com rel=shortlink. Limpar só o HTML e esquecer o cabeçalho HTTP deixa um sinal residual no Network panel.
Caso real de auditoria em loja WooCommerce no Porto: o <head> tinha 14 tags rel="alternate" (categoria, etiqueta, autor) mais o script de emoji a pedir s.w.org. Depois de remove_action seletivo, o HTML encolheu cerca de 3 KB e desapareceram quatro pedidos no primeiro carregamento. O feed principal manteve-se porque a equipa de marketing ainda usava Feedly.
Lista segura de remove_action
A regra prática: remova o que o produto não consome. Não remova o que plugins de SEO, analytics ou pagamentos ainda leem. A lista abaixo é o pacote que uso em sites editoriais e lojas quando não há assinantes de RSS de comentários nem clientes Windows Live Writer.
/**
* Limpeza controlada do head WordPress (WPPoland).
* Preferir mu-plugin; ver secção sobre tema vs mu-plugin.
*/
function wppoland_cleanup_head() {
// Feeds: mantenha feed_links se ainda promover o RSS principal.
remove_action( 'wp_head', 'feed_links', 2 );
remove_action( 'wp_head', 'feed_links_extra', 3 );
add_filter( 'feed_links_show_comments_feed', '__return_false' );
remove_action( 'wp_head', 'wlwmanifest_link' );
remove_action( 'wp_head', 'rsd_link' );
remove_action( 'wp_head', 'wp_generator' );
add_filter( 'the_generator', '__return_empty_string' );
remove_action( 'wp_head', 'print_emoji_detection_script', 7 );
remove_action( 'wp_print_styles', 'print_emoji_styles' );
remove_action( 'admin_print_scripts', 'print_emoji_detection_script' );
remove_action( 'admin_print_styles', 'print_emoji_styles' );
remove_filter( 'wp_mail', 'wp_staticize_emoji_for_email' );
remove_filter( 'the_content_feed', 'wp_staticize_emoji' );
remove_filter( 'comment_text_rss', 'wp_staticize_emoji' );
remove_action( 'wp_head', 'wp_shortlink_wp_head', 10, 0 );
remove_action( 'template_redirect', 'wp_shortlink_header', 11, 0 );
remove_action( 'wp_head', 'adjacent_posts_rel_link_wp_head', 10, 0 );
}
add_action( 'init', 'wppoland_cleanup_head' );Notas de engenharia sobre prioridades: feed_links e feed_links_extra registam-se com prioridades 2 e 3. print_emoji_detection_script usa prioridade 7. Se chamar remove_action sem a prioridade correta, o WordPress não encontra o callback e a tag continua no HTML. Confirme sempre no handbook de remove_action.
Se precisar do feed principal mas quiser cortar só comentários e extras:
add_filter( 'feed_links_show_comments_feed', '__return_false' );
remove_action( 'wp_head', 'feed_links_extra', 3 );
// Não chame remove_action( 'wp_head', 'feed_links', 2 );O que não deve remover
Limpar o head não é apagar tudo o que não reconhece. Estes elementos ficam:
rel_canonical- a URL canónica da página. Sem ela, variantes com query strings, paginação ou parâmetros de tracking competem entre si no índice.- Tags Open Graph / Twitter Card - normalmente injectadas por Yoast, Rank Math ou código próprio. Removê-las partilha social e pré-visualizações.
wp_enqueue_scripts/ estilos e scripts do tema - não passam por estesremove_actionde legado; gerem-se comwp_dequeue_*quando for o caso.- REST API discovery e oEmbed - só remova se tiver uma política explícita de hardening e souber o impacto em Gutenberg e embeds. Fora do âmbito desta limpeza de ruído legado.
- JSON-LD e meta description - vêm de plugins ou do tema; não confundir com
wp_generator.
Num projeto de media em Lisboa, alguém removeu rel_canonical “porque também era um link no head”. Em duas semanas o Search Console mostrou páginas de arquivo com parâmetros UTM a competir com o permalink limpo. O shortlink tinha sido removido corretamente; o erro foi o canónico.
Checklist rápido antes de fazer merge:
- O site ainda precisa de auto-descoberta RSS para podcast ou newsletter? Se sim, preserve
feed_links. - Há ferramenta de publicação remota antiga? Quase nunca;
rsd_linkewlwmanifest_linkpodem sair. - O plugin de SEO já imprime canónico próprio? Mesmo assim, não remova o do core sem confirmar duplicados no View Source.
Scripts de emoji versus estilos de emoji
São dois mecanismos distintos. Tratar só um deixa metade do peso.
print_emoji_detection_script corre em wp_head (prioridade 7) e em admin_print_scripts. Injeta JavaScript que testa se o navegador desenha emoji nativamente. Se falhar, carrega assets a partir de s.w.org. Em Chrome, Firefox, Safari e Edge atuais em Portugal e no resto da UE, o polyfill é desnecessário. O custo real é DNS + TLS para s.w.org, mesmo quando a resposta é pequena.
print_emoji_styles corre em wp_print_styles e admin_print_styles. O CSS ajusta tamanhos e fallbacks. Remover só o script deixa CSS órfão. Remover ambos: os emoji no conteúdo continuam legíveis porque o sistema operativo os desenha como Unicode.
Filtros adicionais (wp_staticize_emoji, wp_staticize_emoji_for_email) convertem emoji em imagens estáticas em feeds e e-mail. Se já cortou o script e o CSS no front, alinhe estes filtros para o comportamento ser consistente.
Quando manter o suporte de emoji do core:
- Público com navegadores muito antigos (intranet corporativa com IE legado - raro em 2026).
- Templates de e-mail HTML que dependem da conversão estática.
- Equipas que auditam o admin e preferem o mesmo comportamento no backend; nesse caso pode remover só no front e deixar
admin_print_*.
Shortlink versus canonical
wp_shortlink_wp_head escreve algo como:
<link rel="shortlink" href="https://exemplo.pt/?p=42" />Em paralelo, wp_shortlink_header envia o cabeçalho HTTP correspondente. Ambos existem por conveniência de ferramentas antigas de partilha. Os motores de busca seguem o canónico, não o shortlink.
rel_canonical aponta para o permalink “bonito”. Shortlink e canónico não se contradizem diretamente, mas dois sinais de URL para o mesmo recurso geram ruído. A combinação correta nesta limpeza: shortlink fora, canónico dentro.
Diferença prática na verificação:
- View Source: procure
rel="shortlink"erel="canonical". - DevTools → Network → cabeçalhos da resposta do documento: procure
Link: <...>; rel=shortlink. - Se o SEO plugin também imprime canónico, confirme que há apenas um
rel="canonical"(ou que são idênticos). Dois canónicos diferentes são piores do que shortlink a mais.
Mu-plugin versus tema
Onde colocar wppoland_cleanup_head muda a durabilidade.
Must-use plugin (wp-content/mu-plugins/wppoland-cleanup-head.php)
- Carrega em todos os pedidos, independentemente do tema ativo.
- Sobrevive a troca de tema filho ou a um redesign.
- Ideal para política de plataforma (agência, multisite, vários clientes com o mesmo baseline).
- Desvantagem: quem só tem acesso ao Customizer não consegue desligar sem FTP ou painel de alojamento.
Tema filho (functions.php)
- Fácil de versionar com o resto do tema.
- Desaparece ou fica órfão se o cliente mudar de tema sem migrar o snippet.
- Adequado para experimentos de um só site ou para clientes que exigem tudo no repositório do tema.
Plugin normal ativável
- Útil se quiser um interruptor na lista de plugins.
- Risco: alguém desativa “para testar” e o head volta a inchir sem aviso.
Recomendação operacional: mu-plugin para a lista estável (RSD, WLW, generator, emoji, shortlink); ajustes finos de feeds no tema ou num plugin de SEO, porque o marketing muda a decisão sobre RSS com mais frequência do que a política de segurança.
Exemplo mínimo de mu-plugin:
<?php
/**
* Plugin Name: WPPoland cleanup head
* Description: Remove ruído legado de wp_head.
* Author: wppoland.com
*/
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
require __DIR__ . '/includes/cleanup-head.php'; // contém wppoland_cleanup_headOu um único ficheiro sem pasta includes, com a função no mesmo PHP. Mu-plugins na raiz de mu-plugins/ carregam automaticamente; subpastas precisam de um loader.
Verificação no View Source
Não confie só no PageSpeed. Confirme o HTML e os cabeçalhos.
- Abra uma página singular e uma página de arquivo (categoria). O inventário de feeds extras muda entre vistas.
- View Source (
Ctrl+U). Procure literais:wlwmanifest,EditURI,generator,wp-emoji,shortlink,alternatecomfeed. - Confirme que
rel="canonical"continua presente e aponta para o permalink esperado. - No DevTools, desative a cache, recarregue, e conte pedidos a
s.w.org/emoji. Depois da limpeza deve ser zero no front. - Inspecione o cabeçalho de resposta: sem
rel=shortlinkse removeuwp_shortlink_header. - Teste o admin numa entrada: se removeu
admin_print_*, o editor também deixa de carregar o script de emoji. Se a redação reclamar, reponha só as ações de admin. - Se usar cache de página (Cloudflare, LiteSpeed, plugin de page cache), limpe a cache depois do deploy. Caso contrário está a auditar HTML antigo.
Sinais de que a prioridade do remove_action está errada: o código está no repositório, mas a tag ainda aparece no source. Corrija a prioridade ou o nome da função, não adicione outro remove_action “por si”.
Sinais de conflito com plugin de SEO: o generator desapareceu, mas aparecem duas tags canónicas. Resolva no plugin (desative o canónico do core ou o do plugin), não com mais remove_action cego.
Impacto esperado e limites
Números honestos, medidos em sites editoriais e lojas médias:
- HTML: menos 2 KB a 5 KB por documento.
- Pedidos: menos 1 a 4 no primeiro carregamento (emoji + feeds descobertos por crawlers de ferramentas).
- JavaScript de emoji: da ordem de 15 KB quando o script e o CSS estavam ativos.
- Tempo: dezenas a poucas centenas de milissegundos no pior caso de cold cache com DNS lento para
s.w.org.
Isto não substitui cache de objeto, imagens AVIF, critical CSS ou revisão de plugins. É higiene de head. Em projetos onde o TTFB já está alto por base de dados, limpar o head melhora a clareza do HTML e remove ruído de auditoria, mas não “salva” o Core Web Vitals sozinho.
Referências do Developer Handbook
Documentação oficial usada neste guia: wp_head, remove_action, feed_links, feed_links_extra, print_emoji_detection_script, print_emoji_styles, wp_shortlink_wp_head, wp_generator, rsd_link, wlwmanifest_link, rel_canonical.
Se precisar de ajuda a aplicar isto num stack com cache e SEO plugin já configurados, fale com um programador WordPress que trate o head como contrato, não como lixo genérico.







