EJB - Interceptores
EJB 3.0 proporciona especificaciones para interceptar llamadas a métodos comerciales utilizando métodos anotados con la anotación @AroundInvoke. EjbContainer llama a un método interceptor antes de que la llamada al método empresarial lo intercepte. A continuación se muestra la firma de ejemplo de un método interceptor
@AroundInvoke
public Object methodInterceptor(InvocationContext ctx) throws Exception {
System.out.println("*** Intercepting call to LibraryBean method: "
+ ctx.getMethod().getName());
return ctx.proceed();
}
Los métodos de interceptor se pueden aplicar o limitar en tres niveles.
Default - El interceptor predeterminado se invoca para cada bean dentro de la implementación. El interceptor predeterminado se puede aplicar solo a través de xml (ejb-jar.xml).
Class- El interceptor de nivel de clase se invoca para cada método del bean. El interceptor de nivel de clase se puede aplicar mediante una anotación o mediante xml (ejb-jar.xml).
Method- El interceptor de nivel de método se invoca para un método particular del bean. El interceptor de nivel de método se puede aplicar mediante anotaciones o via xml (ejb-jar.xml).
Estamos discutiendo el interceptor de nivel de clase aquí.
Clase de interceptor
package com.tutorialspoint.interceptor;
import javax.interceptor.AroundInvoke;
import javax.interceptor.InvocationContext;
public class BusinessInterceptor {
@AroundInvoke
public Object methodInterceptor(InvocationContext ctx) throws Exception {
System.out.println("*** Intercepting call to LibraryBean method: "
+ ctx.getMethod().getName());
return ctx.proceed();
}
}
Interfaz remota
import javax.ejb.Remote;
@Remote
public interface LibraryBeanRemote {
//add business method declarations
}
EJB sin estado interceptado
@Interceptors ({BusinessInterceptor.class})
@Stateless
public class LibraryBean implements LibraryBeanRemote {
//implement business method
}
Aplicación de ejemplo
Creemos una aplicación EJB de prueba para probar EJB sin estado interceptado.
Paso | Descripción |
---|---|
1 | Cree un proyecto con un nombre EjbComponent bajo un paquete com.tutorialspoint.interceptor como se explica en el capítulo EJB - Crear aplicación . También puede utilizar el proyecto creado en el capítulo EJB - Crear aplicación como tal para este capítulo para comprender los conceptos de EJB interceptados. |
2 | Cree LibraryBean.java y LibraryBeanRemote en el paquete com.tutorialspoint.interceptor como se explica en el capítulo EJB - Crear aplicación . Mantenga el resto de los archivos sin cambios. |
3 | Limpie y compile la aplicación para asegurarse de que la lógica empresarial funcione según los requisitos. |
4 | Finalmente, implemente la aplicación en forma de archivo jar en JBoss Application Server. El servidor de aplicaciones JBoss se iniciará automáticamente si aún no se ha iniciado. |
5 | Ahora cree el cliente ejb, una aplicación basada en consola de la misma manera que se explica en el capítulo EJB - Crear aplicación en el temaCreate Client to access EJB. |
EJBComponent (módulo EJB)
LibraryBeanRemote.java
package com.tutorialspoint.interceptor;
import java.util.List;
import javax.ejb.Remote;
@Remote
public interface LibraryBeanRemote {
void addBook(String bookName);
List getBooks();
}
LibraryBean.java
package com.tutorialspoint.interceptor;
import java.util.ArrayList;
import java.util.List;
import javax.ejb.Stateless;
import javax.interceptor.Interceptors;
@Interceptors ({BusinessInterceptor.class})
@Stateless
public class LibraryBean implements LibraryBeanRemote {
List<String> bookShelf;
public LibraryBean() {
bookShelf = new ArrayList<String>();
}
public void addBook(String bookName) {
bookShelf.add(bookName);
}
public List<String> getBooks() {
return bookShelf;
}
}
Tan pronto como implemente el proyecto EjbComponent en JBOSS, observe el registro de jboss.
JBoss ha creado automáticamente una entrada JNDI para nuestro bean de sesión - LibraryBean/remote.
Usaremos esta cadena de búsqueda para obtener un objeto comercial remoto de tipo: com.tutorialspoint.interceptor.LibraryBeanRemote
Salida de registro del servidor de aplicaciones JBoss
...
16:30:01,401 INFO [JndiSessionRegistrarBase] Binding the following Entries in Global JNDI:
LibraryBean/remote - EJB3.x Default Remote Business Interface
LibraryBean/remote-com.tutorialspoint.interceptor.LibraryBeanRemote - EJB3.x Remote Business Interface
16:30:02,723 INFO [SessionSpecContainer] Starting jboss.j2ee:jar=EjbComponent.jar,name=LibraryBean,service=EJB3
16:30:02,723 INFO [EJBContainer] STARTED EJB: com.tutorialspoint.interceptor.LibraryBeanRemote ejbName: LibraryBean
16:30:02,731 INFO [JndiSessionRegistrarBase] Binding the following Entries in Global JNDI:
LibraryBean/remote - EJB3.x Default Remote Business Interface
LibraryBean/remote-com.tutorialspoint.interceptor.LibraryBeanRemote - EJB3.x Remote Business Interface
...
EJBTester (cliente EJB)
jndi.properties
java.naming.factory.initial=org.jnp.interfaces.NamingContextFactory
java.naming.factory.url.pkgs=org.jboss.naming:org.jnp.interfaces
java.naming.provider.url=localhost
Estas propiedades se utilizan para inicializar el objeto InitialContext del servicio de nombres de Java.
El objeto InitialContext se utilizará para buscar un bean de sesión sin estado.
EJBTester.java
package com.tutorialspoint.test;
import com.tutorialspoint.stateful.LibraryBeanRemote;
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.List;
import java.util.Properties;
import javax.naming.InitialContext;
import javax.naming.NamingException;
public class EJBTester {
BufferedReader brConsoleReader = null;
Properties props;
InitialContext ctx;
{
props = new Properties();
try {
props.load(new FileInputStream("jndi.properties"));
} catch (IOException ex) {
ex.printStackTrace();
}
try {
ctx = new InitialContext(props);
} catch (NamingException ex) {
ex.printStackTrace();
}
brConsoleReader =
new BufferedReader(new InputStreamReader(System.in));
}
public static void main(String[] args) {
EJBTester ejbTester = new EJBTester();
ejbTester.testInterceptedEjb();
}
private void showGUI() {
System.out.println("**********************");
System.out.println("Welcome to Book Store");
System.out.println("**********************");
System.out.print("Options \n1. Add Book\n2. Exit \nEnter Choice: ");
}
private void testInterceptedEjb() {
try {
int choice = 1;
LibraryBeanRemote libraryBean =
LibraryBeanRemote)ctx.lookup("LibraryBean/remote");
while (choice != 2) {
String bookName;
showGUI();
String strChoice = brConsoleReader.readLine();
choice = Integer.parseInt(strChoice);
if (choice == 1) {
System.out.print("Enter book name: ");
bookName = brConsoleReader.readLine();
Book book = new Book();
book.setName(bookName);
libraryBean.addBook(book);
} else if (choice == 2) {
break;
}
}
List<Book> booksList = libraryBean.getBooks();
System.out.println("Book(s) entered so far: " + booksList.size());
int i = 0;
for (Book book:booksList) {
System.out.println((i+1)+". " + book.getName());
i++;
}
} catch (Exception e) {
System.out.println(e.getMessage());
e.printStackTrace();
}finally {
try {
if(brConsoleReader !=null) {
brConsoleReader.close();
}
} catch (IOException ex) {
System.out.println(ex.getMessage());
}
}
}
}
EJBTester realiza las siguientes tareas:
Cargue las propiedades de jndi.properties e inicialice el objeto InitialContext.
En el método testInterceptedEjb (), la búsqueda de jndi se realiza con el nombre "LibraryBean / remote" para obtener el objeto de negocio remoto (EJB sin estado).
Luego, se muestra al usuario una interfaz de usuario de la tienda de la biblioteca y se le pide que ingrese una opción.
Si el usuario ingresa 1, el sistema solicita el nombre del libro y guarda el libro usando el método addBook () del bean de sesión sin estado. Session Bean está almacenando el libro en su variable de instancia.
Si el usuario ingresa 2, el sistema recupera libros usando el método getBooks () del bean de sesión sin estado y sale.
Ejecute el cliente para acceder a EJB
Busque EJBTester.java en el explorador de proyectos. Haga clic derecho en la clase EJBTester y seleccionerun file.
Verifique la siguiente salida en la consola de Netbeans.
run:
**********************
Welcome to Book Store
**********************
Options
1. Add Book
2. Exit
Enter Choice: 1
Enter book name: Learn Java
**********************
Welcome to Book Store
**********************
Options
1. Add Book
2. Exit
Enter Choice: 2
Book(s) entered so far: 1
1. Learn Java
BUILD SUCCESSFUL (total time: 13 seconds)
Salida de registro del servidor de aplicaciones JBoss
Verifique la siguiente salida en la salida de registro del servidor de aplicaciones JBoss.
....
09:55:40,741 INFO [STDOUT] *** Intercepting call to LibraryBean method: addBook
09:55:43,661 INFO [STDOUT] *** Intercepting call to LibraryBean method: getBooks