Como exportar datos de WordPress a CSV o Excel

Como exportar datos de WordPress a CSV o Excel

Última verificación: 13 de octubre de 2026
17 min de lectura
Guía
Desarrollador full-stack

Exportar datos de WordPress no siempre requiere un plugin. Si necesitas posts, usuarios, envíos de formularios o pedidos de WooCommerce en una hoja de cálculo, el método correcto depende del tamaño del dataset, de quién consume el archivo y de con qué frecuencia corre el trabajo.

Usa CSV plano para la mayoría de las exportaciones, transmite filas con fputcsv() para descargas en el navegador, procesa por lotes con WP_Query y pasa a WP-CLI cuando una petición de admin chocaría con límites de memoria o timeout. Usa la REST API cuando otro sistema necesita datos estructurados en lugar de un archivo.

#Cómo exportar WordPress a Excel

Tres enfoques cubren casi todos los trabajos de exportación en WordPress:

  • PHP dentro de WordPress para descargas de admin con comprobación de capacidades
  • WP-CLI para datasets grandes y trabajos programados en el servidor
  • REST API para dashboards, warehouses, CRMs y consumidores headless

Las exportaciones ocasionales y pequeñas encajan bien en una descarga PHP. Tablas recurrentes o muy grandes pertenecen a la CLI. Los sistemas externos deberían tirar JSON por REST y dar forma al CSV fuera de WordPress cuando aún necesiten una hoja.

Empareja el método con el modo de fallo. Las descargas en el navegador fallan por timeout. Los plugins fallan cuando intentan construir un objeto de hoja completo en una sola petición. Los dumps SQL ad hoc fallan cuando los nombres de columna cambian tras actualizar un plugin. Elige el camino que mantenga la exportación reproducible el mes que viene, no solo hoy.

En tiendas españolas que cruzan informes con ContaPlus o con un Excel de finanzas, el patrón que más veces evita el caos del viernes es WP-CLI por la noche y CSV diurno solo para muestras. ¿Necesitas un exportador cableado a tu stack? Habla con un desarrollador WordPress que ya haya enviado exportaciones en producción, o contáctanos.

#Qué exporta Herramientas > Exportar en WordPress

WordPress trae un exportador en el núcleo, pero no genera una hoja de cálculo. Según la documentación de la pantalla Herramientas > Exportar, el archivo descargado es un XML en formato WordPress eXtended RSS (WXR) con entradas, páginas, tipos de contenido personalizados, comentarios, campos personalizados, categorías, etiquetas, taxonomías personalizadas y usuarios. Al elegir entradas o páginas puedes filtrar por categoría, autor, rango de fechas y estado.

Ese archivo está pensado para Herramientas > Importar > WordPress en otra instalación. Excel puede abrir el XML, pero cada entrada arrastra el HTML completo del contenido, los metadatos y los comentarios, así que como hoja de cálculo sirve de poco. Usa WXR para migraciones y copias de contenido. Usa CSV cuando una persona tiene que filtrar, sumar o cruzar columnas.

El mismo WXR sale desde el servidor con wp export. Acepta filtros como --post_type, --start_date y --end_date (formato YYYY-MM-DD), --post_status y --author, corta los archivos a 15 MB por defecto (--max_file_size, con -1 para no limitar) y con --stdout escribe el XML en la salida estándar:

wp export --dir=/tmp/exports/ --post_type=post --start_date=2026-01-01 --end_date=2026-06-30

#CSV o XLSX para exportar datos de WordPress

Empieza por CSV salvo que un stakeholder tenga un requisito duro de .xlsx.

Fortalezas del CSV

  • Fácil de generar con PHP o WP-CLI
  • Fácil de inspeccionar y depurar en un editor de texto
  • Se abre en Excel, Numbers y Google Sheets
  • Evita librerías XLSX y su coste de memoria

Compromisos del XLSX

  • Formato binario con hojas, estilos y cadenas compartidas
  • Necesita una librería como PhpSpreadsheet o un paso de conversión post-exportación
  • Construye más estado en memoria antes de que el archivo esté completo
  • Más difícil de transmitir con seguridad durante una petición HTTP larga

