Introducción a JAXB con NetBeans
Hay muchas técnicas de manipular ficheros XML en el mundo Java,
como tratamos
en tutoriales anteriores, y vamos a ver una muy buena opción con JAXB
(Java Architecture for XML Binding )
Antes de hacer un ejemplo con esta tecnología, vamos a montar el Kit de
desarrollo de Web Services, donde viene incluido (utilizaremos este tutorial
como base para otros relacionados con Web Services)
No olvidéis que la primera fuente a consultar siempre, es la original, el
tutorial de Sun.
http://java.sun.com/webservices/docs/1.6/tutorial/doc/index.html
Y que en www.programacion.net se
currar mucho las traducciones (os recomiendo que lo añadáis a vuestras lista de
RSS)
http://www.programacion.com/java/tutorial/jaxb/1
Descarga de WSDP
Lo descargamos del Web de Sun

Y arrancamos el ejecutable

Nos aparece el asistente

Elegimos la máquina virtual (un consejo, evitad los espacios en los trayectos
de instalación)

Elegimos la opción de utilizar un Tomcat como contenedor para nuestra
aplicaciones y servicios Web

Nos descargamos el Tomcat para WSDP

Lo descomprimimos un directorio

Ahora seleccionamos el producto recién instalado

Elegimos el directorio del resto de componentes

Realizamos la instalación típica

Aunque os muestro las opciones en la personalizada….. que ya tenemos
tema para un montón de tutoriales sobre las últimas especificaciones
relacionadas con los servicios web (sobre todo debemos estar atentos a la
evolución de la seguridad)

Definimos el usuario que usuremos para manejar remotamente el Tomcat

No olvidéis que este usuario hay que darlo de alta en el TOMCAT
<!– NOTE: By default, no user is included in the «manager» role required to operate the «/manager» web application. If you wish to use this app, you must define such a user – the username and password are arbitrary. –> <tomcat-users> <user name=»tomcat» password=»tomcat» roles=»tomcat» /> <user name=»role1″ password=»tomcat» roles=»role1″ /> <user name=»both» password=»tomcat» roles=»tomcat,role1″ /> <user name=»admin» password=»admin» roles=»manager,admin» /> </tomcat-users> |
No se os olvide leer las instrucciones finales (lo digo porque al final
hacemos ok, ok, ok y no nos funcionan las cosas)

Copiamos los jar al directorio propuesto

Y ahora acabamos

Y al arrancar sobre los iconos creados ….. no podría dar este
pequeño error… solo tenemos que ir al directorio de binarios de tomcat y
localizar el fichero catalina.bat (actualizando así el acceso directo)

Primer ejemplo de JAXB
Creamos un proyecto dentro de NetBeans 4.1. Será una aplicación Web básica

Elegimos el nombre y trayecto

La gracia está en que a partir de un Schema (esquema) XML podemos crear una
estructura de clases que nos permitan un acceso cómodo y seguro (verificación de
que hacemos lo que debemos en compilación y no en ejecución)
Creamos el esquema

Le damos un nombre (libros.xsd)

<?xml version=»1.0″ encoding=»ISO-8859-1″?>
<xsd:schema xmlns:xsd=»http://www.w3.org/2001/XMLSchema»
targetNamespace=»http://www.adictosaltrabajo.com/esquemas/libro»
xmlns=»http://www.adictosaltrabajo.com/esquemas/libro»
elementFormDefault=»qualified»>
<xsd:element name=»libro»>
<xsd:complexType>
<xsd:sequence>
<xsd:element name=»titulo» type=»xsd:token»/>
<xsd:element name=»autor» type=»xsd:token»/>
</xsd:sequence>
</xsd:complexType>
</xsd:element>
<xsd:element name=»libros» >
<xsd:complexType>
<xsd:sequence>
<xsd:element ref=»libro» maxOccurs=»unbounded» />
</xsd:sequence>
</xsd:complexType>
</xsd:element>
</xsd:schema> |
Creamos un fichero XML que use ese esquema

Decimos que se valide contra un esquema

Y le damos los detalles (el fichero lo llamamos libros.xml)

<?xml version=»1.0″ encoding=»ISO-8859-1″?>
<libros xmlns=’http://www.adictosaltrabajo.com/esquemas/libro’
xmlns:xsi=’http://www.w3.org/2001/XMLSchema-instance’
xsi:schemaLocation=’http://www.adictosaltrabajo.com/esquemas/libro
file:/C:/xml/libros.xsd’>
<libro>
<titulo>El fin de una odisea</titulo>
<autor>Desconocido</autor>
</libro>
<libro>
<titulo>Un lugar en la mente de Kerz</titulo>
<autor>Desconocido</autor>
</libro>
</libros>
|
Bueno, hasta ahora no hemos realizado nada raro …. vamos
con la parte específica
Invocamos fichero xjc.bat pasando como parámetro el
trayecto del fichero xml. También podemos especificar el directorio donde se
generarán las clases
xjc.bat -d directoriofinal ficheros.xsd

Ahora, en nuestro proyecto le vamos a incorporar los JAR de JAXB

Las elegimos

Y pinchando sobre las propiedades del proyecto, añadimos el trayecto de los
ficheros generados automáticamente.

Vemos es aspecto de nuestro proyecto

