Existem vários tutoriais online de como criar seu próprio tema de WordPress (inclusive, um guia completo aqui na Escola WordPress). Estes guias são ótimos para desenvolver um tema para sites que possuem um número de visitas razoáveis. Mas e quando as visitas diárias atingem os 5 dígitos?

É nesse momento que seu serviço de hospedagem pode reclamar que, mesmo com um serviço de caching ativado (como o W3 Total Cache), seu site está consumindo muito poder de processamento chegando até a deixar o seu site offline. Embora a gente já tenha falado sobre como otimizar a velocidade de carregamento do WordPress, neste artigo vamos falar sobre o que você pode alterar no seu tema para ele ficar mais leve.

Sim, este é um tema completo e funcional!

Vamos tratar do assunto assumindo que você já tenha um conhecimento intermediário de WordPress e não tem medo de editar os arquivos do seu tema. Para sua segurança, recomendo fazer um backup do tema original e testar estas alterações antes de colocar ao vivo. Para testar o seu tema “ao vivo”, procure usar o plugin Theme Teste Drive. Assim, seus visitantes vão continuar vendo o tema “antigo” enquanto você edita e testa o novo.

Estas dicas vão funcionar apenas se você não pretende distribuir o seu tema. Você vai configurar ele para funcionar no seu serviço de hospedagem somente. Estas dicas servem também para quem está criando um tema do zero para uso em seu próprio site.

1. Remova as funções de referência

O WordPress define muitas funções em PHP úteis. Algumas funções, conhecidas como Template Tags, são definidas especialmente para  uso nos temas. Existem também funções relacionadas a ações e filtros, mas são mais usadas no desenvolvimento de plugins – vamos apenas focar nas funções usadas nos temas.

A primeira coisa que vamos fazer é abrir o header.php do tema. De início, já vamos ver muitas linhas similares a estas:

<link rel="shortcut icon" href="<?php bloginfo('template_url'); ?>/favicon.jpg" type="image/x-icon" />
<meta http-equiv="content-type" content="<?php bloginfo('html_type') ?>; charset=<?php bloginfo('charset'); ?>" />
<link rel="stylesheet" type="text/css" media="screen" href="<?php bloginfo('stylesheet_url'); ?>" />
<link rel="alternate" type="application/rss+xml" href="<?php bloginfo('rss2_url'); ?>" />
<link rel="alternate" type="application/rss+xml" href="<?php bloginfo('comments_rss2_url'); ?>" />

Note o <?php bloginfo(‘ ‘) ?>. Isto é uma função de referência, que está buscando a informação no banco de dados do WordPress. Como nosso tema vai estar instalado em um domínio específico, podemos substituir esse código para diminuir as requisições. Seguindo o mesmo exemplo, teremos:

<link rel="shortcut icon" href="http://EXEMPLO.COM/wp-content/themes/SEUTEMA/favicon.jpg" type="image/x-icon" />
<meta http-equiv="content-type" content="text/html; charset=UTF-8" />
<link rel="stylesheet" type="text/css" media="screen" href="http://EXEMPLO.COM/wp-content/themes/SEUTEMA/style.css" />
<link rel="alternate" type="application/rss+xml" href="http://EXEMPLO.COM/feed" />
<link rel="alternate" type="application/rss+xml" href="http://EXEMPLO.COM/comments/feed" />