Patrón práctico: exporta CSV desde WordPress y convierte después con Excel, LibreOffice o un script offline pequeño si alguien insiste en XLSX. Así la petición de WordPress se mantiene ligera.

Tip Excel: los CSV UTF-8 a veces necesitan un BOM (\xEF\xBB\xBF) para que Excel en Windows abra bien tildes y eñes. El soporte de Microsoft lo confirma: un CSV en UTF-8 guardado con BOM se abre con doble clic sin problemas. Sin BOM, la vía documentada es Datos > Obtener datos > Desde archivo > Desde texto/CSV, que deja elegir la codificación antes de cargar. Escribe el BOM antes de la fila de encabezado cuando tu audiencia vive en Excel, y omítelo cuando el archivo va a otro script, porque muchos parsers leen esos tres bytes como parte del primer nombre de columna.

#Exportar usuarios de WordPress a CSV con PHP

En herramientas de admin personalizadas, transmite el CSV al navegador. Primero las comprobaciones de capacidad y el nonce. Luego define encabezados, abre php://output, escribe la fila de encabezado y transmite las filas de datos por páginas.

add_action( 'admin_post_wppoland_export_users', 'wppoland_export_users_csv' );

function wppoland_export_users_csv() {
    if ( ! current_user_can( 'manage_options' ) ) {
        wp_die( 'Access denied.' );
    }
    check_admin_referer( 'wppoland_export_users' );

    header( 'Content-Type: text/csv; charset=utf-8' );
    header( 'Content-Disposition: attachment; filename=users-export.csv' );

    $output = fopen( 'php://output', 'w' );
    // BOM opcional para Excel en Windows:
    // fwrite( $output, "\xEF\xBB\xBF" );
    fputcsv( $output, array( 'ID', 'Email', 'Registered' ), ',', '"', '' );

    $page = 1;
    do {
        $users = get_users(
            array(
                'fields'  => array( 'ID', 'user_email', 'user_registered' ),
                'number'  => 500,
                'paged'   => $page,
                'orderby' => 'ID',
                'order'   => 'ASC',
            )
        );

        foreach ( $users as $user ) {
            fputcsv(
                $output,
                array( $user->ID, $user->user_email, $user->user_registered ),
                ',',
                '"',
                ''
            );
        }
        $page++;
    } while ( count( $users ) === 500 );

    fclose( $output );
    exit;
}

Este patrón funciona para exportaciones más pequeñas y herramientas internas de admin. No recopiles todas las filas en un array PHP gigante para luego hacer implode. Transmite cada fila a medida que la obtienes. Una sola llamada a get_users() con number => 500 devolvería solo los primeros 500 usuarios; el bucle con paged recorre el resto en páginas del mismo tamaño.

Protege el endpoint con nonce y comprobación de capacidad. El formulario que lanza la descarga debe incluir wp_nonce_field( 'wppoland_export_users' ) para que check_admin_referer() lo valide. Las exportaciones de usuarios y pedidos suelen contener datos personales, así que trátalas como cualquier otra acción privilegiada de admin bajo reglas al estilo RGPD: registra quién ejecutó la exportación y mantén el archivo fuera de URLs públicas.

#fputcsv en PHP 8.4 y el parámetro escape

Los ejemplos de esta guía pasan cinco argumentos a fputcsv(), y no es capricho. El manual de PHP indica que desde PHP 8.4.0 depender del valor por defecto de escape está obsoleto: hay que pasarlo de forma explícita, por posición o con argumento con nombre. Una exportación que corre en cada cron llenaría el log de avisos de deprecación.

El mismo manual explica que cualquier escape distinto de la cadena vacía puede producir CSV que no cumple RFC 4180 o que no sobrevive a una ida y vuelta por las funciones CSV de PHP. El valor por defecto es la barra invertida, y la recomendación es fijarlo a "". Por eso todas las llamadas usan ',', '"', ''. El manual también avisa de que el valor por defecto cambiará en una versión futura, no antes de PHP 9.0, así que fijarlo hoy evita que la salida cambie sola tras una actualización del servidor.

