Publicado el 17/02/2026 41 visitas KW: xpath xml

XPath básico y avanzado: seleccionar nodos en XML sin volverte loco

Aprende XPath para extraer datos de XML: predicados, atributos, ejes, namespaces y trucos con local-name(). Ejemplos reales.

XPath: el atajo para encontrar “ese dato” dentro de un XML

XPath es un lenguaje de consultas para seleccionar nodos en un documento XML. Si alguna vez te tocó parsear SOAP, leer un sitemap, extraer valores de una factura XML o depurar un feed RSS, XPath puede ser la diferencia entre “2 horas de código” y “2 minutos de consulta”.

Antes de empezar: valida y formatea

XPath asume que el XML está bien formado. Si el documento está roto, la consulta no sirve. Primer paso: valida tu XML en el validador de XML y, si es válido, formatea para leer la estructura con claridad.

La idea base: rutas y nodos

Imagina el XML como un árbol. XPath recorre ese árbol con rutas:

  • / desde la raíz
  • // en cualquier parte
  • @ para atributos

Ejemplo de XML de trabajo

<catalog>
  <book id="bk101">
    <title>XML Developer's Guide</title>
    <author>Matthew Gambardella</author>
    <price currency="USD">44.95</price>
  </book>
  <book id="bk102">
    <title>Midnight Rain</title>
    <author>Kim Ralls</author>
    <price currency="USD">5.95</price>
  </book>
</catalog>

XPath básico (lo que usas el 80% del tiempo)

Seleccionar nodos por nombre

  • Todos los títulos: //title
  • Todos los libros: //book
  • El primer libro: /catalog/book[1]

Filtrar por atributo

Selecciona el libro con id bk102:

//book[@id="bk102"]

Su título:

//book[@id="bk102"]/title

Obtener el valor de un atributo

Moneda del precio del primer libro:

/catalog/book[1]/price/@currency

Predicados y funciones útiles

Contiene texto

//book[contains(title, "Rain")]

Empieza por (prefix)

//book[starts-with(@id, "bk")]

Normalizar espacios

Cuando el XML tiene saltos o espacios raros:

//author[normalize-space()="Kim Ralls"]

XPath en el mundo real: SOAP

En SOAP casi siempre hay namespaces. Un error común es que //Body no devuelve nada. La razón: el nodo real es soap:Body y pertenece a un namespace. Ejemplo:

<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
  <soap:Body>
    <svc:GetStatusResponse xmlns:svc="https://api.ejemplo.com/servicio">
      <svc:status>OK</svc:status>
    </svc:GetStatusResponse>
  </soap:Body>
</soap:Envelope>

XPath correcto (conceptualmente):

/soap:Envelope/soap:Body//svc:status

Para que funcione, tu motor XPath debe tener registrados los namespaces (ver guía de namespaces).

XPath avanzado: ejes (axes)

Los ejes te permiten moverte por el árbol en direcciones específicas:

  • parent:: — ir al padre
  • ancestor:: — ir a ancestros
  • following-sibling:: — hermanos siguientes

Ejemplo: desde un <price> ir al título del mismo libro:

//price[. > 10]/parent::book/title

Patrones muy usados

1) Seleccionar por presencia de nodo

//book[price]

2) Seleccionar por valor numérico

//book[number(price) > 20]

3) Seleccionar el último elemento

//book[last()]

Errores típicos y cómo resolverlos

No devuelve resultados

  • Revisa namespaces (muy común).
  • Revisa mayúsculas/minúsculas: XML es case‑sensitive.
  • Formatea el XML y confirma la ruta real.

Devuelve demasiado

Si usas // sin cuidado, seleccionas nodos en todo el documento. Restringe la ruta desde un contexto más cercano.

Cómo usar XPath en PHP con DOMXPath

