Ver índice
Empezando con XML

        Ocultar índice  

   Índice de contenidos
   Instalación en Windows
   Instalación en Ubuntu
   Servidores seguros
   Páginas dinámicas
   Sintaxis básica
   Operaciones
   Arrays
   Formatos de presentación
   Operadores
   Bucles
   Extraer y ord. información
   Funciones
   Ficheros externos
   Imágenes dinámicas
   Gestión de directorios
   Cookies y sesiones
   Clases y objetos
   Ficheros en formato PDF
   Bases de datos MySQL
   PHP y XML
   PDO - Bases SQLite / MySQL
   MySQL a traves de misqli
   Algo de JavaScript y AJAX


XML

XML son las siglas de eXtensible Markup Language (lenguaje de marcas extensible) que es un metalenguaje que nos permite definir lenguajes de marcado acordes a nuestras necesidades. Se trata básicamente de poder definir nuestras propias etiquetas (marcas) para establecer una estructura destinada al almacenamiento de datos. La libertad de establecimiento de nuestra estructura de marcas está únicamente limitada al cumplimiento de las normas del metalenguaje XML.

Los primeros pasos en XML

Los documentos XML deben tener como extensión xml y es muy aconsejable que estén codificados en en formato UNICODE. Nosotros, tal como detallamos en los ejemplos, vamos a guardar todos los documentos XML con codificación UTF-8. De esta forma estaremos evitando los problemas que nos han surgido en el primero de los ejemplos que incluimos un poco más adelante.

Todo documento XML debe comenzar con un prólogo de tipo:

<?xml version="1.0" ?>

Como puedes ver se utiliza una sintaxis muy próxima a la de PHP (<?php y ?>) esta vez con un xml obligatorio y situado inmediatamente detrás de <?. Cuando usamos la configuración short_open_tag=off (descrita aquí) estaremos diferenciando claramente las etiquetas php (<?php) de las XML que comienzan por <?xml.

Respecto al atributo version se le asigna el valor 1.0 ya que esta es la única versión existente hasta el momento. Esta primera línea de los documentos XML, conocida como prólogo, puede incluir otros atributos que comentaremos más adelante. Si creáramos un documento con esa única línea, la visualización sería la que puedes ver pulsando aquí.

Como puedes observar el mensaje de error se produce porque un documento XML ha de tener obligatoriamente un cuerpo formado por un único elemento (elemento raíz definido por una etiqueta de apertura y otra de cierre) que será que vaya a contener a todos los demás elementos que puedan incluirse en el documento.

Dicho de otra forma, los documentos XML han de incluir, a continuación de la línea prólogo, una etiqueta del tipo <nombre_etiqueta> y han de acabar con </nombre_etiqueta> pudiendo ser nombre_etiqueta cualquier palabra que cumpla la especificación XML 1.0 que establece que «un nombre empieza con una letra o uno o más signos de puntuación, y continúa con letras, dígitos, guiones, rayas, dos puntos o puntos, denominados de forma global como caracteres de nombre. Los nombres que empiezan con la cadena "xml" se reservan para la estandarización de esta o de futuras versiones de esta especificación».

Debemos tener muy presente que los nombres de las etiquetas o marcas son sensibles a mayúsculas y minúsculas. La estructura de un documento XML recuerda mucho los bucles anidados (siempre uno dentro del otro) y/o la interpretación matemática de las estructuras delimitadas por paréntesis, corchetes y/o llaves.

Cada elemento XML –delimitado por sus etiquetas de apertura y cierre– puede tener como contenido más elementos, cadenas de caracteres, ambas cosas, o carecer de contenido (elemento vacío).

Líneas de comentario

las líneas de comentario tienen una sintaxis idéntica a la utilizada para el mismo fin en la edición HTML. Todo comentario comienza con <!-- y acaba con -->

Etiquetas con atributos

De forma similar al HTML en las marcas (de apertura) XML pueden incluirse los atributos que se desee siempre que se utilice la siguiente sintaxis:

<marca atributo="valor" >
ó
<marca atributo='valor' >

