You are on page 1of 14

Conexión a un AS/400 (iSeries) desde JDBC

Conexión a un AS/400 (iSeries) desde JDBC

Un proyecto de i+D para wTul Informática S.L. por Fernando Guillén,


con la colaboración de Javier Prieto y Jose Carlos Segui.

wTul: http://www.wtul.com

Fernando Guillén: http://www.fernandoguillen.info

21 de Marzo de 2008

1
Conexión a un AS/400 (iSeries) desde JDBC

Contenidos
Conexión a un AS/400 (iSeries) desde JDBC...................................................................................... 1
Los dos drivers que pueden hacer el trabajo....................................................................................3
DB2 Universal JDBC Driver...................................................................................................... 3
Ejemplo de conexión.............................................................................................................. 3
IBM ToolBox para Java.............................................................................................................. 4
Ejemplo de conexión.............................................................................................................. 4
Utilidad Ping...........................................................................................................................4
Prueba para insert into............................................................................................................ 5
Lugar oficial de desarrollo y descarga....................................................................................5
Documentación................................................................................................................................ 6
Preparación del AS/400................................................................................................................... 6
Requerimientos del AS/400 para funcionar con IBM Toolbox para java................................... 6
Acciones realizadas en el AS400 de wTul.................................................................................. 7
Problemas de conexión con el AS400..............................................................................................8
Configurando todo para trabajar desde Hibernate........................................................................... 9
hibernate.cfg.xml........................................................................................................................ 9
Problemas con Hibernate............................................................................................................ 9
Error SQL7008....................................................................................................................... 9
Intento de recrear el PreparedStatement desde JDBC..................................................... 10
Solución:.......................................................................................................................... 10
Activación de los diarios.............................................................................................10
Solución rápida:............................................................................................................... 11
Aplicación de prueba java-db2...................................................................................................... 11
Configuración y ejecución de los tests...................................................................................... 11
Configuración y despliegue de la aplicación web.....................................................................12
Aplicación de pruebas online.................................................................................................... 13
Conclusiones.................................................................................................................................. 14

2
Conexión a un AS/400 (iSeries) desde JDBC

Los dos drivers que pueden hacer el trabajo


DB2 Universal JDBC Driver

Con este driver no he tenido problemas para conectar a una Base de Datos DB2 corriendo
en un servidor Linux.

Pero para conectar a un AS/400 este driver requiere un fichero de licencia que nos ha
resultado imposible encontrar.

El error:

La versión del controlador IBM Universal JDBC utilizada carece de


licencia para la conectividad con las bases de datos QAS.
Para conectarse con este servidor debe obtener una copia de licencia del
controlador IBM DB2 Universal para JDBC y SQLJ.
Debe instalarse en la vía de acceso de clase de aplicación un archivo de
licencia db2jcc_license_*.jar adecuado a la plataforma de este destino.
La conectividad con las bases de datos QAS puede habilitarse mediante uno
de los siguientes archivos de licencia: [ db2jcc_license_cisuz.jar ].
ERRORCODE=-4472, SQLSTATE=42968
Este fichero se supone que se encuentra en el producto DB2 Connect pero hemos
revisado los CDs que había en las oficinas de Wtul y no lo hemos encontrado, incluso
hemos instalado el producto y no hemos encontrado el fichero en todo lo que el producto
instala.

IBM dice que se encuentra ahí: http://www-1.ibm.com/support/docview.wss?uid=swg21191319

Ejemplo de conexión

public Connection getConnectionIBMUniversalDriver(


String username,
String password,
String ipServer,
String Database
) throws SQLException{
DriverManager.registerDriver( new com.ibm.db2.jcc.DB2Driver() );
Connection connection = null;
String urlConnection = "jdbc:db2://" + ipServer + "/" + Database;
connection = DriverManager.getConnection( urlConnection, username, password );
return connection;
}

3
Conexión a un AS/400 (iSeries) desde JDBC

IBM ToolBox para Java

Este es el driver más recomendado y sobre el que existe más documentación y


comunidad.

Es también conocido por JTOpen.