#Exportar muchos datos de WordPress sin errores de memoria

El modo de fallo habitual es cargar demasiado de una vez. Los límites de memoria de PHP, max_execution_time y los timeouts de reverse proxy matan exportaciones largas en el admin. Procesa por lotes con WP_Query usando posts_per_page y offset, o mejor, pagina con un cursor estable cuando el offset se vuelve caro en tablas grandes.

// $output es el stream abierto como en el ejemplo de usuarios.
$offset = 0;
$limit  = 500;

do {
    $query = new WP_Query(
        array(
            'post_type'              => 'post',
            'post_status'            => 'publish',
            'posts_per_page'         => $limit,
            'offset'                 => $offset,
            'orderby'                => 'ID',
            'order'                  => 'ASC',
            'fields'                 => 'ids',
            'no_found_rows'          => true,
            'update_post_meta_cache' => false,
            'update_post_term_cache' => false,
        )
    );

    foreach ( $query->posts as $post_id ) {
        fputcsv( $output, array( $post_id, get_the_title( $post_id ) ), ',', '"', '' );
    }

    $offset += $limit;
    wp_cache_flush_runtime(); // WP 6.0+: vacía solo la caché en memoria de esta petición
} while ( count( $query->posts ) === $limit );

Por qué ayuda:

  • fields => 'ids' mantiene ligera la hidratación de objetos
  • Desactivar caches de meta y términos evita que el object cache crezca sin límite
  • Tamaños de lote fijos mantienen el pico de memoria cerca de una página de filas
  • Transmitir con fputcsv() evita guardar la cadena CSV completa en RAM
  • Ordenar por ID ascendente evita que una entrada publicada durante la exportación desplace las páginas y duplique o salte filas

Usa wp_cache_flush_runtime() y no wp_cache_flush() dentro del bucle. Con un object cache persistente (Redis o Memcached), wp_cache_flush() vacía la caché de todo el sitio en mitad de la exportación. La función runtime, disponible desde WordPress 6.0, limpia solo la memoria de la petición actual, y si el drop-in no la soporta devuelve false sin tocar la caché compartida.

En tablas muy grandes, el propio offset se vuelve lento porque MySQL aún recorre las filas descartadas. Prefiere keyset pagination: WHERE ID > last_id ORDER BY ID ASC LIMIT N. En trabajos CLI, ese patrón vale el código extra.

Referencia oficial de los argumentos de consulta: la clase WP_Query en developer.wordpress.org.

#Exportar entradas de WordPress a CSV con WP-CLI

Cuando exportas decenas de miles de filas, WP-CLI evita el navegador y la cadena de timeouts del servidor web.

wp post list --post_type=post --fields=ID,post_title,post_date --format=csv > posts.csv

Útil para:

  • catálogos grandes de posts o productos
  • dumps de pedidos WooCommerce que provocarían timeout en wp-admin
  • exportaciones nocturnas vía cron a object storage o una carpeta compartida
  • entregas de migración y reporting

Documentación del comando: wp post list. Acepta --format=csv, json, yaml, ids, count o table, y cualquier argumento de WP_Query como --<campo>=<valor>. Hay un detalle que importa en sitios grandes: --posts_per_page vale -1 por defecto, es decir, todas las entradas en una sola consulta. Si la tabla es enorme, pagina con --posts_per_page=1000 --paged=N en un bucle de shell.

Para usuarios existe el comando equivalente wp user list, con los campos por defecto ID, user_login, display_name, user_email, user_registered y roles:

wp user list --role=customer --fields=ID,user_email,user_registered --format=csv > clientes.csv

Todos los comandos aceptan el parámetro global --ssh=usuario@host/ruta, que ejecuta la exportación contra un servidor remoto desde tu máquina sin abrir una sesión aparte.