siendo en este caso obligatorio que los valores vayan entre comillas (simples o dobles). Dentro de una misma etiqueta podemos incluir tantos atributos como deseemos y, de igual forma que en aquellas, también a los atributos podemos asignarles el nombre que deseemos.

Caracteres especiales

Puede ocurrir que los textos que pretendamos introducir dentro de un elemento requieran el uso de caracteres especiales que puedieran provocar conflictos con los utilizados para delimitar etiquetas y/o valores de los atributos. En XML existen entidades que pueden utilizarse para que esos caracteres sean interpretados como texto y no como elementos de marcado. Son estos:

Entidad Caracter
&amp; &
&lt; <
&gt; >
&apos; '
&quot; "

Otra forma de incluir información que contenga caracteres especiales puede ser esta:

<![CDATA[ caracteres raros ]]>

donde pueden incluirse cualesquiera caracteres con la excepción de la cadena ]]> que se confundiría con el cierre del bloque CDATA.

Documentos XML bien formados

Los documentos denominados bien formados (well formed en inglés) son aquellos que cumplen con todas las definiciones básicas de formato y pueden, por lo tanto, analizarse correctamente por cualquier parser (analizador sintáctico) que cumpla con la norma. Por el momento nos bastará con comprobar que los documentos estén bien formados y saber que bien formado y válido son cosas distintas y que un documento bien formado puede no ser válido o viceversa.

El sitio World Wide Web Consortium (W3C) dispone de un servicio que permite comprobar la buena formación de un documento XML.





En las imágenes podemos ver los resultados de la comprobación de un fichero. En la primera de la ventanas elegimos la opción Validate by Direct Imput, pegamos el contenido de nuestro documento el área del texto del formulario, pulsamos el botón check y obtenemos el resultado de la validación y los eventuales mensajes de error o advertencia.

El documento XML más simple

Este es el ejemplo más simple de un documento bien formado en XML. Ambos ejemplos tienen el contenido que puedes ver en el código fuente. Si los compruebas pulsando los enlaces podrás observar que se comportan de forma diferente. El primero nos da un error mientras que el segundo parece correcto.

<?xml version="1.0" ?>
<!-- Aquí los comentarios se ponen así -->
<cuerpo>
Lo minimo minimorum
</cuerpo>
ejemplo471.xml ejemplo472.xml

El origen del problema, en este caso, son los caracteres con tilde. El primer documento ha sido elaborado utilizando el Notepad++ y guardando con el formato por defecto (ANSI) de este editor. El segundo documento es el resultado de abrir el documento anterior con el bloc de notas de Windows y guardarlo sin modificar su contenido utilizando la opción de codificación UTF-8 tal como puedes ver en la imagen.



Habríamos obtenido igual resultado si al crear un archivo nuevo en Notepad++ hubiéramos elegido la opción UTF-8 tal como puedes ver en esta imagen.

Otros ejemplos

<?xml version="1.0" ?>
<!-- Todo el contenido ha de ir dentro de esta etiqueta -->
<ContieneTodo>
<!-- La parte1 contiene información en forma de texto -->
    <parte1>
        Estos son los datos de la parte1
    </parte1>
<!-- Dentro de la parte2 incluiremos dos nuevas etiquetas con sus datos -->
    <parte2>
        Aqui pueden ir datos y también nuevas etiquetas
        <parte2_1>
           Incluimos más datos, ahora en la parte 2_1
        </parte2_1>
        Fuera de la parte 2_1 podemos añadir datos
        <parte2_2>
           Una nueva etiqueta y nuevos datos
        </parte2_2>
    </parte2>
    <!-- Aqui incluimos apertura y cierre en la misma etiqueta
     es una etiqueta vacía -->
    <parte3 />
</ContieneTodo>
ejemplo473.xml
  ¡Cuidado!  

Recuerda que los nombres de las etiquetas son sensibles a mayúsculas/minúsculas por lo tanto < /contieneTodo> no cerraría < ContieneTodo>

Tampoco debes olvidarte de guardar los documentos xml con codificación UTF-8.

Un ejemplo algo más completo de XML

