Bean Scopes se refiere al ciclo de vida de Bean, lo que significa cuándo se creará una instancia del objeto de Bean, cuánto tiempo vive ese objeto y cuántos objetos se crearán para ese bean a lo largo. Básicamente, controla la creación de instancias del bean y es administrado por el contenedor de primavera.
Ámbitos de Bean en Spring
El marco Spring proporciona cinco ámbitos para un frijol. Podemos usar tres de ellos solo en el contexto de Spring ApplicationContext compatible con la web y el resto de los dos está disponible tanto para el contenedor IoC como para el contenedor Spring-MVC . Los siguientes son los diferentes alcances provistos para un bean:
- Singleton: solo se creará una instancia para una sola definición de bean por contenedor Spring IoC y se compartirá el mismo objeto para cada solicitud realizada para ese bean.
- Prototipo: se creará una nueva instancia para una sola definición de bean cada vez que se realice una solicitud para ese bean.
- Solicitud: se creará una nueva instancia para una sola definición de bean cada vez que se realice una solicitud HTTP para ese bean. Pero solo es válido en el contexto de un Spring ApplicationContext compatible con la web.
- Sesión: limita una definición de bean individual al ciclo de vida de una sesión HTTP. Pero solo es válido en el contexto de un Spring ApplicationContext compatible con la web.
- Sesión global: limita una definición de bean única al ciclo de vida de una sesión HTTP global. También solo es válido en el contexto de un Spring ApplicationContext compatible con la web.
Veamos algunos de ellos en detalle:
Alcance único:
Si el alcance es un singleton, solo se instanciará una instancia de ese bean por contenedor Spring IoC y se compartirá la misma instancia para cada solicitud. Es entonces cuando el alcance de un bean se declara singleton, luego, cada vez que se realiza una nueva solicitud para ese bean, el contenedor Spring IOC primero verifica si una instancia de ese bean ya se creó o no. Si ya se creó, el contenedor IOC devuelve la misma instancia; de lo contrario, crea una nueva instancia de ese bean solo en la primera solicitud. Por defecto, el alcance de un bean es un singleton.
Entendamos este alcance con un ejemplo.
- Paso 1: Primero creemos un bean (es decir), la columna vertebral de la aplicación en Spring Framework.
Java
// Java program to illustrate a bean // created in the spring framework package bean; public class HelloWorld { public String name; // Create a setter method to // set the value passed by user public void setName(String name) { this.name = name; } // Create a getter method so that // the user can get the set value public String getName() { return name; } }
- Paso 2: Ahora, escribimos un archivo de configuración Spring XML “spring.xml” y configuramos el bean definido anteriormente.
XML
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN 2.0//EN" "http://www.springframework.org/dtd/spring-beans-2.0.dtd"> <beans> <!--configure the bean HelloWorld.java and declare its scope--> < bean id = "hw" class= "bean.HelloWorld" scope = "singleton" / > </beans>
- Paso 3: finalmente, escriba una clase de controlador «Client.java» para solicitar el bean anterior.
Java
// Java program to illustrate // the client to perform the // request to the defined bean package driver; import org.springframework .context.ApplicationContext; import org.springframework .context.support .ClassPathXmlApplicationContext; import bean.HelloWorld; // Client Class to request the // above defined bean public class Client { public static void main(String[] args) { // Load the Spring XML configuration // file into IoC container ApplicationContext ap = new ClassPathXmlApplicationContext( "resources/spring.xml"); // Get the "HelloWorld" bean object // and call getName() method HelloWorld Geeks1 = (HelloWorld)ap.getBean("hw"); // Set the name Geeks1.setName("Geeks1"); System.out.println( "Hello object (hello1)" + " Your name is: " + Geeks1.getName()); // Get another "HelloWorld" bean object // and call getName() method HelloWorld Geeks2 = (HelloWorld)ap.getBean("hw"); System.out.println( "Hello object (hello2)" + " Your name is: " + Geeks2.getName()); // Now compare the references to see // whether they are pointing to the // same object or different object System.out.println( "'Geeks1' and 'Geeks2'" + " are referring" + "to the same object: " + (Geeks1 == Geeks2)); // Print the address of both // object Geeks1 and Geeks2 System.out.println( "Address of object Geeks1: " + Geeks1); System.out.println( "Address of object Geeks2: " + Geeks2); } }
- Producción:
Hello object (hello1) Your name is: Geeks1 Hello object (hello2) Your name is: Geeks1 'Geeks1' and 'Geeks2' are referring to the same object: true Address of object Geeks1: bean.HelloWorld@627551fb Address of object Geeks2: bean.HelloWorld@627551fb
- Explicación: cuando llamamos al método getName() utilizando la referencia de ‘Geeks1’ y ‘Geeks2’, obtenemos los mismos resultados. Esto significa que ambas referencias están llamando al método getName() del mismo objeto. Además, cuando comparamos la referencia ‘Geeks1’ y ‘Geeks2’, la salida es «verdadera», lo que significa que el mismo objeto se comparte entre ‘Geeks1’ y ‘Geeks2’. Entonces, está claro que se crea una nueva instancia de bean (HelloWorld) cuando realizamos la solicitud por primera vez y para cada nueva solicitud, se comparte el mismo objeto.
Alcance del prototipo:
Si el alcance se declara prototipo , entonces el contenedor IOC de primavera creará una nueva instancia de ese bean cada vez que se realice una solicitud para ese bean específico. Se puede realizar una solicitud a la instancia del bean mediante programación utilizando el método getBean() o mediante XML para inyección de dependencia de tipo secundario. En general, usamos el ámbito prototipo para todos los beans con estado, mientras que el ámbito único se utiliza para los beans sin estado.
Entendamos este alcance con un ejemplo:
- Paso 1: primero vamos a crear un bean (es decir), la columna vertebral de la aplicación en el marco de Spring.
Java
// Java program to illustrate a bean // created in the spring framework package bean; public class HelloWorld { public String name; // Create a setter method to // set the value passed by user public void setName(String name) { this.name = name; } // Create a getter method so that // the user can get the set value public String getName() { return name; } }
- Paso 2: Ahora, escribimos un archivo de configuración Spring XML “spring.xml” y configuramos el bean definido anteriormente.
XML
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN 2.0//EN" "http://www.springframework.org/dtd/spring-beans-2.0.dtd"> < beans> <!--configure the bean HelloWorld.java and declare its scope--> < bean id = "hw" class = "bean.HelloWorld" scope = "prototype" / > </ beans>
- Paso 3: finalmente, escriba una clase de controlador «Client.java» para solicitar el bean anterior.
Java
// Java program to illustrate // the client to perform the // request to the defined bean package driver; import org.springframework .context.ApplicationContext; import org.springframework.context.support .ClassPathXmlApplicationContext; import bean.HelloWorld; public class Client { public static void main(String[] args) { // Load the Spring XML configuration // file into IoC container ApplicationContext ap = new ClassPathXmlApplicationContext( "resources/spring.xml"); // Get the "HelloWorld" bean object // and call getName() method HelloWorld Geeks1 = (HelloWorld)ap.getBean("hw"); // Set the name Geeks1.setName("Geeks1"); System.out.println( "Hello object (hello1)" + " Your name is: " + Geeks1.getName()); // Get another "HelloWorld" bean object // and call getName() method HelloWorld Geeks2 = (HelloWorld)ap.getBean("hw"); System.out.println( "Hello object (hello2)" + "Your name is: " + Geeks2.getName()); // Now compare the references to see // whether they are pointing to the // same object or different object System.out.println( "'Geeks1' and 'Geeks2'" + "are referring " + "to the same object: " + (Geeks1 == Geeks2)); // Print the address of both // object Geeks1 and Geeks2 System.out.println( "Address of object Geeks1: " + Geeks1); System.out.println( "Address of object Geeks2: " + Geeks2); } }
- Producción:
Hello object (hello1) Your name is: Geeks1 Hello object (hello2) Your name is: null 'Geeks1' and 'Geeks2' are referring to the same object: false Address of object Geeks1: bean.HelloWorld@47ef968d Address of object Geeks2: bean.HelloWorld@23e028a9
- Explicación: cuando llamamos al método getName() usando la referencia ‘Geeks1’ y ‘Geeks2’, obtenemos resultados diferentes, lo que significa que la referencia está llamando al método getName() de un objeto diferente. Además, cuando comparamos la referencia ‘Geeks1’ y ‘Geeks2’, el resultado es «falso», lo que significa que ambas referencias se refieren a un objeto diferente. Entonces, está claro que se crea una nueva instancia de bean (HelloWorld) en cada solicitud realizada para este bean.
Diferencia entre Singleton y prototipo
único | Prototipo |
---|---|
Solo se crea una instancia para una sola definición de bean por contenedor Spring IoC | Se crea una nueva instancia para una sola definición de bean cada vez que se realiza una solicitud para ese bean. |
Se comparte el mismo objeto para cada solicitud realizada para ese bean. es decir, se devuelve el mismo objeto cada vez que se inyecta. | Para cada nueva solicitud se crea una nueva instancia. es decir, se crea un nuevo objeto cada vez que se inyecta. |
Por defecto, el alcance de un bean es singleton. Por lo tanto, no necesitamos declarar explícitamente un estado como singleton. | De forma predeterminada, el alcance no es prototipo, por lo que debe declarar el alcance de un estado como prototipo explícitamente. |
El alcance Singleton debe usarse para beans sin estado. | Mientras que el alcance del prototipo se usa para todos los beans que tienen estado |
Publicación traducida automáticamente
Artículo escrito por kashiffiroze95 y traducido por Barcelona Geeks. The original can be accessed here. Licence: CCBY-SA