Es el recomendado de IBM.

Ejemplo de conexión

public Connection getConnectionAS400Driver(


String username,
String password,
String ipServer,
String Database
) throws SQLException{
DriverManager.registerDriver(new
com.ibm.as400.access.AS400JDBCDriver());
Connection connection = null;
String urlConnection = "jdbc:as400://" + ipServer + "/" + Database;
connection = DriverManager.getConnection( urlConnection, username, password );
return connection;
}

Utilidad Ping

Este Driver tiene una curiosa utilidad para comprobar si en la ip que le indicas hay un
AS/400 con su DB2 escuchando:
public Connection ToolBoxPing(
String ipServer
) throws SQLException{
AS400JPing pingObj = new AS400JPing( IpServer , AS400.COMMAND, false);
if (pingObj.ping()) {
System.out.println("SUCCESS");
} else {
System.out.println("FAILED");
}
}

Podemos ampliar esta utilidad con un montón de tests:


public static void main(String[] args) {
String ipServer = "217.127.196.233";

//
// cargamos hash con todos los servicios a ejecutar.
//
HashMap<String , Integer> servicios = new HashMap<String, Integer>();

4
Conexión a un AS/400 (iSeries) desde JDBC

servicios.put( "AS400.FILE", new Integer( AS400.FILE ) );


servicios.put( "AS400.DATABASE", new Integer( AS400.DATABASE ) );
servicios.put( "AS400.COMMAND", new Integer( AS400.COMMAND ) );
servicios.put( "AS400.SIGNON", new Integer( AS400.SIGNON ) );
servicios.put( "AS400.CENTRAL", new Integer( AS400.CENTRAL ) );
servicios.put( "AS400.DATAQUEUE", new Integer( AS400.DATAQUEUE ) );
servicios.put( "AS400.RECORDACCESS", new Integer( AS400.RECORDACCESS )
);
servicios.put( "AS400.PRINT", new Integer( AS400.PRINT ) );

//
// iniciamos objeto AS400Ping
//
AS400JPing pingObj = new AS400JPing( ipServer );

//
// ejecuto pings
//
Set<String> keys = servicios.keySet();
for (Iterator iter = keys.iterator(); iter.hasNext(); ) {
String key = (String) iter.next();
int servicio = servicios.get( key ).intValue();

if (pingObj.ping( servicio )) {
System.out.println( key + ":SUCCESS");
} else {
System.out.println( key + ":FAILED" );
}

}
}

Prueba para insert into

public void insertARegister(


Connection connection,
String text
) throws SQLException {

String sql =
"insert into MESSAGES ( MESSAGE_ID, MESSAGE_TEXT ) values
( default, '" + text + "' )";

Statement s = connection.createStatement();
s.execute( sql );
s.close();
}

Lugar oficial de desarrollo y descarga

http://jt400.sourceforge.net/

5
Conexión a un AS/400 (iSeries) desde JDBC

Documentación
● Sitio oficial de IBM ToolBox para Java:
http://www-03.ibm.com/systems/i/software/toolbox/index.html

● Sitio oficial de IBM ToolBox para Java para programadores:


http://publib.boulder.ibm.com/infocenter/systems/scope/i5os/index.jsp?
topic=/rzahh/page1.htm

● Foro AS/400: http://www.mail-archive.com/forum.help400@combios.es/info.html

● Lista del desarrollo del driver JT400: https://lists.sourceforge.net/lists/listinfo/jt400-


news

● Foro AS/400: http://recursos-as400.com/forum/

● Foro AS/400: http://forums.systeminetwork.com/isnetforums/forumdisplay.php?f=84

● Foro AS/400: http://foros.emagister.com/foro-foro_de_as400-12625.htm

● Foro del Driver JTOpen: http://www-912.ibm.com/j_dir/JTOpen.nsf/($All)?OpenView

Preparación del AS/400


