Você está na página 1de 27

Introducción a Spring

Norberto Fernández
Departamento de Ingeniería Telemática
Universidad Carlos III de Madrid
berto@it.uc3m.es

Servidores de Información 2008/2009 1

¿Qué es Spring?
• Framework de código abierto para el desarrollo de
aplicaciones (empresariales) Java
• Origen: Rod Johnson, Expert One-to-One J2EE Design and
Development (Octubre, 2002)
• Alternativa popular a J2EE (EJBs)
• Veremos la versión 2.5

Servidores de Información 2008/2009 2


Fuente: Dzone

1
Motivación
• Malas experiencias con aplicaciones J2EE
o Complejas,difíciles de probar, pobres prestaciones,...

• Críticas al uso de EJBs:


o Rod Johnson, J2EE development without EJB (2004)
 Complejidad (descriptores, implementación interfaces,...) y
baja productividad del programador
 Modelo remoto basado sólo en RMI
 Muchas aplicaciones no necesitan componentes remotos
 Difíciles de depurar (dependencias con contenedor, volver a
hacer deployment y volver a arrancar)
 Mapeo O/R basado en entity beans limitado (p.ej. no
considera la relación de herencia)
 ...

Servidores de Información 2008/2009 3

Motivación

• J2EE objetivo: estandarizar servicios de uso común en el


desarrollo de aplicaciones empresariales
o Directorio (JNDI), transacciones (JTA), conexión a sistemas legados
(JCA), pooling de recursos, etc
• EJB es sólo una forma de llevar a la práctica a esos
servicios a través de un modelo de componentes
• Sin embargo podemos usar las funcionalidades de los
servicios sin tener EJBs ...
• ... este es el objetivo de Spring: ofrecer librerías con las
funcionalidades de uso común por aplicaciones
empresariales ...
• ... y más "ligeras" que los EJBs
o Usar POJOs (Plain Old Java Objects) en su lugar
Servidores de Información 2008/2009 4

2
Módulos principales de Spring
• Spring Core (Inversión del control (IoC) / Inyección de
dependencias (DI))
• Spring AOP (Programación orientada a aspectos)
• Spring JDBC (Acceso a datos)
• Spring MVC (desarrollo Web según el patrón MVC)
• Spring Remoting (distribución)
• Spring Transaction Abstraction (Gestión de
transacciones)
• Otros: Spring TestContext (pruebas), Spring JMX
(gestión), Spring Security (seguridad), Spring Web Flow
(control de flujos en aplicaciones Web)

Servidores de Información 2008/2009 5

Spring Core

Dependency Injection

3
IoC / DI: Introducción
• El núcleo de Spring (Spring Core)
• Inversion of Control (IoC): Hollywood principle
o "Don't call us, we'll call you"
• Los componentes no crean (con new) o buscan (p.ej. con
JNDI) las referencias a otros componentes que necesitan
para realizar su trabajo, sino que simplemente declaran
qué dependencias tienen (fichero de configuración,
anotaciones) y un contenedor les proporciona (inyecta)
estas dependencias
o Dependency Injection (DI)
• El contenedor se encarga de instanciar o localizar los
componentes necesarios e inicializarlos antes de inyectar su
referencia a quién la necesite

Servidores de Información 2008/2009 7

IoC / DI: Introducción


• Se suele combinar con programación basada en interfaces,
para conseguir bajo acoplamiento entre componentes
o Sólo dependencia con las interfaces, no con las implementaciones
concretas
• Ventajas:
o Se reduce el código de pegamento
 Llamadas a JNDI para localizar componentes
 Código de conexión con componentes remotos
 El contenedor proporciona proxy
o Fichero de configuración de dependencias: tocar sólo ahí
para cambiarlas
 Sin tocar el código fuente y sin recompilar
o Facilidad para llevar a cabo pruebas
 Reemplazar componentes por Mockup objects

Servidores de Información 2008/2009 8

4
DI: HolaMundo (I)
Interfaz del servicio:

package spring.core.ejemplos;

public interface MessagingService {


public String sayMessage(String name);
}

Servidores de Información 2008/2009 9

DI: HolaMundo (II)

Implementación del servicio:


package spring.core.ejemplos;

public class MessagingServiceImpl implements MessagingService {


Message msg = null;
public void setMsg(Message msg) {
this.msg = msg;
}
public String sayMessage(String name) {
return msg.getMsg() + " " + name;
}
}