<?php
$dom = new DOMDocument();
$dom->loadXML($xml, LIBXML_NONET);
$xp = new DOMXPath($dom);
// $xp->registerNamespace('soap', 'http://schemas.xmlsoap.org/soap/envelope/');
// $xp->registerNamespace('svc', 'https://api.ejemplo.com/servicio');
$nodes = $xp->query('//book[@id="bk102"]/title');
echo $nodes->item(0)->textContent;

FAQ

¿XPath reemplaza a XSD?

No. XSD valida estructura/tipos; XPath extrae datos. Son complementarios.

¿Puedo usar XPath con XML que tiene namespace por defecto?

Sí, pero debes mapear ese namespace a un prefijo en tu motor XPath y usarlo en la consulta.

Conclusión

XPath es una herramienta imprescindible si trabajas con XML. Aprende lo básico (rutas, predicados, atributos) y luego incorpora namespaces y ejes cuando los necesites. Para avanzar más rápido, valida y formatea el XML primero: entender la forma del árbol es la mitad del trabajo.

XPath “sin namespaces”: local-name() como plan B

Cuando recibes XML con namespaces pero tu herramienta XPath no está configurada (o la URI varía), puedes usar una técnica de emergencia: seleccionar por local-name(). Ejemplo, buscar el Body sin importar el prefijo:

//*[local-name()="Body"]

Y el status del ejemplo anterior:

//*[local-name()="status"]

Esto funciona, pero no es lo ideal para producción porque puede devolver falsos positivos si hay elementos con el mismo nombre local en distintos namespaces. Úsalo para depuración rápida, o cuando el contrato es inconsistente.

Recetas rápidas (las que más se usan en integraciones)

1) Extraer todas las URLs de un sitemap

En un sitemap con namespace por defecto, la consulta conceptual sería //sm:loc. Si no quieres lidiar con namespaces en un debug puntual:

//*[local-name()="loc"]/text()

En un motor XPath que soporta devolver texto, esto te da todas las URLs.

2) Obtener títulos de un RSS

//channel/item/title

Si el RSS tiene extensiones con namespaces (por ejemplo content:encoded), tendrás que registrar el namespace correspondiente o recurrir a local-name().

3) Obtener el total de una factura XML

Los XML de facturación varían, pero el patrón es el mismo: localizar un nodo por nombre y navegar hacia el valor. Ejemplo genérico:

//*[local-name()="Total"]

Una vez que lo encuentras, puedes ajustar a una ruta más precisa (por ejemplo dentro de un bloque de Invoice).

XPath y números: cuidado con los tipos

XPath 1.0 (muy común) trata todo como string y convierte “cuando puede”. Para comparar números de forma robusta, usa number():

//price[number(.) > 10]

Si tu precio viene con coma decimal o con moneda, primero hay que normalizar (en esos casos es mejor limpiar el dato en el lenguaje anfitrión).

Cómo depurar una consulta XPath paso a paso

  1. Empieza amplio: usa //*[local-name()="algo"] para ver si el nodo existe.
  2. Restringe el contexto: una vez localizado, construye una ruta desde un ancestro claro.
  3. Añade filtros: predicados por atributo o por texto.
  4. Finalmente, añade namespaces de forma correcta para una solución “limpia”.

Este enfoque evita la frustración del “no devuelve nada” y te obliga a confirmar la estructura real del XML.

Namespaces + XPath: el punto clave

Si vas a trabajar en serio, te conviene dominar namespaces. La regla: si el XML declara namespace por defecto o prefijos, tu XPath debe usar esos namespaces. Tenemos una guía completa aquí: Namespaces en XML: guía práctica.

XPath vs XQuery (rápido y al pie)

XPath es para seleccionar nodos. XQuery es para consultar y transformar XML con más potencia (loops, construcción de documentos, etc.). En integraciones típicas, XPath te alcanza para:

  • Extraer valores puntuales.
  • Validar que existe un nodo.
  • Hacer comprobaciones simples (por ejemplo, “si status = OK”).

