XML está por todas partes. A pesar de su molesto uso de corchetes angulares, el formato XML aún se utiliza ampliamente. Archivos de configuración, feeds RSS, archivos de Office (la ‘x’ en el .docx) son solo una lista parcial. Utilizar PowerShell para analizar archivos XML es un paso esencial en tu viaje con PowerShell.
Este tutorial te mostrará cómo analizar archivos XML con PowerShell y validarlos. Esto te guiará desde cero hasta héroe en todos los aspectos de obtener y evaluar datos XML. Se te proporcionarán herramientas que te ayudarán a validar la integridad de los datos XML y detener datos defectuosos justo en la entrada de tus scripts!
Prerrequisitos
Para seguir el material presentado, deberías tener:
- Versión de PowerShell 3.0 o superior. Los ejemplos fueron creados en Windows PowerShell v5.1
- Notepad++, Visual Studio Code u otro editor de texto que entienda XML.
Análisis de Elementos XML de Powershell con Select-Xml
Comencemos cubriendo uno de los métodos más populares y fáciles de usar de PowerShell para analizar XML, y eso es con Select-Xml
. El cmdlet Select-Xml
te permite proporcionar un archivo XML o una cadena junto con un “filtro” conocido como XPath para extraer información específica.
XPath es una cadena de nombres de elementos. Utiliza una sintaxis “similar a un camino” para identificar y navegar por nodos en un documento XML.
Supongamos que tienes un archivo XML con una serie de computadoras y quieres usar PowerShell para analizar este archivo XML. Cada computadora tiene varios elementos como nombre, dirección IP y un elemento Include
para su inclusión en un informe.
Un elemento es una porción XML con una etiqueta de apertura y una etiqueta de cierre, posiblemente con algún texto en medio, como
<Name>SRV-01</Name>
Te gustaría usar PowerShell para analizar este archivo XML y obtener los nombres de las computadoras. Para hacer eso, podrías usar el comando Select-Xml
.
En el archivo anterior, los nombres de las computadoras aparecen en el texto interno (InnerXML) del elemento Name.
InnerXML es el texto entre las etiquetas de los dos elementos.
Para encontrar los nombres de las computadoras, primero proporcionarías el XPath adecuado (/Computadoras/Computadora/Nombre
). Esta sintaxis de XPath devolvería solo los nodos Nombre
bajo los elementos Computadora
. Luego, para obtener solo el InnerXML de cada elemento Nombre
, accederías a la propiedad Node.InnerXML
en cada elemento con un bucle ForEach-Object
.
Uso de PowerShell para analizar atributos XML con Select-Xml
Ahora abordemos este problema de encontrar nombres de computadoras desde un ángulo diferente. Esta vez, en lugar de los descriptores de computadoras representados con elementos XML “, se representan con atributos XML “. `
` Un atributo es una porción de clave/valor, como `
name="SRV-01"
`. Los atributos siempre aparecen dentro de la etiqueta de apertura, justo después del nombre de la etiqueta.`
A continuación se muestra el archivo XML con descriptores de computadoras representados con atributos. Ahora puedes ver cada descriptor como un atributo en lugar de un elemento. `
` Dado que cada descriptor es un atributo esta vez, ajusta un poco el XPath para encontrar solo los elementos de la computadora. Luego, utilizando nuevamente el cmdlet `ForEach-Object
`, encuentra el valor del atributo `name`. `
` Y de hecho, esto también trae los mismos resultados: `SRV-01`, `SRV-02` y `SRV-03 :

