Exportar datos de WordPress no siempre requiere un plugin. Si necesitas posts, usuarios, envios de formularios o pedidos de WooCommerce en una hoja de calculo, el mejor método depende de cuantos datos tienes y a donde necesita ir la exportacion.
Conoce más sobre el desarrollo WordPress profesional en WPPoland.
Si quieres la versión corta primero, usa CSV plano para la mayoria de las exportaciones, usa fputcsv() cuando construyas una descarga en el navegador con PHP, y cambia a WP-CLI cuando el dataset sea demasiado grande para una solicitud de página de administración normal.
1. Elige el método de exportacion correcto
Hay tres opciones comunes:
- Exportacion PHP dentro de WordPress para descargas controladas solo para administradores
- WP-CLI para datasets grandes y automatizacion del lado del servidor
- REST API para dashboards externos, integraciones o flujos de trabajo headless
Si la exportacion es ocasional y pequeña, una descarga basada en PHP es generalmente suficiente. Si es grande o recurrente, WP-CLI es más seguro y fácil de automatizar.
2. Exportar CSV con PHP
Para exportaciones personalizadas, CSV es el formato más fácil de generar.
function wppoland_exportar_usuarios_csv() {
if ( ! current_user_can( 'manage_options' ) ) {
wp_die( 'Acceso denegado.' );
}
header( 'Content-Type: text/csv; charset=utf-8' );
header( 'Content-Disposition: attachment; filename=usuarios-exportacion.csv' );
$output = fopen( 'php://output', 'w' );
fputcsv( $output, array( 'ID', 'Email', 'Registrado' ) );
$usuarios = get_users(
array(
'fields' => array( 'ID', 'user_email', 'user_registered' ),
'number' => 500,
)
);
foreach ( $usuarios as $usuario ) {
fputcsv(
$output,
array(
$usuario->ID,
$usuario->user_email,
$usuario->user_registered,
)
);
}
fclose( $output );
exit;
}
Esto funciona bien para exportaciones más pequeñas o herramientas internas en el area de administración.
3. Usar procesamiento por lotes para exportaciones más grandes
El error más comun es cargar demasiados datos en memoria a la vez. En su lugar, obtiene filas en lotes.
$offset = 0;
$limite = 500;
do {
$query = new WP_Query(
array(
'post_type' => 'post',
'posts_per_page' => $limite,
'offset' => $offset,
'fields' => 'ids',
)
);
foreach ( $query->posts as $post_id ) {
fputcsv( $output, array( $post_id, get_the_title( $post_id ) ) );
}
$offset += $limite;
} while ( ! empty( $query->posts ) );
El procesamiento por lotes reduce la presion de memoria y ayuda a prevenir timeouts.
Exportacion avanzada con metadatos personalizados
function wppoland_exportar_posts_completo() {
if ( ! current_user_can( 'manage_options' ) ) {
wp_die( 'Acceso denegado.' );
}
header( 'Content-Type: text/csv; charset=utf-8' );
header( 'Content-Disposition: attachment; filename=posts-completo-' . date('Y-m-d') . '.csv' );
$output = fopen( 'php://output', 'w' );
// Encabezados con BOM para compatibilidad con Excel
fprintf( $output, chr(0xEF) . chr(0xBB) . chr(0xBF) );
fputcsv( $output, array(
'ID', 'Título', 'Fecha', 'Estado', 'Autor',
'Categorias', 'Etiquetas', 'URL', 'Extracto'
) );
$offset = 0;
$limite = 200;
do {
$query = new WP_Query( array(
'post_type' => 'post',
'post_status' => 'publish',
'posts_per_page' => $limite,
'offset' => $offset,
) );
foreach ( $query->posts as $post ) {
$categorias = wp_get_post_categories( $post->ID, array( 'fields' => 'names' ) );
$etiquetas = wp_get_post_tags( $post->ID, array( 'fields' => 'names' ) );
fputcsv( $output, array(
$post->ID,
$post->post_title,
$post->post_date,
$post->post_status,
get_the_author_meta( 'display_name', $post->post_author ),
implode( ', ', $categorias ),
implode( ', ', $etiquetas ),
get_permalink( $post->ID ),
wp_trim_words( $post->post_excerpt ?: $post->post_content, 30 ),
) );
}
$offset += $limite;
wp_cache_flush(); // Liberar memoria del cache de objetos
} while ( $query->found_posts > $offset );
fclose( $output );
exit;
}
4. Usar WP-CLI para exportaciones pesadas
Si estas exportando decenas de miles de filas, WP-CLI es generalmente la mejor ruta.
wp post list --post_type=post --fields=ID,post_title,post_date --format=csv > posts.csv
Esto es especialmente útil para:
- exportaciones grandes de pedidos WooCommerce
- exportaciones nocturnas programadas
- tareas de migración y reportes
- flujos de trabajo internos de BI o hojas de calculo
Comandos WP-CLI avanzados para exportacion
# Exportar usuarios con roles específicos
wp user list --role=subscriber --fields=ID,user_email,user_registered --format=csv > suscriptores.csv
# Exportar pedidos de WooCommerce
wp wc shop_order list --format=csv --fields=id,status,total,date_created > pedidos.csv
# Exportar con metadatos personalizados
wp eval '
$query = new WP_Query(array("post_type" => "product", "posts_per_page" => -1));
echo "ID,Título,Precio,Stock\n";
while ($query->have_posts()) {
$query->the_post();
$id = get_the_ID();
printf("%d,\"%s\",%s,%s\n",
$id,
get_the_title(),
get_post_meta($id, "_price", true),
get_post_meta($id, "_stock", true)
);
}
' > productos.csv
Automatizacion con cron del servidor
# Crontab para exportacion nocturna
0 2 * * * cd /var/www/html && wp post list --post_type=post --format=csv > /backups/posts-$(date +\%Y\%m\%d).csv
5. Usar la REST API cuando otro sistema necesita los datos
Si los datos van a otra aplicación en lugar de un humano descargando un archivo, la REST API es generalmente más limpia que generar CSV en WordPress mismo.
Casos tipicos:
- sincronizar datos a un dashboard
- exportar contenido a un warehouse o CRM
- disparar exportaciones estructuradas desde otro servicio
Ejemplo de endpoint personalizado
function wppoland_registrar_endpoint_exportacion() {
register_rest_route( 'wppoland/v1', '/exportar/posts', array(
'methods' => 'GET',
'callback' => 'wppoland_endpoint_exportar_posts',
'permission_callback' => function() {
return current_user_can( 'manage_options' );
},
'args' => array(
'página' => array(
'default' => 1,
'sanitize_callback' => 'absint',
),
'por_página' => array(
'default' => 100,
'sanitize_callback' => 'absint',
),
),
) );
}
add_action( 'rest_api_init', 'wppoland_registrar_endpoint_exportacion' );
function wppoland_endpoint_exportar_posts( $request ) {
$query = new WP_Query( array(
'post_type' => 'post',
'post_status' => 'publish',
'posts_per_page' => $request['por_página'],
'paged' => $request['página'],
) );
$datos = array();
foreach ( $query->posts as $post ) {
$datos[] = array(
'id' => $post->ID,
'título' => $post->post_title,
'fecha' => $post->post_date,
'url' => get_permalink( $post->ID ),
);
}
return new WP_REST_Response( array(
'datos' => $datos,
'total' => $query->found_posts,
'páginas' => $query->max_num_pages,
), 200 );
}
6. CSV vs Excel
La mayoria de las exportaciones de WordPress deberian comenzar como CSV:
- más fácil de generar
- más simple de depurar
- funciona con Excel, Numbers y Google Sheets
- evita librerias XLSX extra y sobrecarga de memoria
Si alguien explicitamente necesita .xlsx, a menudo es mejor convertir el CSV despues de la exportacion en lugar de hacer que WordPress genere un formato de hoja de calculo más pesado directamente.
Tip: BOM para compatibilidad con Excel
Si tus datos contienen caracteres especiales (acentos, ñ, etc.), agrega un BOM (Byte Order Mark) al inicio del archivo:
// Agregar BOM para que Excel interprete UTF-8 correctamente
fprintf( $output, chr(0xEF) . chr(0xBB) . chr(0xBF) );
Sin esto, Excel puede mostrar caracteres corruptos en lugar de acentos.
Resumen
- Usa PHP +
fputcsv()para exportaciones personalizadas más pequeñas. - Usa procesamiento por lotes cuando el dataset crezca.
- Usa WP-CLI para exportaciones grandes o recurrentes.
- Usa la REST API cuando otro sistema necesite datos estructurados.
- Prefiere CSV primero, luego convierte a Excel solo si es necesario.
Necesitas ayuda con exportaciones complejas de datos de WordPress? Nuestro equipo de desarrollo WordPress puede crear soluciones personalizadas. Contactanos.