<?xml version="1.0" ?>
<!-- Después de prólogo incluimos la etiqueta
     de apertura del elemento raiz (cuerpo_del_XML) que será
     el que contenga todo y que se cerrará al final del documento -->
<cuerpo_del_XML>
     <!-- Establecemos un elemento (alumnos) que va a contener
           los datos de todos los alumnos (lo marcamos en magenta) -->
<alumnos>
     <!-- dentro de la etiqueta alumno (podremos poner cuantas queramos)
          incluimos inforamcion relativa a el. En este caso ponemos su
          número de orden como caracter y, además, dentro de etiquetas
           contenedoras los datos nombre, apellidos, sexo y
           comentarios relativos a cada uno de ellos -->
    <alumno> 1
         <nombre>Juan</nombre>
         <apellidos>Fernández Gómez</apellidos>
         <sexo>Varón</sexo>
         <comentarios/>
    </alumno>
    <!-- En este caso incluiremos una entidad para representar
            el símbolo menor que en la etiqueta de comentarios -->
    <alumno> 2
        <nombre>Luisa</nombre>
        <apellidos>García Bermúdez</apellidos>
        <sexo>Hembra</sexo>
        <comentarios>Es la &lt; de 17 hermanos</comentarios>
    </alumno>
</alumnos>
     <!-- Establecemos un elemento (profes) que va a contener
           los datos de los profesores (lo marcamos en magenta) -->
<profes>
     <!-- El número de orden y el sexo de los profesores los
         insertamos ahora como atributos del elemento profe.
         Es una opción alternativa a la usada en el caso de los alumnos -->
    <profe sexo="Varon" numero="1">
        <nombre>Alejandro</nombre>
        <apellidos>Iglesias Fernández</apellidos>
        <comentarios></comentarios>
    </profe>
    <!-- Los comentarios relativos a esta profesora
        los incluimos usando CDATA para evitar posibles conflictos
        con los caracteres especiales -->
    <profe sexo="Hembra" numero="2">
        <nombre>Liliana</nombre>
        <apellidos>Fernández de Arriba</apellidos>
        <comentarios> 
        <![CDATA[ Es la < de los ^profes^ y "profas" ]]>
        </comentarios>
    </profe>
</profes>
        <!-- incluimos un nuevo elemento padres que, por el momento,
        dejamos vacío -->
<padres>
</padres>
</cuerpo_del_XML>
ejemplo474.xml

Exportación de tablas MySQL a ficheros XML

No es infrecuente que se plantee la necesidad de intercambiar información entre dos formatos de almacenamiento. En los ejemplos siguientes hemos descrito el proceso de lectura de tablas MySQL y su transformación en ficheros con formato XML.

En este primer ejemplo hemos hecho la transformación considerando que cada campo de la tabla fuera convertido en un elemento del fichero XML

<?php
/* establecemos una conexión con la base de datos ejemplos de MySQL */
$base="ejemplos";
$tabla="demo4";
$conexion=mysql_connect("localhost","pepe","pepa");
mysql_select_db($base,$conexion);
/*leemos todos los campos de la tabla y todos los registros */
$resultado= mysql_query("SELECT * FROM $tabla" ,$conexion);
/* inicializamos una variable con la primera etiqueta obligatoria de los ficheros
   xml. Ponemos \n para incluir un salto de línea */