Si necesitas transformar documentos enteros, ahí entra XSLT o XQuery, según el stack.

Seguridad y robustez al evaluar XPath

Si tu sistema acepta expresiones XPath “del usuario” (por ejemplo, en una herramienta interna), valida y limita lo que se permite. XPath puede usarse para acceder a partes no esperadas del documento. Y si además el XML proviene de terceros, recuerda desactivar entidades externas para evitar XXE. Son medidas simples que evitan sorpresas.

Ejemplo completo: extraer status y mensaje en SOAP Fault

Muchos servicios devuelven un Fault con detalles. Un patrón típico es buscar si existe Fault y extraer faultstring:

//*[local-name()="Fault"]

Luego:

string(//*[local-name()="faultstring"])

Esto te permite construir mensajes de error más útiles en logs y evitar tickets “sin contexto”.

Conclusión ampliada

XPath no es solo teoría: es una herramienta práctica para integraciones. Si lo aprendes, vas a depurar XML más rápido, escribir menos código y entender mejor contratos SOAP/RSS/sitemaps. Empieza por lo básico, incorpora namespaces y guarda una “caja de recetas” para tus casos frecuentes. Y recuerda: todo empieza con un XML válido y bien formateado.

Más herramientas del día a día

position() y last() para paginar o tomar muestras

Cuando el XML trae listas grandes, puedes seleccionar por posición:

  • Primer elemento: //item[position()=1]
  • Último elemento: //item[last()]
  • Últimos 3: //item[position() > last()-3]

Unión (union) para combinar selecciones

Si quieres títulos de RSS y Atom en una sola consulta (según el documento), puedes unir rutas:

//channel/item/title | //entry/title

Wildcard y “cualquier atributo”

  • Cualquier hijo: /root/*
  • Cualquier atributo: //book/@*
  • Nodos que tienen un atributo: //book[@*]

Rendimiento y estabilidad

XPath es rápido para consultas puntuales, pero si ejecutas cientos de consultas sobre el mismo XML, es mejor:

  • Parsear una sola vez (DOM) y reutilizar el objeto.
  • Evitar consultas con // muy amplias si el documento es enorme.
  • Crear rutas más específicas desde un nodo “ancla” (por ejemplo desde el Body de SOAP).

En sistemas de alto volumen, estas optimizaciones reducen CPU y mejoran latencia de forma visible.

Un consejo final para depurar rápido

Si algo no sale, no te pelees con XPath a ciegas: formatea el XML, identifica el árbol y construye la consulta de menos a más. Esa disciplina te evita el 90% de frustraciones, especialmente con namespaces.

Preguntas frecuentes

¿XPath distingue mayúsculas de minúsculas?

Sí. XML es case‑sensitive. //Title y //title no son lo mismo.

¿Puedo usar XPath para “editar” XML?

XPath selecciona. Para editar necesitas el lenguaje anfitrión (DOM) o tecnologías de transformación como XSLT. Aun así, XPath es el paso previo para encontrar qué editar.

¿Qué versión de XPath se usa normalmente?

Muchos stacks siguen usando XPath 1.0 por compatibilidad, aunque existen XPath 2.0/3.1 con funciones más potentes. Lo importante: aprende bien lo básico, porque es común a todas.

Si estás armando tu “kit” de depuración de APIs, mi recomendación es: validador de XML, validador de JSON, y un par de recetas XPath guardadas. Con eso resuelves la mayoría de incidencias sin depender del proveedor.

Empieza probando tus XML en la herramienta y luego aplica las consultas de este artículo sobre el resultado formateado: verás que todo encaja.

Una vez que lo interiorizas, XML deja de dar miedo.

Y tus tiempos de soporte bajan.

Mucho.

En serio: se nota en tickets.

Autor: Equipo Tecno Inteligente
Especialistas en automatización, desarrollo web y herramientas digitales.