Y ya solo nos queda escribir el código específico.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73
|
<font size="1" color="#0000FF"> package adictosjaxb; import com.adictosaltrabajo.esquemas.libro.*; import com.adictosaltrabajo.esquemas.libro.impl.*; import javax.xml.bind.*; import java.io.*; import java.util.*; /** * * @author Roberto Canales */ public class <b>Main</b> { public static void depura(String cadena) { System.out.println("adictosjaxb: " + cadena); } public static void <b>main</b>(String[] args) { depura("Empezamos la operación"); try { JAXBContext jc = JAXBContext.newInstance( "com.adictosaltrabajo.esquemas.libro" ); Unmarshaller u = jc.createUnmarshaller(); </font><font size="1"><font color="#009933"> // es una chapuza pero para el ejemplo nos vale </font><font color="#0000FF"> InputStream in = new FileInputStream("c:/xml/libros.xml"); if(in == null) { depura("No encuentro el fichero"); return; } </font><font color="#009933"> // construimos el modelo a partir el stream de entrada </font><font color="#0000FF"> Libros mifichero = (Libros)u.unmarshal( in ); </font><font color="#009933"> // recuperamos la lista de libros </font><font color="#0000FF"> List mislibros = mifichero.getLibro(); int numero = mislibros.size(); depura("El numero de libros es " +numero ); for (int i = 0; i <font color="#009933"> // ahora añadimos un libro nuevo </font><font color="#0000FF"> LibroTypeImpl nuevoLibro = new LibroTypeImpl(); </font><font color="#009933"> // establecemos los elementos </font><font color="#0000FF"> nuevoLibro.setTitulo("Domina tu proyecto"); nuevoLibro.setAutor("Anónimo"); </font><font color="#009933"> // añadimos a la lista </font><font color="#0000FF"> mislibros.add(nuevoLibro); </font><font color="#009933"> // vamos a pintar ahora el arbol XML generado para asegurarnos que se ha añadido </font><font color="#0000FF"> Marshaller formateador = jc.createMarshaller(); formateador.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); formateador.marshal( mifichero, System.out ); </font><font color="#009933"> // ahora escribimos a un fichero, en el correcto juego de caracteres </font></font><font size="1" color="#0000FF"> formateador.setProperty(Marshaller.JAXB_ENCODING, "ISO-8859-1"); FileOutputStream salida = new FileOutputStream("c:/xml/salida.xml"); formateador.marshal( mifichero, salida); } catch(Exception e) // esto es otra chapucilla, no me copieis { depura("el error es " + e.toString()); } } }</font></font> |
|
Analizamos el código
Si lo analizamos, veremos que con 4 líneas, hacemos operaciones comunes…
Recuperar el contenido de un fichero:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
|
<font size="1" color="#0000FF"> JAXBContext jc = JAXBContext.newInstance( "com.adictosaltrabajo.esquemas.libro" ); Unmarshaller u = jc.createUnmarshaller(); </font><font size="1"><font color="#009933"> // es una chapuza pero para el ejemplo nos vale </font><font color="#0000FF"> InputStream in = new FileInputStream("c:/xml/libros.xml"); if(in == null) { depura("No encuentro el fichero"); return; } </font><font color="#009933"> // construimos el modelo a partir el stream de entrada </font><font color="#0000FF"> Libros mifichero = (Libros)u.unmarshal( in ); </font><font color="#009933"> // recuperamos la lista de libros </font><font color="#0000FF"> List mislibros = mifichero.getLibro(); int numero = mislibros.size(); depura("El numero de libros es " +numero ); for (int i = 0; i </font></font> |
|
Insertar un nuevo nodo
|
<font size="1"><font color="#0000FF"> </font><font color="#009933"> // ahora añadimos un libro nuevo </font><font color="#0000FF"> LibroTypeImpl nuevoLibro = new LibroTypeImpl(); </font><font color="#009933"> // establecemos los elementos </font><font color="#0000FF"> nuevoLibro.setTitulo("Domina tu proyecto"); nuevoLibro.setAutor("Anónimo"); </font><font color="#009933"> // añadimos a la lista </font><font color="#0000FF"> mislibros.add(nuevoLibro); </font></font> |
|
Volcar el contenido a la pantalla
|
<font size="1"><font color="#0000FF"> </font><font color="#009933"> // vamos a pintar ahora el arbol XML generado para asegurarnos que se ha añadido </font><font color="#0000FF"> Marshaller formateador = jc.createMarshaller(); formateador.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE); formateador.marshal( mifichero, System.out ); </font><font color="#009933"> </font></font> |
|
Y escribir el contenido en un fichero
|
<font size="1"><font color="#0000FF"> </font><font color="#009933"> // ahora escribimos a un fichero, en el correcto juego de caracteres </font></font><font size="1" color="#0000FF"> formateador.setProperty(Marshaller.JAXB_ENCODING, "ISO-8859-1"); FileOutputStream salida = new FileOutputStream("c:/xml/salida.xml"); formateador.marshal( mifichero, salida);</font> |
|
Conclusiones
La opción de JAXB, junto con JDOM, es una de mis preferidas para manipular de un
modo rápido y sencillo ficheros XML.
De todos modos podemos sacar algunas conclusiones importantes:
- Cada vez hay más técnicas para hacer lo mismo.
- Los conocimientos (aparentemente) cada vez tienen un ciclo de vida más
corto
- No es tan importante el manipular el fichero XML como definir bien su
esquema desde un principio (lo que requiere saber analizar).