Servidores de Información 2008/2009 10

5
DI: HolaMundo (III)
Message (interfaz e implementación):
package spring.core.ejemplos;

public interface Message {


public String getMsg();
}

package spring.core.ejemplos;

public class HelloMessage implements Message {

public String getMsg() {


return "Hello";
}
}

Servidores de Información 2008/2009 11

DI: HolaMundo (IV)


Fichero de configuración XML de Spring (spring-beans.xml):
<?xml version="1.0" encoding="UTF-8"?>

<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">

<bean id="helloMsg" class="spring.core.ejemplos.HelloMessage"/>

<bean id="helloSrv" class="spring.core.ejemplos.MessagingServiceImpl">


<property name="msg" ref="helloMsg"/>
</bean>

</beans>

Servidores de Información 2008/2009 12

6
DI: HolaMundo (y V)
Main de la aplicación:
package spring.core.ejemplos;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;

public class Main {

public static void main(String[] args) {

ApplicationContext context = new


FileSystemXmlApplicationContext("src/spring/core/ejemplos/spring-beans.xml");

MessagingService hello = (MessagingService)context.getBean("helloSrv");


System.out.println(hello.sayMessage(args[0]));
}
}

Servidores de Información 2008/2009 13

Spring AOP

Programación Orientada a Aspectos

7
AOP: Introducción
• ¿Qué es?
o Aspect Oriented Programming
o Permite combinar cierto código con otro (aspecto) para añadir cierta
funcionalidad al original sin necesidad de modificarlo
o Facilitar la implementación de funcionalidades transversales de una
aplicación
 Ej.: logging, control acceso

• Tipos de AOP
o Estática
 En tiempo de compilación
 Se incluye la información de aspectos en los bytecodes
 Problema: recompilar para modificar
o Dinámica
 En tiempo de ejecución
 Problema: mayor coste computacional
 Interrumpir flujo programa para comprobar si hay que ejecutar el aspecto

Servidores de Información 2008/2009 15

AOP: Conceptos
• Joinpoint (Punto de cruce)
o Punto concreto del flujo de ejecución
 Ej.: Llamada al método hola de una determinada clase
• Advice (Consejo)
o Código que el aspecto ejecuta en un joinpoint
• Pointcuts (Punto de corte)
o Combinación de joinpoints
 Ej.: Llamada a cualquier método de una clase concreta
• Aspects (Aspecto)
o Combinación de advice (código) y pointcut (lugar donde se interrumpe el
flujo normal para ejecutarlo)
• Target (Destinatario)
o Objeto cuyo comportamiento modifica el aspecto
• Introduction
o Permite añadir métodos o atributos a clases ya existentes
Servidores de Información 2008/2009 16

8
Spring AOP

• AOP dinámica
• Implementada a través de Proxys
• Más limitada que la de otras librerías (ej.: AspectJ)
o Ej.: Sólo un tipo de joinpoint (invocación a método)
 Se puede combinar AspectJ con Spring si se necesita más
• El propio framework utiliza aspectos para implementar otras
funcionalidades
o Ej.: Transacciones
• A continuación veremos el HolaMundo

Servidores de Información 2008/2009 17

Spring AOP: Hola Mundo (I)

Target:

package spring.aop.ejemplos;

public class HelloWorldServiceImpl implements HelloWorldService {

public String sayHello(String name) {


return "Hello " + name;
}
}

Servidores de Información 2008/2009 18

9
Spring AOP: HolaMundo (II)
Advice:
package spring.aop.ejemplos;

public class HelloWorldAdvice {

public void antes() {


System.out.println("Llamando a sayHello");
}

public void despues(Object ret) {


System.out.println("sayHello ha devuelto " + ret.toString());
}
}

Servidores de Información 2008/2009 19

Spring AOP: HolaMundo (III)


Fichero de configuración:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd">

<bean id="helloSrv" class="spring.aop.ejemplos.HelloWorldServiceImpl" />


<bean id="helloAdvice" class="spring.aop.ejemplos.HelloWorldAdvice" />

<aop:config>
<aop:aspect ref="helloAdvice">
<aop:pointcut id="sayHelloPointCut" expression="execution(* *.sayHello(..))" />
<aop:before method="antes" pointcut-ref="sayHelloPointCut" />
<aop:after-returning method="despues" pointcut-ref="sayHelloPointCut"
returning="ret" />
</aop:aspect>
</aop:config>
</beans>
Servidores de Información 2008/2009 20