Otra cosa y esta si es importante, entérate en que versión de sistema
operativo esta el as400, como sea inferior a la 4.4 date por muerto. Ten en
cuenta que es un sistema que tiene 20 años y hay quien esta todavía en 2.3.
http://www.lawebdelprogramador.com/news/mostrar_new.php?
id=6&texto=AS/400&n1=491315&n2=1&n3=1&n4=1&n5=0&n6=0&n7=0&n8=0&n9=0&n0=0

Requerimientos del AS/400 para funcionar con IBM Toolbox para java
http://publib.boulder.ibm.com/iseries/v5r1/ic2924/index.htm?info/rzahh/rzahnm05.htm

Running IBM Toolbox for Java in a client/server environment requires that


you enable the QUSER user profile, start the host servers, and have TCP/IP
running. Perform these actions from an iSeries command line by running the
following commands:
1. Type DSPUSRPRF USRPRF(QUSER) and press ENTER to enable
the QUSER
user profile. The resulting display shows the status for QUSER.
2. Type STRHOSTSVR and press ENTER to start the OS/400 host
servers.
3. Type STRTCPSVR SERVER(*DDM) to start the TCP/IP server (with

6
Conexión a un AS/400 (iSeries) desde JDBC

*DDM specified for the Server parameter).


Tradución libre mía sin conocimientos técnicos del AS400:

Ejecutar el IBM Toolbox para Java en un entorno cliente/servidor requiere


que tu actives el perfil QUSER, arranques los servidores del host, y tengas
TCP/IP ejecutándose. Haz estas acciones desde una consola iSeries
ejecutando los siguientes comandos:
1. Escribe DSPUSRPRF USRPRF(QUSER) y pulsa ENTER para
activar el perfil QUSER. La pantalla resultante muestra el estado para
QUSER.
2. Escribe STRHOSTSVR y pulsa ENTER para arrancar los servidores
de host OS/400.
3. Escribe STRTCPSVR SERVER(*DDM) para arrancar el servidor
TCP/IP (con *DDM especificado para los paramétros Server).
Alguien por los foros es más estricto con los servidores del host y aconsejan ejecutar:
STRHOSTSVR *ALL.

Otra persona me dice esto:

Has mirado que estén arrancados los servicios necesarios en el AS400,


por ejemplo el servicio de router.
La gente del Aqua Data Studio me recomienda:

The OS/400 database host server is not started. You can start this by running
the following command on the OS/400 command line: STRHOSTSVR
*DATABASE

You can verify if the OS/400 database host server is running by running the
NETSTAT *CNN command. When the Work with TCP/IP Connection Status
screen is displayed, look for entry as-database under the Local Port heading
and ensure it is in Listen status.
Atención: el arranque de todos los servicios puede tardar bastante y consumir mucha
máquina.

Acciones realizadas en el AS400 de wTul

Arrancar los siguientes subsistemas (WRKSBSD) (a determinar los estrictamente


necesarios):
QBASE
QBATCH
QCMN
QCTL

7
Conexión a un AS/400 (iSeries) desde JDBC

QHTTPSVR
QINTER
QSPL
QSYSWRK
QDSNX
QPGMR
QSERVER
QSNADS
QSYSSBSD
QUSRWRK

Arrancar el servidor TCP/IP:


STRTCPSVR SERVER(*DDM)

Arrancar servidor del sistema principal (con autorización a nivel QSECOFR)


STRHOSTSVR SERVER(*ALL)

Comprobar conectividad desde consola de MSDOS con:


CWBPING 200.0.0.5

Problemas de conexión con el AS400


Hemos tenido muchos problemas de conexión y hemos estado consultando la
documentación, foros y listas de correo.

Como estas:

http://foros.emagister.com/mensaje-
PostPost_connection_refused_conectando_a_db2_desde_java-12625-638637-1-.htm

http://www.lawebdelprogramador.com/news/mostrar_new.php?
id=6&texto=AS/400&n1=491315&n2=0&n3=0&n4=0&n5=0&n6=0&n7=0&n8=0&n9=0&n0=0

Lo primero ha sido probar la conexión al AS400 desde un cliente que sabemos que
debería funcionar como un Access con driver ODBC. Hemos visto que esto también
fallaba.