$xml= "<?xml version=\"1.0\" ?>\n";
/* ponemos la etiqueta de apertura del elemento raiz. En este caso le asignamos
el nombre de la tabla aunque podríamos ponerle cualquier otro nombre y lo
agregamos alla variable que recogerá toda la información */
$xml.= "<".$tabla.">\n";
/* leemos todas la filas del resultado filtrando aquellos elementos de array asociativo
serán precisamente esos indices los que utilizaremos para asignar nombre a los elementos
hijos del array */
while ($registro = mysql_fetch_array($resultado,MYSQL_ASSOC)){
        /* cada registro será un elemento xml. Le pondremos como nombre usuario aunque
         podríamos ponerles cualquier otro nombre y lo agregamos a la variable que recogerá todo*/
        $xml.= "<usuario>\n";
        /* leemos el buche de los resultado y vamos añadiendo etiquetas de apertura con el mismo
           nombre que el índice asociativo, con el valor contenido en el array (codificado utf8
           para evitar problemas de lectura del xml y después ponemos la etiqueta de cierre
           con el mismo nombre que la de apertura) */
        foreach($registro  as $indice=>$valor){
                    $xml.=  "<".$indice.">".utf8_encode($valor)."</".$indice.">\n";
        }
        /* leido el registro completo añadimos la etiqueta de cierre del usuario */
        $xml.= "</usuario>\n";
}
/* añadimos la etiqueta de cierre del elemento raiz */
$xml.= "</".$tabla.">\n";
/* cerramos la conexión con la base de datos */
mysql_close();
/* escribimos el contenido de la variable que recoge toda la información en
   un fichero xml y colocamos un enlace para poder visualizarlo en el navegador */
  if (file_put_contents("demo4.xml",$xml)){
         print '<a href="demo4.xml">Ver el fichero demo4.xml que acaba de crearse</a>';
   }else{
         print "El fichero demo4.xml no ha podido crearse. Ha habido un error";
}

?>
Crear fichero XML

Este otro ejemplo es una modificación del anterior. En este caso hemos optado por convertir uno de los campos de la tabla en atributo de uno de los elementos del fichero XML.

<?php
/* establecemos una conexión con la base de datos ejemplos de MySQL */
$base="ejemplos";
$tabla="demo4";
$conexion=mysql_connect("localhost","pepe","pepa");
mysql_select_db($base,$conexion);
/*leemos todos los campos de la tabla y todos los registros */
$resultado= mysql_query("SELECT * FROM $tabla" ,$conexion);
/* inicializamos una variable con la primera etiqueta obligatoria de los ficheros
   xml. Ponemos \n para incluir un salto de línea */
$xml= "<?xml version=\"1.0\" ?>\n";
/* ponemos la etiqueta de apertura del elemento raiz. En este caso le asignamos
el nombre de la tabla aunque podríamos ponerle cualquier otro nombre y lo
agregamos alla variable que recogerá toda la información */
$xml.= "<".$tabla.">\n";
/* leemos todas la filas del resultado filtrando aquellos elementos de array asociativo
serán precisamente esos indices los que utilizaremos para asignar nombre a los elementos
hijos del array */
while ($registro = mysql_fetch_array($resultado,MYSQL_ASSOC)){
        /* cada registro será un elemento xml. Le pondremos como nombre usuario  e incluiremos
        ahora el Sexo como atributo en la etiqueta usuario asignando como valor el contenido
        de el elemento del mismo nombre del array resultante de la lectura de la tabla*/
        $xml.= "<usuario Sexo='".$registro['Sexo']. "' >\n";
        /* leemos el buche de los resultado y vamos añadiendo etiquetas de apertura con el mismo
           nombre que el índice asociativo, con el valor contenido en el array (codificado utf8
           para evitar problemas de lectura del xml y después ponemos la etiqueta de cierre
           con el mismo nombre que la de apertura
           Excluimos el de indice Sexo que ya ha sido incluido como atributo del usuario */
        foreach($registro  as $indice=>$valor){
          if ($indice !='Sexo'){
                    $xml.=  "<".$indice.">".utf8_encode($valor)."</".$indice.">\n";
                    }
        }
        /* leido el registro completo añadimos la etiqueta de cierre del usuario */
        $xml.= "</usuario>\n";
}
/* añadimos la etiqueta de cierre del elemento raiz */
$xml.= "</".$tabla.">\n";
/* cerramos la conexión con la base de datos */
mysql_close();
/* escribimos el contenido de la variable que recoge toda la información en
   un fichero xml y colocamos un enlace para poder visualizarlo en el navegador */
  if (file_put_contents("demo4_1.xml",$xml)){
         print '<a href="demo4_1.xml">Ver el fichero demo4_1.xml que acaba de crearse</a>';
   }else{
         print "El fichero demo4_1.xml no ha podido crearse. Ha habido un error";
}

?>
Crear fichero XML