También puedes escribir un comando WP-CLI personalizado que abra un fichero, pagine con WC_Order_Query o WP_Query y escriba CSV a disco. Eso mantiene la memoria predecible y permite reanudar desde un checkpoint si el trabajo se interrumpe:

WP_CLI::add_command( 'wppoland export-orders', function ( $args, $assoc_args ) {
    $file = fopen( 'orders.csv', 'w' );
    fputcsv( $file, array( 'order_id', 'date_created', 'status', 'total', 'billing_email' ), ',', '"', '' );

    $page = 1;
    do {
        $orders = wc_get_orders(
            array(
                'type'    => 'shop_order',
                'limit'   => 200,
                'paged'   => $page,
                'orderby' => 'ID',
                'order'   => 'ASC',
            )
        );

        foreach ( $orders as $order ) {
            $created = $order->get_date_created();
            fputcsv(
                $file,
                array(
                    $order->get_id(),
                    $created ? $created->date( 'c' ) : '',
                    $order->get_status(),
                    $order->get_total(),
                    $order->get_billing_email(),
                ),
                ',',
                '"',
                ''
            );
        }
        $page++;
    } while ( count( $orders ) === 200 );

    fclose( $file );
    WP_CLI::success( 'Exported to orders.csv' );
} );

limit y paged son parámetros documentados de wc_get_orders(). Con limit => -1 el comando cargaría todos los pedidos en memoria antes de escribir la primera fila, justo lo que el lote evita.

#Exportar la base de datos completa con wp db export

A veces lo que piden no es una hoja, sino una copia de todo. wp db export ejecuta mysqldump con las credenciales de wp-config.php y escribe un archivo SQL. Con --tables eliges tablas concretas, con --exclude_tables las excluyes y con - como nombre de archivo el volcado sale por la salida estándar:

wp db export - --tables=wp_posts,wp_postmeta | gzip > contenido.sql.gz

Ajusta el prefijo de las tablas al de tu instalación. Un volcado SQL sirve para restaurar o para cargar en otra base de datos, no para abrirlo en Excel. Además incluye la tabla de usuarios con los hashes de contraseñas y, con frecuencia, claves de API que los plugins guardan en wp_options. Trátalo como un secreto: nunca en una carpeta pública, nunca adjunto en un correo.

#Exportar datos de WordPress a un CRM con REST API

Si el consumidor es software, no una persona con Excel, la REST API suele ser más limpia que generar CSV dentro de WordPress.

Casos típicos:

  • sincronizar contenido a un warehouse o herramienta de BI
  • alimentar un CRM desde usuarios o leads
  • front ends headless que necesitan payloads estructurados de posts

Referencia de la colección de posts: endpoint de Posts.

La REST devuelve JSON. Pagina con page y per_page, autentica con Application Passwords o flujos OAuth que tu hosting soporte, y respeta rate limits. Según la guía de paginación, per_page tiene un máximo de 100 registros, y cada respuesta trae las cabeceras X-WP-Total (registros totales) y X-WP-TotalPages (páginas totales). El cliente debe leer X-WP-TotalPages y pedir páginas hasta llegar a ese número, en lugar de adivinar cuándo parar. Construye el CSV aguas abajo si aún hace falta una hoja. Esa división mantiene a WordPress responsable del acceso autorizado y deja el formato del archivo al consumidor.

No expongas rutas privilegiadas de exportación sin autenticación. Trata los endpoints de exportación como cualquier otra superficie de admin adyacente a escritura, aunque solo lean.

#Exportar productos de WooCommerce a CSV sin plugin

Para el catálogo no hace falta código. Según la documentación del importador y exportador CSV de productos, WooCommerce incluye una herramienta propia para importar, exportar y actualizar productos en bloque:

  1. Ve a Productos > Todos los productos y pulsa Exportar en la parte superior.
  2. Elige las columnas o deja la opción de exportar todas.
  3. Filtra por tipos de producto y categorías, o deja ambos en todos.
  4. Marca la casilla de exportar todos los metadatos personalizados si necesitas datos de WooCommerce o de otros plugins. Esas columnas llevan el prefijo meta:.
  5. Pulsa Generar CSV y espera a que el navegador descargue el archivo.