10
Spring AOP: HolaMundo (y IV)

Main de la aplicación:
package spring.aop.ejemplos;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;

public class Main {

public static void main(String[] args) {

ApplicationContext context = new


FileSystemXmlApplicationContext("src/spring/aop/ejemplos/spring-beans.xml");

HelloWorldService hello = (HelloWorldService)context.getBean("helloSrv");


System.out.println(hello.sayHello(args[0]));
}
}

Servidores de Información 2008/2009 21

Spring Data Access

11
Acceso a datos

Una estructura Java típica de acceso a BD:


public void saveWhatever(Whatever w) {

Connection conn = null;


PreparedStatement stmt = null;
try {
conn = dataSource.getConnection();
stmt = conn.prepareStatement(DB_QUERY);
...
stmt.execute();
} catch (SQLException e) {

} finally {
try {
if(stmt != null) { stmt.close(); }
if(conn != null) { conn.close(); }
} catch (SQLException e) { // noop }
}

Servidores de Información 2008/2009 23

Acceso a datos
• Aspectos a mejorar en el ejemplo:
o SQLException: excepción genérica
o Captura de excepciones para no hacer nada
• ¿Cómo lo mejora Spring?
o Mapeo de SQLException a excepciones específicas
 Subclases de org.springframework.dao.DataAccessException
o Uso de unchecked exceptions
 DataAccessException es una subclase de java.lang.RuntimeException
 Se pueden capturar si se desea, pero no es obligatorio
o Automatiza la gestión de conexiones
 Se declara una fuente de datos y Spring la gestiona
 No se accede directamente a las conexiones, sino que se utiliza un
JdbcTemplate
 Usualmente un org.springframework.jdbc.core.JdbcTemplate
• Veremos acceso a BD relacionales, pero Spring ofrece
integración con librerías ORM como Hibernate
Servidores de Información 2008/2009 24

12
Acceso a datos: HolaMundo (I)
• Vamos a trabajar con una base de datos de
productos:

Prod_ID char(5), Nombre varchar(20), Stock int, Precio double

• Creamos un bean para trabajar con estos productos:

public class Producto {


String id;
String nombre;
int stock;
float precio;

// Aquí van los getters y setters


}

Servidores de Información 2008/2009 25

Acceso a datos: HolaMundo (II)

Interfaz del servicio de acceso a datos:

package spring.jdbc.ejemplos;

public interface DataAccessService {

public void insertarProducto(Producto p);


public Producto consultarProducto(String id);
}

Servidores de Información 2008/2009 26

13
Acceso a datos: HolaMundo (III)
Implementación del servicio de acceso a datos (I):
package spring.jdbc.ejemplos;

import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;
import org.springframework.dao.DataAccessException;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;

public class DataAccessServiceImpl implements DataAccessService {

private JdbcTemplate jdbcTemplate;


public void setJdbcTemplate(JdbcTemplate jdbcTemplate) {
this.jdbcTemplate = jdbcTemplate;
}

...

Servidores de Información 2008/2009 27

Acceso a datos: HolaMundo (IV)

Implementación del servicio de acceso a datos (II):

...

private static final String PRODUCT_INSERT =


"insert into Productos (prod_id, nombre, stock, precio) values (?,?,?,?)";

public void insertarProducto(Producto p) {


jdbcTemplate.update(PRODUCT_INSERT,
new Object[]{p.getId(), p.getNombre(), p.getStock(), p.getPrecio()});
}

...

Servidores de Información 2008/2009 28

14
Acceso a datos: HolaMundo (V)
Implementación del servicio de acceso a datos (y III):
private static final String PRODUCT_SELECT =
"select prod_id, nombre, stock, precio from Productos where prod_id=?";

public Producto consultarProducto(String id) {

List matches = jdbcTemplate.query(PRODUCT_SELECT,


new Object[]{id},
new RowMapper() {
public Object mapRow(ResultSet rs, int rowNum)
throws SQLException, DataAccessException {

Producto p = new Producto();


p.setId(rs.getString(1));
p.setNombre(rs.getString(2));
p.setStock(rs.getInt(3));
p.setPrecio(rs.getFloat(4));
return p;
}
}
);

return matches.size() > 0 ? (Producto) matches.get(0) : null;


} Servidores de Información 2008/2009 29

Acceso a datos: HolaMundo (VI)


Fichero de configuración de Spring:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">

<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource">


<property name="driverClassName" value="com.mysql.jdbc.Driver"/>
<property name="url" value="jdbc:mysql://localhost:3306/Productos"/>
<property name="username" value="user"/>
<property name="password" value="*****"/>
<property name="initialSize" value="5" />
<property name="maxActive" value="10" />
</bean>
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
<property name="dataSource" ref="dataSource"/>
</bean>
<bean id="dao" class="spring.jdbc.ejemplos.DataAccessServiceImpl">
<property name="jdbcTemplate" ref="jdbcTemplate" />
</bean>

</beans>
Servidores de Información 2008/2009 30

15
Acceso a datos: HolaMundo (y VII)
Main de la aplicación:
package spring.jdbc.ejemplos;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;

public class Main {


public static void main(String[] args) {

ApplicationContext context = new


FileSystemXmlApplicationContext("src/spring/jdbc/ejemplos/spring-beans.xml");
DataAccessService daoSvc = (DataAccessService)context.getBean("dao");

Producto p = new Producto();


p.setId("id123");
p.setNombre("NuevoProducto");
p.setPrecio((float)12.37);
p.setStock(120);

daoSvc.insertarProducto(p);
System.out.println(daoSvc.consultarProducto("id123"));
}
}
Servidores de Información 2008/2009 31

Spring MVC

Desarrollo de aplicaciones Web

16
Spring MVC: Funcionamiento (I)

Fuente: Spring in action Servidores de Información 2008/2009 33

Spring MVC: Funcionamiento (II)


(1) Las peticiones pasan a través de un servlet que
actúa de Front Controller (DispatcherServlet)
(2) El DispatcherServlet consulta a un HandlerMapping
para decidir a qué controlador le pasa la petición
o Usa la URL de la solicitud para decidir
(3 y 4) El controlador procesa la petición, accede a la
lógica de negocio y potencialmente obtiene
resultados (modelo, un Map) además selecciona la
vista para presentar el modelo
o Para que el controlador no esté acoplado a la vista, se
devuelve un identificador lógico (nombre) de vista
o Devuelve al DispatcherServlet un objeto que encapsula
ambos: ModelAndView

Servidores de Información 2008/2009 34

17
Spring MVC: Funcionamiento (y III)

(5) El DispatcherServlet utiliza un ViewResolver para


resolver el nombre en una vista concreta
o Normalmente un JSP, pero se soportan otros Velocity,
XSLT,Tiles, ...
(6) El DispatcherServlet utiliza la vista para mostrar el
modelo al usuario

Servidores de Información 2008/2009 35

Spring MVC: DispatcherServlet

• Objeto de la clase DispatcherServlet del paquete


org.springframework.web.servlet
• Actúa como un broker: despacha las peticiones que recibe al
controlador responsable de tratarlas
• Configurar el /WEB-INF/web.xml de la aplicación para que el
dispatcher reciba las peticiones
• Lee su configuración del fichero dispatcher-servlet.xml
o Ubicado en el /WEB-INF/ de la aplicación
o Referencia al HandlerMapping
o Referencias a los controladores
o Referencia al ViewResolver

Servidores de Información 2008/2009 36

18
Spring MVC: HandlerMapping
• Interfaz HandlerMapping del paquete
org.springframework.web.servlet
• Spring proporciona varias implementaciones. Dos de las
más utilizadas son:
o Paquete: org.springframework.web.servlet.handler
o BeanNameUrlHandlerMapping
 Selección por nombre del bean (el nombre coincide con la URL de
invocación). Es el HandlerMapping por defecto

<bean name="/home.htm" class="this.is.an.example.HomePageController"/>

o SimpleUrlHandlerMapping
 Se define una tabla que asocia URLs a controladores
 Lo veremos en el ejemplo

Servidores de Información 2008/2009 37

Spring MVC: Controller

• Interfaz Controller del paquete


org.springframework.web.servlet.mvc
• Método principal:
ModelAndView handleRequest(HttpServletRequest request,
HttpServletResponse response) throws Exception;

• Usualmente para implementar un controlador se extiende


de la clase abstracta AbstractController del mismo paquete
• Al controlador se le inyecta (si es necesario) la referencia al
bean que ofrece el servicio de la lógica de negocio

Servidores de Información 2008/2009 38

19
Spring MVC: ViewResolver
• Interfaz ViewResolver del paquete
org.springframework.web.servlet
• Método:
View resolveViewName(String viewName, Locale locale) throws Exception

• Spring ofrece algunas implementaciones:


o Paquete: org.springframework.web.servlet.view
o ResourceBundleViewResolver
 Un fichero bundle contiene las definiciones de vista (mapeo nombre de vista a
implementación de vista). Por ejemplo, bundle views_EN.properties:
nombre-vista.class=org.springframework.web.servlet.view.JstlView
nombre-vista.url=/WEB-INF/views/en_GB/user/edit.jsp

o UrlBasedViewResolver
 No mapeo: el nombre es directamente una referencia a la vista
 No implementa soporte para localización
 Veremos en el ejemplo el uso de una de sus
subclases: InternalResourceViewResolver 39

Spring MVC: View

• Interfaz View del paquete org.springframework.web.servlet


• Métodos principales:
String getContentType()
void render(Map model, HttpServletRequest request,
HttpServletResponse response) throws Exception

• Spring proporciona múltiples implementaciones de esta


interfaz
o JstlView, VelocityView, TilesView, XsltView, ...

Servidores de Información 2008/2009 40

20
Spring MVC: HolaMundo (I)
/WEB-INF/web.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">

<servlet>
<servlet-name>dispatcher</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<load-on-startup>2</load-on-startup>
</servlet>

<servlet-mapping>
<servlet-name>dispatcher</servlet-name>
<url-pattern>*.do</url-pattern>
</servlet-mapping>

<welcome-file-list>
<welcome-file>index.jsp</welcome-file>
</welcome-file-list>

</web-app> Servidores de Información 2008/2009 41

Spring MVC: HolaMundo (II)

Página de bienvenida: index.jsp


<%@page contentType="text/html" pageEncoding="UTF-8"%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
"http://www.w3.org/TR/html4/loose.dtd">

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Spring MVC Hello World</title>
</head>

<body>
<form method="post" action="greet.do">
Type in your name here: <input type="text" name="name"/>
<input type="submit" value="Go!"/>
</form>
</body>
</html>

Servidores de Información 2008/2009 42

21
Spring MVC: HolaMundo (III)

/WEB-INF/dispatcher-servlet.xml
<?xml version="1.0" encoding="UTF-8"?>

<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:aop="http://www.springframework.org/schema/aop"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd>

<bean id="urlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">


<property name="mappings">
<props><prop key="greet.do">greetingController</prop></props>
</property>
</bean>
<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="viewClass" value="org.springframework.web.servlet.view.JstlView"/>
<property name="prefix" value="/WEB-INF/jsp/"/>
<property name="suffix" value=".jsp"/>
</bean>
<bean name="greetingController" class="spring.mvc.ejemplos.GreetController"/>

</beans>
Servidores de Información 2008/2009 43

Spring MVC: HolaMundo (IV)


package spring.mvc.ejemplos;

import java.util.HashMap;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.mvc.AbstractController;

public class GreetController extends AbstractController {

protected ModelAndView handleRequestInternal(HttpServletRequest req, HttpServletResponse res)


throws Exception {

String param = req.getParameter("name");


if ((param == null) || (param.trim().equals(""))) {
param = "Anonimous User";
}

Map model = new HashMap();


model.put("usrName", param);

return new ModelAndView("greet", model);


}
}

Servidores de Información 2008/2009 44

22
Spring MVC: HolaMundo (y V)

/WEB-INF/jsp/greet.jsp
<%@page contentType="text/html" pageEncoding="UTF-8"%>
<%@taglib prefix="c" uri="http://java.sun.com/jstl/core_rt" %>

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"


"http://www.w3.org/TR/html4/loose.dtd">

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>JSP Page</title>
</head>
<body>
<h1>Hello <c:out value="${usrName}"></c:out>!</h1>
</body>
</html>

Servidores de Información 2008/2009 45

Spring Remoting

Acceso a componentes remotos

23
Spring Remoting: Introducción
• Objetivo: facilitar el desarrollo de aplicaciones distribuidas
o Reducir el código que se necesita para exponer un bean como servicio o
para acceder desde un bean a un servicio remoto
• Spring proporciona mecanismos para:
o Definir service exporter (convertir bean en servicio)
o Definir proxies (acceder a beans remotos como locales)
• En la práctica Spring 2.5 soporta cinco tipos distintos de
arquitecturas distribuidas:
o RMI
o Servicios Web (sólo proxy, no exporter)
o HTTP Invoker (específico de Spring)
o Hessian (Caucho.com, protocolo binario, poco utilizado)
o Burlap (Caucho.com, protocolo XML, poco utilizado)

Servidores de Información 2008/2009 47

Spring Remoting: HolaMundo (I)


• Se ha convertido el HolaMundo en un servicio Web que
atiende peticiones remotas
• Se pretende integrar ese servicio como un componente más
dentro de una aplicación Spring
• Fragmento del WSDL del servicio:

<wsdl:definitions
targetNamespace="http://platino:8181/axis/services/HolaMundo">
...
<wsdl:service name="HelloWorldServiceImplService">
<wsdl:port binding="impl:HolaMundoSoapBinding" name="HolaMundo">
<wsdlsoap:address
location="http://platino:8181/axis/services/HolaMundo"/>
</wsdl:port>
</wsdl:service>
</wsdl:definitions>

Servidores de Información 2008/2009 48

24
Spring Remoting: HolaMundo (II)
Fichero de configuración de Spring:
<?xml version="1.0" encoding="UTF-8"?>

<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">

<bean id="remoteHelloSrv"
class="org.springframework.remoting.jaxrpc.JaxRpcPortProxyFactoryBean">
<property name="wsdlDocumentUrl"
value="http://platino:8181/axis/services/HolaMundo?wsdl" />
<property name="serviceInterface"
value="spring.remote.ejemplos.HelloWorldService"/>
<property name="portName" value="HolaMundo" />
<property name="serviceName" value="HelloWorldServiceImplService" />
<property name="namespaceUri"
value="http://platino:8181/axis/services/HolaMundo" />
</bean>

</beans>

Servidores de Información 2008/2009 49

Spring Remoting: HolaMundo (III)


Main de la aplicación:
package spring.remote.ejemplos;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;

public class Main {

public static void main(String[] args) {

ApplicationContext context = new


FileSystemXmlApplicationContext("src/spring/core/ejemplos/spring-beans.xml");

HelloWorldService remoteHello =
(HelloWorldService)context.getBean("remoteHelloSrv");

System.out.println(remoteHello.sayHello(args[0]));
}
}

Servidores de Información 2008/2009 50

25
Gestión de transacciones
• Spring ofrece gestión de transacciones programática o
declarativa
• Cuando se trabaja con una fuente de datos Spring permite
utilizar el soporte de transacciones de la fuente (BD
relacional JDBC, Hibernate, ...)
• Spring es compatible con JTA (Java Transaction API)
o Permite ofrecer soporte a transacciones distribuidas
• Spring no gestiona directamente las transacciones, sino que
hace uso de un gestor de transacciones
(TransactionManager) del que se ofrecen varias
implementaciones:
o org.springframework.jdbc.datasource.DataSourceTransactionManager (JDBC)
o org.springframework.orm.hibernate3.HibernateTransactionManager (Hibernate)
o org.springframework.transaction.jta.JtaTransactionManager (JTA)
o ...

Servidores de Información 2008/2009 51

Gestión de transacciones
Ejemplo de (parte de) fichero de configuración de Spring:
<bean id="fooService" class="x.y.service.DefaultFooService"/>
<tx:advice id="txAdvice" transaction-manager="txManager">
<tx:attributes>
<tx:method name="get*" read-only="true"/>
<tx:method name="*"/>
</tx:attributes>
</tx:advice>

<aop:config>
<aop:pointcut id="fooServiceOperation" expression="execution(* x.y.service.FooService.*(..))"/>
<aop:advisor advice-ref="txAdvice" pointcut-ref="fooServiceOperation"/>
</aop:config>

<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource">


<property name="driverClassName" value="com.mysql.jdbc.Driver">
<property name="url" value="jdbc:mysql://localhost/Productos"/>
<property name="username" value="user"/>
<property name="password" value="*******"/>
</bean>

<bean id="txManager"
class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean>

26
Referencias
• Rod Johnson; Expert One-to-One J2EE
Design and Development. Ed Wrox,
ISBN: 9780764543852, 2002.

• Rod Johnson; J2EE development without


EJB. Ed Wrox, ISBN: 9780764558313,
2004.

• J. Machacek, A. Vukotic, A. Chakraborty,


J.Ditt; Pro Spring 2.5. Ed. Apress, ISBN:
9781590599211, 2008.

• C. Walls, R. Breidenbac; Spring in action


(2nd Ed.). Ed. Manning, ISBN:
9781933988139, 2007. 53

27

Você também pode gostar