Al final hemos tenido que levantar todos los servicios del AS400, esto casi fríe la
máquina pero al final ha conectado.

8
Conexión a un AS/400 (iSeries) desde JDBC

Configurando todo para trabajar desde Hibernate


hibernate.cfg.xml
<?xml version='1.0' encoding='utf-8'?> <!DOCTYPE hibernate-configuration
PUBLIC "-//Hibernate/Hibernate Configuration DTD//EN"
"http://hibernate.sourceforge.net/hibernate-
configuration-3.0.dtd">

<?xml version='1.0' encoding='utf-8'?> <!DOCTYPE hibernate-configuration


PUBLIC "-//Hibernate/Hibernate Configuration DTD//EN"
"http://hibernate.sourceforge.net/hibernate-
configuration-3.0.dtd">

<hibernate-configuration>
<session-factory>
<property
name="hibernate.connection.driver_class">com.ibm.as400.access.AS400JDBCDri
ver</property>
<property
name="hibernate.connection.url">jdbc:as400://217.127.196.233/JAVADB2;promp
t=false</property>

<property name="hibernate.connection.username">JAVADB2</property>
<property name="hibernate.connection.password">DB2JAVA</property>

<property name="hibernate.c3p0.min_size">5</property>
<property name="hibernate.c3p0.max_size">20</property>
<property name="hibernate.c3p0.timeout">300</property>
<property name="hibernate.c3p0.max_statements">50</property>
<property name="hibernate.c3p0.idle_test_period">3000</property>

<!-- SQL to stdout logging -->


<property name="show_sql">true</property>
<property name="format_sql">true</property>
<property name="use_sql_comments">true</property>

<property
name="dialect">org.hibernate.dialect.DB2400Dialect</property>

<mapping resource="hello/Message.hbm.xml"/>

</session-factory>
</hibernate-configuration>

Problemas con Hibernate

Error SQL7008

java.sql.SQLException: [SQL7008] MESSAGES de JAVADB2 no válido


para la operación.

9
Conexión a un AS/400 (iSeries) desde JDBC

Estoy teniendo este problema al hacer los insert intos esta es la sentencia que hibernate
intenta ejecutar:
insert into
MESSAGES
(MESSAGE_ID, MESSAGE_TEXT)
values
(default, ?)

En formato Prepared Statement.

Intento de recrear el PreparedStatement desde JDBC

public void insertByPreparedStatement(


Connection connection,
String text
) throws SQLException{
String sql =
"insert into MESSAGES ( MESSAGE_ID, MESSAGE_TEXT ) values
( default, ? )";

PreparedStatement ps = connection.prepareStatement(sql);
ps.setString( 1, text );
ps.executeUpdate();
ps.close();
}

La llamada al PreparedStatement funciona perfectamente así que el problema debe ser


algo de Hibernate.

Solución:

Según estos foros:

● http://www.mail-archive.com/forum.help400@combios.es/msg14793.html

● http://forum.hibernate.org/viewtopic.php?t=924511&highlight=sql7008

El problema es que tanto EJBs como Hibernate usan transacciones por defecto y para que
puedan funcionar el AS400 debe tener activados los diarios (journal) para el fichero que
se intenta actualizar.

Activación de los diarios

Lo puedes hacer desde linea de mandatos primero creando primero el


receptor (mandato CRTJRNRCV) y luego el diario(mandato CRTJRN).
Finalmente arrancas el registro por diario de tablas/ficheros deseados con
STRJRNPF.

10
Conexión a un AS/400 (iSeries) desde JDBC

Todo esto tambien se puede hacer fácilmente desde el navegador de


operaciones de Client Access en su apartado bases de datos.
http://www.mail-archive.com/forum.help400@combios.es/msg14793.html

Los de Hibernate dicen:

The problem is that Hibernate will require transactions, and without


journaling DB2/400 is not capable of SQL transactions. You will REQUIRE
journaling to work with hibernate
http://forum.hibernate.org/viewtopic.php?t=924511&highlight=sql7008

Solución rápida:

Hackear el hibernate.cfg.xml:
<property name="hibernate.connection.isolation">0</property>

