Muchos freelancers y agencias tratan la sección de portfolio como una galería: “aquí tienes la web de una pizzería, ¿verdad que es bonita?”. Quien contrata no compra una web, compra la solución a un problema. Un portfolio que no muestra el problema, la decisión técnica y el resultado deja al cliente sin la información que necesita para elegirte.
Por qué importa el portfolio de un desarrollador WordPress
Para un desarrollador WordPress, el portfolio es la prueba de que sabes hacer lo que dices, y la forma de enseñar cómo piensas, algo que un CV no transmite. Hay mucha oferta de freelancers de WordPress, así que lo que te distingue es la calidad de lo que enseñas, no el número de proyectos.
Qué busca un cliente en un freelancer WordPress
- Soluciones, no tecnologías: a quien contrata no le importa que uses React, le importa que hayas resuelto su tipo de problema.
- Métricas y resultados: números concretos con fuente, no frases vagas como “mejoré el rendimiento”.
- Proceso de pensamiento: cómo llegaste a la solución y qué alternativas descartaste.
Cómo se escribe un caso de estudio para el portfolio
En lugar de una captura y un enlace, describe el proceso. Un buen portfolio es una colección de casos de estudio, y cada uno responde a tres preguntas.
Desafío: el problema del cliente
No escribas “construí una web”. Escribe el problema específico. Los ejemplos siguientes son ilustrativos, no de proyectos reales:
- “Una tienda con 10 000 productos tardaba 8 segundos en cargar y perdía carritos por el camino.”
- “El sitio consumía un ancho de banda mensual enorme por imágenes sin optimizar.”
- “El cliente perdía conversiones desde el móvil porque la web no era responsive.”
Por qué funciona: quien lee se reconoce en el problema. Si tiene uno parecido, sabe enseguida que entiendes su situación.
Solución: qué hiciste y por qué
Cuenta no solo qué hiciste, sino por qué elegiste esa solución y no otra:
“En lugar de WooCommerce estándar, elegí WordPress headless con Next.js porque el cliente necesitaba:
- un tiempo de carga inferior a 1 s (Core Web Vitals),
- integración con la API externa de su ERP,
- capacidad para escalar a 100 000 productos.
Solución: WordPress como CMS headless, frontend en Next.js, caché Redis y CDN de Cloudflare.”
Así se ve que no copias plantillas, sino que decides con criterio técnico. Conviene añadir también lo que no elegiste y por qué: una frase del tipo “descarté un plugin de caché porque el catálogo cambiaba cada hora” dice más que la lista de herramientas.
Resultado: números con fuente
Es la parte más importante. Muestra el estado antes y después, y di de dónde sale cada cifra:
- Google Analytics: conversiones, tasa de rebote, abandono de carrito.
- PageSpeed Insights (Core Web Vitals): LCP, INP, CLS.
- GTmetrix: tiempo de carga.
- Logs del servidor: transferencia de datos y consultas a la base de datos.
Una cifra sin fuente no sobrevive a la primera pregunta de un cliente técnico. Si no puedes demostrarla, no la publiques.
Ejemplo de caso de estudio con un cliente inventado
Proyecto: tienda online de un fabricante de muebles. Las cifras de este ejemplo son inventadas para ilustrar el formato y no corresponden a un proyecto real.
Desafío. El cliente tenía una tienda WooCommerce con 8 000 productos. La web cargaba en 6 segundos, con tres consecuencias:
- 45 % de abandono de carrito,
- una caída de conversión del 3,2 % al 1,8 % en un año,
- problemas de indexación y Core Web Vitals en rojo.
Solución.
- Migración a WordPress headless: WordPress como CMS y Next.js como frontend.
- Optimización de imágenes: AVIF, carga diferida e imágenes responsive.
- Estrategia de caché: Redis para productos y Cloudflare para los recursos estáticos.
- Optimización de la base de datos: índices y consultas WP_Query.
- CDN con minificación automática de CSS y JS.
Stack: WordPress headless, Next.js, Redis, Cloudflare, API REST de WooCommerce.
Resultado (ilustrativo):
- Tiempo de carga: de 6 s a 0,8 s.
- Conversión: del 1,8 % al 3,9 %.
- Abandono de carrito: del 45 % al 12 %.
- Core Web Vitals: todo en verde.
Un buen caso también indica cuánto duró el proyecto y quién participó, porque da al cliente una idea de escala. Si fue solo tuyo, dilo; si trabajaste con diseño y otro desarrollador, nómbralos por rol.
Qué código enseñar en GitHub
Si buscas trabajo en una empresa de software, el portfolio debe mostrar calidad de código.
Cómo publicar código de proyectos privados
Aunque el proyecto sea privado, puedes crear muestras públicas:
- Fragmentos de proyectos: extrae las piezas mejores y elimina cualquier dato del cliente.
- Contribuciones open source: a WordPress Core o a plugins.
- Proyectos personales: herramientas pequeñas que muestren tus habilidades.
Antes de publicar un fragmento, comprueba que no incluye claves, rutas internas ni nombres del cliente.
1. Hooks personalizados de WordPress
Este ejemplo limita y filtra la consulta principal de una tienda:
/**
* Limitar y filtrar la consulta del catálogo de WooCommerce
*
* @param WP_Query $query
*/
add_action('pre_get_posts', function ($query) {
if (!is_admin() && $query->is_main_query() && is_shop()) {
$query->set('posts_per_page', 24);
$query->set('meta_query', [
[
'key' => '_stock_status',
'value' => 'instock',
'compare' => '=',
],
]);
}
});Demuestra que conoces los hooks de WordPress, que piensas en el rendimiento de la consulta y que documentas el código. Un detalle que cuenta: no añadas no_found_rows en un listado con paginación, porque rompe el cálculo de páginas.
2. PHP moderno (8.1 o superior)
class ProductCache
{
public function __construct(
private Redis $redis,
private int $ttl = 3600
) {}
public function getProductData(int $productId): ?array
{
$cacheKey = "product:{$productId}";
if ($cached = $this->redis->get($cacheKey)) {
return json_decode($cached, true);
}
$product = wc_get_product($productId);
if (!$product) {
return null;
}
$data = ['id' => $productId, 'name' => $product->get_name(), 'price' => $product->get_price()];
$this->redis->setex($cacheKey, $this->ttl, json_encode($data));
return $data;
}
}Enseña propiedades tipadas, promoción de propiedades en el constructor, inyección de dependencias y un patrón de caché. Cachea solo los datos que necesitas, no objetos completos de WooCommerce.
3. Desarrollo de bloques de Gutenberg
import { registerBlockType } from '@wordpress/blocks';
import { useBlockProps } from '@wordpress/block-editor';
registerBlockType('mi-prefijo/portfolio-item', {
edit: ({ attributes }) => {
const blockProps = useBlockProps();
return (
<div {...blockProps}>
<h3>{attributes.title}</h3>
<p>{attributes.description}</p>
</div>
);
},
save: () => null, // Renderizado del lado del servidor
});Muestra conocimiento de la API de bloques, React dentro de WordPress y renderizado en servidor. Para ir más allá, la guía de bloques de Gutenberg, patrones y Full Site Editing detalla cómo estructurarlos.
Qué stack vale la pena mostrar
Imprescindible en 2026:
- Gutenberg (FSE): Full Site Editing y desarrollo de bloques.
- React y Next.js: WordPress headless.
- Composer: gestión de dependencias.
- WP-CLI: automatización y despliegue.
- Docker: entorno local; hay una guía de desarrollo WordPress con Docker.
- Git: control de versiones, y no solo push y pull sino una estrategia de ramas.
Suma puntos: TypeScript, GraphQL, tests (PHPUnit, Jest, Cypress) y CI/CD con GitHub Actions o GitLab CI.
Qué no enseñar en un portfolio de desarrollador
- Proyectos sobre temas listos de ThemeForest, salvo que los hayas personalizado a fondo. En ese caso, enseña qué cambiaste.
- Código sin comentarios, aunque te parezca obvio.
- Prácticas antiguas, como consultas SQL directas en lugar de WP_Query.
- Valores fijos en el código: muestra que usas constantes, filtros y opciones.
Cómo montar el portfolio en WordPress con ACF
No necesitas plugins complejos: WordPress trae lo necesario.
Cómo registrar un custom post type para el portfolio
function mi_tema_registrar_portfolio_cpt() {
register_post_type('portfolio', [
'labels' => [
'name' => 'Portfolio',
'singular_name' => 'Proyecto',
],
'public' => true,
'has_archive' => true,
'supports' => ['title', 'editor', 'thumbnail', 'excerpt'],
'rewrite' => ['slug' => 'portfolio'],
'show_in_rest' => true,
]);
}
add_action('init', 'mi_tema_registrar_portfolio_cpt');Campos ACF para los proyectos del portfolio
acf_add_local_field_group([
'key' => 'portfolio_fields',
'title' => 'Detalles del portfolio',
'fields' => [
['key' => 'client_name', 'name' => 'client_name', 'label' => 'Nombre del cliente', 'type' => 'text'],
['key' => 'project_year', 'name' => 'project_year', 'label' => 'Año del proyecto', 'type' => 'number'],
[
'key' => 'tech_stack',
'name' => 'tech_stack',
'label' => 'Stack tecnológico',
'type' => 'checkbox',
'choices' => [
'wordpress' => 'WordPress',
'react' => 'React',
'nextjs' => 'Next.js',
'woocommerce' => 'WooCommerce',
],
],
[
'key' => 'metrics',
'name' => 'metrics',
'label' => 'Métricas (antes y después)',
'type' => 'repeater',
'sub_fields' => [
['key' => 'metric_name', 'name' => 'metric_name', 'label' => 'Métrica', 'type' => 'text'],
['key' => 'before_value', 'name' => 'before_value', 'label' => 'Antes', 'type' => 'text'],
['key' => 'after_value', 'name' => 'after_value', 'label' => 'Después', 'type' => 'text'],
],
],
],
'location' => [[[
'param' => 'post_type',
'operator' => '==',
'value' => 'portfolio',
]]],
]);Con esto cada proyecto tiene los mismos campos, y puedes mostrar la comparativa antes y después con la misma estructura en todos los casos. Los datos que no quieras que aparezcan en la pantalla de edición, como notas internas o la fuente de cada métrica, guárdalos en campos meta con prefijo de guion bajo (_fuente_metricas): WordPress los oculta del panel de campos personalizados.
Plantilla single-portfolio.php para cada proyecto
// single-portfolio.php
get_header();
?>
<article class="portfolio-case-study">
<header>
<h1><?php the_title(); ?></h1>
<p>
<?php if ($client = get_field('client_name')) : ?>
Cliente: <?php echo esc_html($client); ?>
<?php endif; ?>
Año: <?php echo esc_html(get_field('project_year')); ?>
</p>
</header>
<section class="solution">
<h2>Solución</h2>
<?php the_content(); ?>
</section>
<section class="results">
<h2>Resultados</h2>
<?php foreach ((array) get_field('metrics') as $metric) : ?>
<p>
<?php echo esc_html($metric['metric_name']); ?>:
<?php echo esc_html($metric['before_value']); ?> a
<?php echo esc_html($metric['after_value']); ?>
</p>
<?php endforeach; ?>
</section>
</article>
<?php get_footer();Escapa siempre con esc_html(): el portfolio es código tuyo y se juzga como tal.
Cómo posicionar el portfolio en Google
El portfolio no es solo para personas: Google también lo lee.
Marcado schema.org JSON-LD para el portfolio
function mi_tema_portfolio_schema() {
$schema = [
'@context' => 'https://schema.org',
'@type' => 'CreativeWork',
'name' => get_the_title(),
'description' => get_the_excerpt(),
'creator' => [
'@type' => 'Person',
'name' => 'Tu nombre',
],
'datePublished' => get_the_date('c'),
'url' => get_permalink(),
];
if ($client = get_field('client_name')) {
$schema['sourceOrganization'] = [
'@type' => 'Organization',
'name' => $client,
];
}
return $schema;
}El nombre del cliente solo entra en el marcado si el campo tiene valor, así que un cliente que prefiere el anonimato no aparece ni en la página ni en los datos estructurados.
Cómo optimizar las imágenes del portfolio
- Carga diferida (lazy loading): salvo la primera imagen visible.
- Formatos modernos: WebP o AVIF; la guía de optimización de imágenes en WordPress explica el proceso.
- Imágenes responsive: tamaños distintos según el dispositivo.
- Texto alt descriptivo: “panel de métricas antes y después de la migración”, no “portfolio-imagen-1”.
Qué tienen en común los mejores portfolios
- Métricas concretas: no “mejoré el rendimiento”, sino “el tiempo de carga bajó de 5 s a 0,8 s”, con la fuente.
- Proceso de pensamiento: cómo se llegó a la solución y qué se descartó.
- Código en contexto: no solo un enlace a GitHub, sino la explicación de las decisiones.
- Material visual: diagramas de arquitectura y capturas del antes y el después.
- Opiniones de clientes: una frase firmada por el cliente, con su permiso, pesa más que cualquier adjetivo propio.
Cómo mostrar proyectos privados o con acuerdo de confidencialidad
Muchos de los mejores proyectos no se pueden enseñar tal cual: el código es del cliente o el contrato impide nombrarlo. El caso de estudio sigue siendo posible.
- Nombre del cliente: el campo de ACF es opcional, y el marcado CreativeWork solo añade la organización cuando tiene valor. Describe el sector, por ejemplo “fabricante de muebles”, y deja el nombre vacío.
- Código: extrae fragmentos a un repositorio público. Un hook que optimiza WP_Query o una clase de caché con PHP 8.1 demuestran criterio sin exponer el proyecto.
- Métricas: si no las anotaste durante el trabajo, recupéralas de Google Analytics, PageSpeed Insights, GTmetrix o los logs. Si no hay un dato fiable, describe el desafío y la decisión técnica y no publiques una cifra que no podrías defender delante del cliente.
- Permiso: pregunta qué puedes publicar antes de redactar el caso, no después.
- Archivo propio: conserva las cifras de antes y después, las capturas y la opinión del cliente de cada proyecto en tus archivos, para poder demostrarlas cuando alguien las cuestione.
Un caso sin logotipo, con el problema, la solución y el porqué bien explicados, sigue respondiendo a la pregunta que cuenta: por qué debería el cliente elegirte a ti.
Perfil de WordPress.org como prueba pública de contribución
Un caso de estudio lo escribes tú. El perfil de WordPress.org (profiles.wordpress.org) lo genera la propia plataforma, y por eso un cliente técnico lo lee como un registro independiente. Enlázalo desde el portfolio junto al de GitHub.
Lo que más pesa en ese perfil son las insignias. El manual del equipo Meta distingue dos tipos: las insignias de colaborador, que se asignan en general a cualquiera que haya contribuido a un equipo, y las insignias de equipo, que reciben quienes están activos en él. Cada equipo fija sus propios criterios, y varias se asignan solas:
| Insignia | Cómo se obtiene, según el manual de Meta |
|---|---|
| Core Contributor | Automáticamente, aunque no al instante, al recibir props en un commit de core |
| Plugin Developer | Automáticamente, al tener un plugin en el directorio |
| Theme Developer | Automáticamente, al tener un tema en el directorio |
| WordCamp Speaker | Automáticamente, por el estado de ponente en WordCamp.org, con usuario de WordPress.org |
Las demás las asigna cada equipo a mano. Los criterios varían: el manual del equipo de Openverse, por ejemplo, pide cumplir al menos una de varias condiciones, entre ellas abrir cinco o más issues válidos, conseguir que se fusione un pull request sustancial o traducir 25 cadenas. Una insignia de Plugin Developer no dice si el plugin es bueno, pero sí que pasó una revisión ajena, y eso es más de lo que demuestra una captura.
Qué es Five for the Future y cómo cuenta en un portfolio
Five for the Future nació de una entrada de Matt Mullenweg del 30 de septiembre de 2014. La frase que da nombre al programa dice que las organizaciones que quieren hacer crecer el pastel de WordPress, y no solo su porción, «deberían dedicar el 5 % de su gente a trabajar en algo relacionado con core», sea desarrollo, documentación, seguridad, foros de soporte, revisión de temas, formación, pruebas o traducción (Matt Mullenweg, Five for the Future, traducción propia).
Hoy el programa vive en wordpress.org/five-for-the-future. Pueden comprometerse tanto organizaciones como personas: las organizaciones aparecen en la página de compromisos (pledges), y los colaboradores individuales se muestran con su nombre, una foto, una breve biografía y la organización que los patrocina, si la hay. Para un freelancer, un compromiso de horas semanales con un equipo concreto (Core, Polyglots, Training, Documentation) es una línea verificable en el portfolio. Para una agencia, aparecer en la lista de organizaciones es una forma de demostrar que contribuye al proyecto del que vive.
Cómo publicar un plugin en el directorio de WordPress.org
Un plugin aprobado en el directorio es una muestra de código revisada por terceros y con usuarios reales. El manual de plugins describe el proceso:
- Registrarte en WordPress.org con un correo que revises; si envías en nombre de una empresa, usa un correo oficial de la empresa.
- Enviar una descripción breve y un zip completo del plugin, el mismo que instalarías a mano desde el panel.
- Esperar la revisión: el equipo revisa el código en un plazo de 14 días hábiles y, si encuentra problemas, contacta contigo.
- Tras la aprobación recibes acceso a un repositorio Subversion; el plugin aparece en el directorio cuando subes el código y el readme por SVN.
Dos detalles importan para el portfolio. La URL del plugin no se puede cambiar después del envío, aunque el nombre visible sí. Y cada plugin del directorio tiene un foro de soporte propio, así que tus respuestas a usuarios quedan públicas y forman parte de lo que un cliente puede leer sobre ti.
Las directrices detalladas del directorio son 18. Las que más rechazos explican: licencia GPL o compatible (directriz 1), código mayoritariamente legible por humanos (4), nada de funciones bloqueadas hasta pagar (5), nada de contactar servidores externos sin consentimiento explícito (7) y no usar marcas ajenas como primer término del slug (17). Si tu plugin las cumple, ya tienes un argumento técnico para el caso de estudio.
Perfil de GitHub: README de perfil y repositorios fijados
La documentación de GitHub fija cuatro condiciones para que aparezca un README en tu perfil: un repositorio con el mismo nombre que tu usuario, público, con un archivo README.md en la raíz y con algún contenido. Úsalo como índice: qué haces, enlace al portfolio, enlace al perfil de WordPress.org y los dos o tres repositorios que mejor te representan.
Además puedes fijar en el perfil hasta seis repositorios y gists en total. Fija los que se corresponden con tus casos de estudio, como el plugin del directorio, el repositorio de fragmentos de clientes anonimizados o el tema de bloques, y no los forks sin cambios.
Learn WordPress para cubrir huecos del stack
Si al preparar el portfolio ves que te falta algo de la lista de stack, Learn WordPress organiza su contenido en tres itinerarios (usar, desarrollar y diseñar con WordPress), con cursos, lecciones y talleres en directo. En octubre de 2026 el curso Beginner WordPress Developer figura con 9 horas y 59 lecciones, e Intermediate Theme Developer con 8 horas y 32 lecciones. Un curso terminado no sustituye a un caso de estudio; lo que entra en el portfolio es el bloque o el tema que construyas con lo aprendido.
Por dónde empezar a crear tu portfolio
- Elige 5 a 7 proyectos con un resultado que puedas medir.
- Reúne los datos: métricas con fuente, capturas y, si el cliente lo permite, una frase suya.
- Escribe el primer caso con la estructura desafío, solución y resultado. Calcula unas dos horas.
- Prepara las muestras de código en GitHub, sin datos del cliente y con PHP 8.1 o superior.
- Monta el CPT con ACF y publica los casos con el mismo formato.
- Revisa el código de GitHub cada vez que añadas un proyecto: un repositorio con sintaxis antigua debilita el caso que enlaza a él.
El portfolio no es un CV: cada proyecto debe responder por qué deberían elegirte a ti. Como referencia de un caso publicado con esta estructura, mira el caso de estudio de optimización WooCommerce.