Ou seja, estamos substituindo a função do bloginfo por endereços fixos. Eliminamos 5 requisições de uma só vez! Uma explicação das funções que existem e o valor que são retornadas:

  • name = Título do seu site
  • description = Descrição do seu site
  • url = Endereço completo da página inicial do seu site (Ex: http://escolawp.com)
  • template_url = Endereço completo do tema do seu site (Ex: http://escolawp.com/wp-content/themes/SEUTEMA)
  • stylesheet_url = Endereço completo da sua folha de estilo CSS do tema (Ex: http://escolawp.com/wp-content/themes/SEUTEMA/style.css)
  • rss2_url = Endereço completo do seu feed RSS (Ex: http://escolawp.com/feed)

E como você pode descobrir qual o endereço correto destes itens? Basta acessar o seu site, ver o código fonte e procurar nas linhas iniciais do seu tema.

Você deve fazer o mesmo com os outros arquivos do seu tema, em especial o index.php, single.php e footer.php.

2. Faça include() manual

Para incluir o header.php, sidebar.php e footer.php no seu tema, geralmente recomenda-se usar as funções existentes do WordPress. Mas no nosso caso, estamos diminuindo ao máximo qualquer tipo de requisição que o WordPress possa fazer ao banco de dados.

Usar o get_header(), get_sidebar() e get_footer() pode parecer mais simples, mas para diminuir a quantidade de requisições, o ideal é fazer um include() manual.

Para isto, você precisa saber o caminho (path) do arquivo para que nenhum erro ocorra. Na maioria dos casos, ele deve ser algo similar a isto:

include('/wp-content/themes/SEUTEMA/header.php');

Basta substituir o SEUTEMA e o nome do arquivo pelo correto (header.php, sidebar.php e footer.php). Não vá esquecer o .php no final!

3. Use sprites

Um sprite nada mais é que uma imagem que contém várias outras dentro dela. Com o uso de CSS, você pode fazer apenas com que uma parte desta imagem apareça. Isto é feito para diminuir a quantidade de imagens que o navegador precisa baixar do servidor.

Talvez você esteja se perguntando: “Mas não fica mais leve se eu tiver 40 imagens em vez de uma?”. Não. Antigamente era normal “recortar” imagens para que o download parecia estar ocorrendo rapidamente, sendo que o olho estava apenas sendo enganado. Cada imagem nova é um HTTP-Request novo. E quanto mais requisições você tiver, menos eficiente seu site será.

Eu costumo criar apenas duas imagens para um blog que necessita ser o mais leve possível: uma é a imagem de fundo e outra é o sprite, que vai conter os ícones de redes sociais, imagens de detalhes e até banners. Assim, o navegador precisa apenas baixar duas imagens e o CSS faz o resto.

Mas nada como uma imagem para explicar melhor:

mídias sociais

No exemplo acima, em vez de criarmos 14 imagens separadas, cada uma contendo um ícone (que seria o equivalente a 14 HTTP-Requests), criamos apenas uma imagem com todos eles juntos.

Assim, para separar essa imagem em blocos menores, vamos usar a função background-position: Xpx Ypx; onde o X equivale a distância do início de nossa imagem até a borda esquerda, e Y a distância da borda de cima até nossa imagem. Como queremos mover nossa imagem para o canto superior esquerdo, vamos usar valores negativos.

Neste exemplo, vamos apenas usar os ícones do Facebook, Twitter e YouTube. Os valores de posição deles ficaria assim:

mídias sociais

E no código CSS, temos isto:

/* Vamos primeiro definir que os links serão em "block". Cada bloco de imagem tem o tamanho de 74x74, e a imagem do sprite é sprite_de_redes.jpg */
a {display:block; width: 74px; height: 74px; background:url('sprite_de_redes.jpg') no-repeat;}

/* Cada link terá uma classe com o nome da rede social, só para entendermos melhor: */
.facebook {background-position: -89px -11px;}
.twitter {background-position: -411px -95px;}
.youtube {background-position: -510px -95px;}

Pode parecer meio complexo e chato de se fazer, mas existe uma solução fácil: o SpriteMe. Ele é um “bookmarklet” que você adiciona ao seu navegador, acessa o seu site e ele pode gerar uma folha de sprite pronta para ser usada.

Mas onde que os sprites não podem ser usados? Não dá para usar em lugares onde a imagem vá se repetir (como é o caso da imagem de fundo). Esse artigo do CSS-Tricks explica detalhadamente sobre sprites, caso você queira se aprofundar no assunto.

4. Diminua a quantidade de arquivos no seu tema

A dica final pode parecer mais difícil do que é, ainda mais quando o tema tem muitas páginas diferentes. Mas vamos supor que sua página inicial é similar a página de single e a página interna. Vamos também supor que sua página de arquivos, tags e categorias sejam iguais, mudando apenas alguns detalhes (como um título no topo te informando o que você está visualizando).

Em vez de ter um arquivo index.php, single.php, page.php, archive.php, category.php e tags.php, podemos reduzir para apenas um: o index.php.

O padrão de página de tema no WordPress é sempre o index.php caso algum dos outros não exista, então podemos nos aproveitar disto. O melhor jeito de explicar como isto funciona é usando um exemplo real, comentado de acordo:

<?php get_header(); ?>
	<!-- Loop padrão do WordPress: -->
	<?php if (have_posts()) : while (have_posts()) : the_post(); ?>		

	<article class="post">
		<!-- Se a página for o category.php, vamos mostrar um aviso no topo informando ao usuário em qual categoria ele está -->
		<?php if (is_category()) { ?>
			<h3>Vendo artigos na categoria: “<?php single_cat_title() ?>”</h3>

		<!-- Se ele estiver vendo os artigos de um determinado mês: -->
		<?php } elseif (is_month()) { ?>
			<h3>Vendo os artigos do mês de “<?php the_time('F Y') ) ?>”</h3>

		<!-- Se ele estiver vendo os artigos de um certo ano: -->
		<?php } elseif (is_year()) { ?>
			<h3>Vendo os artigos do mês de “<?php the_time('Y') ) ?>”</h3>

		<!-- Caso seja uma busca: -->
		<?php } elseif (is_search()) { ?>
			<h3><?php printf(__('Resultado da procura por “%3$s”</strong>.'), get_bloginfo('url'), get_bloginfo('name'), wp_specialchars(get_search_query(), true)); ?></h3>
		<!-- E se for a página de arquivos gerais: -->

		<?php } elseif (isset($_GET['paged']) && !empty($_GET['paged'])) { ?>
			<h3><?php printf(__('Você está vendo os artigos arquivados do blog'), get_bloginfo('url'), get_bloginfo('name')); ?></h3>
	<?php }  ?>

	<!-- Não queremos que a data apareça na page.php, mas queremos que apareça em todas as outras. Então usamos a condicional !is_page() para simbolizar “todas as páginas, exceto o page.php”: -->
	<?php if (!is_page()) { ?> 
		<span class="post-date"><?php the_time('d M Y’); ?></span>
	<?php } ?>

	<!-- Caso o usuário esteja na página inicial, queremos que o título tenha <h2>, mas nas outras, ele deve ter <h1> (por motivos de SEO): -->
	<?php if (is_home()) { ?>
		<h2 class="post-title"><a href="<?php the_permalink(); ?>" title="Link para: <?php the_title(); ?>"><?php the_title(); ?></a></h2>
	<?php } else {	?>
		<h1 class="post-title"><a href="<?php the_permalink(); ?>" title="Link para: <?php the_title(); ?>"><?php the_title(); ?></a></h1>
	<?php } ?> 

<!-- Aqui vai mostrar o conteúdo geral: -->
<div class="post-content">
	<?php the_content('› continue lendo'); ?>
</div><!-- post-content -->

<!-- Queremos que as informações do autor e da categoria apareçam em todas as páginas, exceto o page.php. Novamente, vamos usar a condicional: -->
<?php if (!is_page()) { ?> 
	<div class="post-meta">
		<p class="post-meta-info">Publicado por: <?php the_author(); ?> em <?php the_category(', '); ?></p>
	</div>
<?php } ?> 

<!-- Os comentários vão apenas aparecer no single.php? Então usaremos o seguinte: -->
<?php if(is_single()) { ?>
	<div id="commentarios">
		<?php comments_template(); ?>
	</div>
<?php } ?> 

</article><!-- post -->
<!-- Para finalizar o loop padrão: -->
<?php endwhile; endif; ?>

<?php get_sidebar(); ?>
<?php get_footer(); ?>

Mesmo assim, podemos facilmente remover o get_header, get_sidebar e get_footer e inserir o código deles direto no index.php. Você pode montar um tema inteiro usando apenas o index.php, style.css e functions.php!

Conclusão

A primeira vista, pode parecer que o seu site não mudou em nada. Mas, além do fato de que sites com um carregamento de 100 milisegundos mais rápido garantem um posicionamento melhor no ranking do Google, a quantidade de requisições que seu WordPress deixa de fazer com estas dicas já melhora muito o consumo de processamento do seu servidor.

Menos consumo significa mais up-time, algo importantíssimo para sites de grande acesso.

Abraços!