Los de Hibernate dicen:

I too had to work against an AS400 database with journalling off. Setting
hibernate.connection.isolation 0 worked for me, however each statement was
autocommitted.
http://forum.hibernate.org/viewtopic.php?t=924511&highlight=sql7008

Aplicación de prueba java-db2


Se ha desarrollado una aplicación completamente operativa y con un juego de tests
configurables para poder probar futuras conexiones AS400.

La aplicación se llama java-db2 y se adjunta con este documento tanto el código de la


misma como todas las herramientas necesarias para su compilación, configuración y
ejecución.

Configuración y ejecución de los tests

1. Conseguir el codigo del proyecto.

2. Descomprimirlo en un directorio de usuario.

3. Preparar el AS400

1. Escribe DSPUSRPRF USRPRF(QUSER) y pulsa ENTER para activar el perfil


QUSER. La pantalla resultante muestra el estado para QUSER.

11
Conexión a un AS/400 (iSeries) desde JDBC

2. Escribe STRHOSTSVR y pulsa ENTER para arrancar los servidores de host


OS/400.

3. Escribe STRTCPSVR SERVER(*DDM) para arrancar el servidor TCP/IP (con


*DDM especificado para los paramétros Server).

4. Crear la tabla usando el sql en schema-db2.sql

5. Configurar los parámetros en el build.xml

1. ipServer

2. userName

3. userPassword

6. Configurar las propiedades de Hibernate en src/java/hibernate.cfg.xml

1. hibernate.connection.url

2. hibernate.connection.username

3. hibernate.connection.password

7. Configurar el log en src/java/log4j.properties

1. log4j.appender.R

2. log4j.appender.R.File

8. Usar las task de ant para ejecutar las pruebas

1. ant testPing (para testear la conexión con el AS400)

2. ant testJTOpen (para testear los select, insert ydelete en la tabla MESSAGES)

3. ant testHibernate (para testear los select, insert ydelete en la tabla


MESSAGES usando Hibernate)

Configuración y despliegue de la aplicación web

1. Conseguir el codigo del proyecto.

2. Descomprimirlo en un directorio de usuario.

3. Preparar el AS400

12
Conexión a un AS/400 (iSeries) desde JDBC

1. Escribe DSPUSRPRF USRPRF(QUSER) y pulsa ENTER para activar el perfil


QUSER. La pantalla resultante muestra el estado para QUSER.

2. Escribe STRHOSTSVR y pulsa ENTER para arrancar los servidores de host


OS/400.

3. Escribe STRTCPSVR SERVER(*DDM) para arrancar el servidor TCP/IP (con


*DDM especificado para los paramétros Server).

4. Crear la tablas usando el sql en schema-db2.sql

5. Configurar las propiedades de Hibernate en src/java/hibernate.cfg.xml

1. hibernate.connection.url

2. hibernate.connection.username

3. hibernate.connection.password

6. Configurar el log en src/java/log4j.properties

1. log4j.appender.R

2. log4j.appender.R.File

7. Usar las task de ant para crear la aplicación web .war

1. ant dist

8. Usar el dist/java-db2.war para desplegar la aplicación en un contenedor de


servlets como Tomcat

Aplicación de pruebas online

Durante un período de tiempo estará disponible un despliegue de la aplicación de pruebas


de un servidor mío:

http://fernandoguillen.info:8180/java-db2/

Podéis comprobar que esta aplicación está atacando a vuestro AS400.

13
Conexión a un AS/400 (iSeries) desde JDBC

Conclusiones
Ha sido una prueba dura y hemos tenido menos suerte de la que nos merecíamos.

Aún así esto puede ser una cosa a celebrar pues nos hemos topado y hemos superado
muchos obstáculos que sabremos solventar rápidamente en el futuro.

La conexión con el AS400 no es trivial y requiere de una configuración del AS400 muy
específica.

Existe más documentación sobre conectar JDBC con el AS400 de la que me esperaba.

IBM presta mucha documentación incluso un driver open-source para programar Java
atacando a un AS400.

14

You might also like