` En ambos casos, ya sea que estés leyendo elementos o atributos, la sintaxis de `Select-Xml
` es engorrosa: te obliga a usar el parámetro `XPath
`, luego a pasar el resultado a un bucle y, finalmente, buscar los datos bajo la propiedad `Node`. `
` Afortunadamente, PowerShell ofrece una forma más conveniente e intuitiva de leer archivos XML. PowerShell te permite leer archivos XML y convertirlos en objetos XML “. `
` `Relacionado: Usando Aceleradores de Tipos de Datos de PowerShell para Acelerar la Codificación
`
Otra forma de usar PowerShell para analizar XML es convertir ese XML en objetos. La manera más sencilla de hacer esto es con el acelerador de tipo [xml]
.
Al anteponer los nombres de las variables con [xml]
, PowerShell convierte el XML original en texto plano en objetos con los que luego puedes trabajar.
Lectura de Elementos del Objeto XML
Ahora, tanto las variables $xmlElm
como $xmlAttr
son objetos XML que te permiten hacer referencia a propiedades mediante la notación de punto. Tal vez necesites encontrar la dirección IP de cada elemento de la computadora. Dado que el archivo XML es un objeto, puedes hacerlo simplemente haciendo referencia al elemento IP.
A partir de la versión 3.0 de PowerShell, el objeto XML obtiene el valor del atributo con la misma sintaxis utilizada para leer el texto interno del elemento. Por lo tanto, los valores de las direcciones IP se leen del archivo de atributos con la misma sintaxis que el archivo de elementos.
Lectura de Atributos XML
Usando exactamente la misma notación de punto, puedes leer atributos XML a pesar de las diferencias en la estructura XML.
Y los resultados a continuación muestran que ambos obtuvieron los mismos datos, cada uno de su archivo correspondiente:

Además, con el objeto, una vez que está cargado en la memoria, incluso obtienes IntelliSense para completar automáticamente si estás utilizando PowerShell ISE. Por ejemplo, como se muestra a continuación.

Iteración a Través de Datos XML
Una vez que logras leer archivos XML directamente como objetos XML (aprovechando el acelerador de tipo [xml]
), tienes todo el poder completo de los objetos de PowerShell.
Por ejemplo, supongamos que se requiere recorrer todos los equipos que aparecen en el archivo XML con el atributo include=”true” para verificar su estado de conexión. El siguiente código muestra cómo se puede hacer.
Este script es:
- Leyendo el archivo y convirtiéndolo en un objeto XML.
- Iterando a través de los equipos relevantes para obtener su estado de conexión.
- Finalmente, enviando el objeto de salida del resultado al pipeline.
Y los resultados del script anterior se muestran a continuación:

Esquemas XML
En la sección anterior, viste dos archivos XML diferentes que representan un conjunto de datos de dos formas diferentes. Esas formas se llaman esquemas XML. Un esquema XML define los bloques de construcción legales de un documento XML específico:
- Los nombres de los elementos y atributos que pueden aparecer en ese documento específico.
- El número y orden de los elementos secundarios.
- Los tipos de datos para los elementos y atributos.
El esquema define básicamente la estructura del XML.
Validando datos XML
Un archivo XML puede tener la sintaxis correcta (los editores como Notepad++ se quejarán si no es así), pero sus datos podrían no cumplir con los requisitos del proyecto. Aquí es donde entra el esquema. Cuando dependes de datos XML, debes asegurarte de que todos los datos sean válidos según el esquema definido.
Lo último que quieres es descubrir errores de datos en tiempo de ejecución, 500 líneas en el medio del script. Para ese momento, ya podría haber realizado algunas operaciones irreversibles en el sistema de archivos y el registro.
Entonces, ¿cómo puedes verificar de antemano que los datos son correctos? Veamos primero algunos posibles tipos de errores.
Posibles errores en los datos XML
Hablando en términos generales, los errores encontrados en archivos XML pertenecen a una de dos categorías: errores de metadatos y errores en los propios datos.
Errores de metadatos XML
Este archivo MorePeople.xml a continuación es perfectamente válido en cuanto a la sintaxis. Puedes ver que el archivo tiene un único elemento People (el elemento raíz) con tres elementos Person en su interior. Esta estructura es perfectamente aceptable. Sin embargo, contiene una excepción, ¿puedes verla?
No te preocupes si no lo ves, está simplemente oculta. El problema se encuentra en el primer elemento interno:
Lo que debería haber sido un Country estaba mal escrito, y Canadá se degradó a un County.
Errores en los datos XML
Después de corregir el problema del Country en MorePeople.xml, otro problema se coló:
El metadata, es decir, los elementos y atributos, están bien. Entonces, ¿cuál es el problema? Esta vez, el problema, nuevamente en la primera línea Person , está en uno de los valores. Alguien decidió que yes es un sustituto lo suficientemente bueno para true – pero el código como el siguiente fallará al obtener el primer elemento, ya que está buscando true, no yes:
Creando un Esquema XML
Ahora que conoces los tipos de errores que pueden ocurrir, es hora de mostrar cómo ayuda un archivo de esquema. El primer paso es crear un archivo de datos de ejemplo. El ejemplo puede ser el ejemplo más pequeño y contener solo un elemento interno. Para los ejemplos anteriores, creemos un archivo de muestra como este People.xml:
Ahora construye una función de PowerShell a continuación y úsala con los datos de muestra para crear el esquema .xsd.
Copia la función en tu ISE o tu editor de PowerShell favorito, cárgala en memoria y úsala para crear el esquema. Con la función cargada, el código para crear el esquema es esta única línea:
Los resultados mostrarán la ruta al esquema recién creado:

Usando el Archivo de Esquema para Validar tus Datos
Echa un vistazo a la ubicación especificada por los resultados anteriores. Si el archivo .xsd está allí, estás en el camino correcto para ver la validación en acción. Para el paso de confirmación, usa la función a continuación:
Carga la función en memoria y úsala para validar el archivo MorePeople.xml de los dos ejemplos de errores. Para desencadenar la validación, usa el comando a continuación:
Los resultados reales dependen del contenido de MorePeople.xml.
Veamos dos ejemplos. Ten en cuenta que cuando MorePeople.xml no tiene errores, la función anterior devolverá True
.

Cuando el archivo MorePeople.xml contiene datos incorrectos (la clave Country mal escrita como County), la función devolverá algunos detalles de error y False
.

Como puedes ver, el error especificado en la salida detallada es muy informativo: señala al archivo culpable y señala el componente exacto en el que ocurrió el problema.
Ajuste fino del esquema de validación
Echemos un vistazo al archivo de esquema, luego veamos cómo podemos mejorarlo aún más.
El esquema creado por New-XmlSchema
por defecto es el siguiente:
El esquema predeterminado anterior es bueno, pero no perfecto. De hecho, ha detectado el error tipográfico con el atributo Country. Pero, si dejas el esquema como está, en caso de que otras expectativas que puedas tener no se cumplan, estos problemas no se informarán como errores por la validación Test-XmlBySchema
. Resolvamos esto.
La tabla a continuación presenta algunos casos que no se consideran errores de validación y pasarán desapercibidos para Test-XmlBySchema
. En cada fila, la columna de la derecha muestra cómo cambiar manualmente el esquema para agregar soporte a la protección necesaria.
A modified version of the schema file, with all protections added, is shown right after the table.
Agregar configuración al esquema predeterminado – ejemplos
Required Behavior | Relevant setting on the schema file |
At least one Person element | Set the minOccurs value of the Person element to 1 |
Make Name, Country and IsAdmin attributes mandatory | Add use=”required” to each of these attributes declaration |
Allow only true/false values for IsAdmin | Set type=”xs:boolean” for the IsAdmin declaration |
Allow only Country names between 3 and 40 characters | Use the xs:restriction (see detailed explanation after the schema text) |
Con la restricción booleana en su lugar para el atributo IsAdmin en el ejemplo, su valor debe ser en minúsculas verdadero o falso.
Validación de longitud de cadena con xs:restriction
La validación de longitud de cadena es un poco compleja. Entonces, aunque se muestra arriba como parte del esquema modificado, merece un poco más de atención.
El elemento de esquema original para el atributo Country (después de haber agregado manualmente use=”required”), es el siguiente:
Para agregar la protección de longitud, debe agregar el elemento <xs:simpleType>
, y dentro de él, el <xs:restriction base="xs:string">
. Esta restricción a su vez contiene los límites requeridos declarados en xs:minLength
y en xs:minLength
.
Después de todos estos cambios, la declaración final de xs:attribute
ha pasado de ser una sola línea a un nodo gigante de 8 líneas:
Si tu cabeza no da vueltas después de la explicación anterior, te has ganado el derecho de ver la validación en acción. Para hacerlo, acortemos intencionalmente el valor Canadá a dos sílabas: Ca
Con el nombre corto del país en su lugar, y MorePeople.xml guardado, estás listo para ejecutar el comando de validación a continuación:
y los resultados de hecho muestran que el esquema complejo ha hecho su trabajo:

La validación del esquema XML puede crecer en complejidad y validar casi cualquier patrón que puedas imaginar, especialmente cuando se combina con expresiones regulares.