El archivo usa el mismo formato que lee el importador, así que sirve de base para cambios masivos de precios o stock: exportas, editas en la hoja y vuelves a importar. La herramienta cubre el catálogo de productos. Los pedidos quedan fuera, y para ellos aplica la sección siguiente.

#Cómo exportar pedidos de WooCommerce a CSV

Las exportaciones de pedidos parecen simples hasta que las líneas de ítem, los reembolsos y HPOS cambian el cuadro.

Las líneas de ítem no son una sola fila. Un pedido puede tener varios productos, tasas, envíos e impuestos. Decide de antemano si una fila CSV significa un pedido o una línea de ítem. Mezclar ambos sin un esquema claro produce hojas inutilizables.

Meta y campos personalizados explotan el ancho. IDs de pasarela de pago, números de tracking y meta de plugins crean columnas anchas y dispersas. Exporta solo los campos que el informe necesita. Añade un segundo archivo para líneas de ítem si debes mantener ambas formas.

Los backends de almacenamiento diferencian. Posts clásicos shop_order y tablas High-Performance Order Storage (HPOS) no se consultan igual. HPOS es el almacenamiento por defecto desde WooCommerce 8.2, según la documentación de wc_get_orders(). Prefiere el CRUD de WooCommerce (wc_get_orders() / WC_Order_Query) frente a WP_Query crudo sobre shop_order para que el exportador sobreviva a cambios de storage. Para filtrar por fechas, date_created acepta un rango con la forma 2026-01-01...2026-03-31, interpretado en la zona horaria del sitio.

Los filtros de estado importan. Borradores, pagos fallidos, reembolsados y papelera inflan o sesgan informes de ingresos. Documenta qué estados incluyes.

PII y acceso. Los pedidos incluyen nombres, emails y direcciones. Comprobaciones de capacidad (manage_woocommerce o una capacidad personalizada), nonces y logs de auditoría pertenecen a todo exportador de admin. Prefiere WP-CLI para dumps masivos para que el archivo nunca quede en una ruta de uploads alcanzable públicamente.

Rendimiento. Unir todas las claves meta de pedido en un solo SQL parece rápido hasta que la tabla crece. Pagina pedidos, hidrata cada uno con wc_get_order(), escribe la fila y descarta el objeto. Ese patrón es más lento por pedido que un JOIN gigante y mucho más estable bajo límites de memoria.

Moneda y formato. Guarda totales como números simples. Deja que Excel formatee la moneda. Separadores de miles específicos del locale dentro de campos CSV rompen importaciones en otras herramientas.

Campos de fecha. Guarda ISO-8601 o timestamps Unix en el CSV y formatea en la hoja. Cadenas de fecha locales mezcladas (03/04/2026 vs 04/03/2026) causan bugs silenciosos de reordenación cuando el archivo cruza regiones, algo habitual entre equipos en Madrid y clientes en Latinoamérica.

Reembolsos y reembolsos parciales. Decide si los totales reembolsados aparecen como filas negativas, IDs de reembolso separados o totales netos del pedido. Documenta la elección en un README junto al cron de exportación para que finanzas e ingeniería coincidan en la misma hoja.

#Cómo evitar la inyección de fórmulas en un CSV exportado

Un CSV exportado desde WordPress mezcla datos que escribieron tus usuarios: nombres visibles, comentarios, campos de formularios, direcciones de facturación. OWASP describe este riesgo como CSV injection o formula injection: ocurre cuando una web incrusta entradas no confiables en un archivo CSV. Si una celda empieza por =, +, - o @, o por un tabulador, un retorno de carro o un salto de línea, la hoja de cálculo puede interpretarla como fórmula al abrir el archivo.

La mitigación de OWASP es asegurarse de que ninguna celda empiece por esos caracteres, por ejemplo anteponiendo una comilla simple para que el programa la lea como texto:

function wppoland_csv_safe( $value ) {
    $value = (string) $value;
    if ( '' !== $value && in_array( $value[0], array( '=', '+', '-', '@', "\t", "\r", "\n" ), true ) ) {
        return "'" . $value;
    }
    return $value;
}

Aplícalo a las columnas de texto libre, no a los importes calculados por WooCommerce: un total negativo de un reembolso empieza por - y quedaría convertido en texto, lo que rompe las sumas en la hoja.

#Exportar datos personales de un usuario con la herramienta de RGPD

Cuando la petición viene de una persona que ejerce sus derechos, no hace falta un exportador propio. La documentación para desarrolladores de plugins explica que WordPress 4.9.6 añadió una herramienta de exportación de datos personales (Herramientas > Exportar datos personales) pensada para leyes como el RGPD.

La clave de cada exportación es la dirección de email, lo que cubre a usuarios registrados y también a quien solo dejó un comentario. El administrador introduce el nombre de usuario o el email, WordPress envía un enlace de confirmación y, una vez confirmado, el administrador descarga el ZIP o lo envía directamente a la persona. Dentro hay una página HTML índice con los datos agrupados, por ejemplo los comentarios. Los plugins que guardan datos personales propios se enganchan con el filtro wp_privacy_personal_data_exporters para que sus datos aparezcan en el mismo archivo.

#Checklist para exportar datos de WordPress

  1. Prefiere CSV a XLSX dentro de WordPress, y WXR solo para migrar contenido.
  2. Transmite con fputcsv(), escape explícito y comprobaciones de capacidad para descargas pequeñas de admin.
  3. Procesa por lotes con WP_Query o consultas WooCommerce; desactiva caches innecesarios.
  4. Mueve trabajos grandes o programados a WP-CLI.
  5. Usa la REST API cuando otro sistema tira datos estructurados.
  6. En WooCommerce, define el grano de la fila (pedido vs línea de ítem) y usa APIs CRUD para que HPOS no rompa el exportador.
  7. Neutraliza celdas que empiezan por =, +, - o @ en las columnas de texto libre.

Bien hecho, las exportaciones de WordPress se quedan aburridas: columnas predecibles, memoria acotada y sin timeouts sorpresa durante un informe de pico de tráfico.

Siguiente paso

Transforma el artículo en una implementación real

Este bloque refuerza el enlazado interno y lleva al lector al siguiente paso más útil dentro de la arquitectura del sitio.

¿Quieres implementar esto en tu sitio?

Si quieres transformar el artículo en mejoras concretas, rediseño o un plan de implementación, puedo cerrar el alcance y ejecutar.

Cluster relacionado

Explora otros servicios WordPress y base de conocimiento

Refuerza tu negocio con soporte técnico profesional en áreas clave del ecosistema WordPress.

¿Cuál es la forma más segura de exportar datasets grandes de WordPress?#
Para exportaciones muy grandes, WP-CLI suele ser la opción más segura porque evita los límites de ejecución del navegador y te da mejor control sobre memoria y lotes.
¿Debo exportar a CSV o XLSX desde WordPress?#
CSV suele ser el formato más simple y portable. Si alguien necesita Excel de forma específica, exporta CSV primero y ábrelo o conviértelo después.
¿Puedo exportar pedidos de WooCommerce sin un plugin?#
Sí. Puedes exportar pedidos con PHP, WP-CLI, consultas conscientes de WooCommerce o la REST API, según el tamaño del dataset y el control que necesites sobre líneas de ítem y meta.
¿Cómo evito problemas de memoria y timeout durante la exportación?#
Transmite filas en lugar de construir todo en memoria, obtén registros en lotes y mueve exportaciones muy grandes a WP-CLI o trabajos programados en segundo plano.
¿Cuándo debo usar la REST API en lugar de una descarga CSV?#
Usa la REST API cuando otro sistema necesite JSON estructurado bajo demanda o en horario. Usa CSV cuando una persona necesite una hoja de cálculo.

¿Necesitas un FAQ adaptado a tu sector y mercado? Preparamos una versión alineada con tus objetivos de negocio.

Hablemos

Artículos Relacionados