Spring Framework is built on the Inversion of Control (IOC) principle. Dependency injection is the technique to implement IoC in applications. This article is aimed to explain core concepts of Spring IoC container and Spring Bean with example programs.

  1. Spring IoC Container
  2. Spring Bean
  3. Spring Bean Scopes
  4. Spring Bean Configuration
  5. Spring IoC and Bean Example Project
    1. XML Based Bean Configuration
    2. Annotation Based Bean Configuration
    3. Java Based Bean Configuration

Spring IoC Container

Inversion of Control is the mechanism to achieve loose-coupling between Objects dependencies. To achieve loose coupling and dynamic binding of the objects at runtime, the objects define their dependencies that are being injected by other assembler objects. Spring IoC container is the program that injects dependencies into an object and make it ready for our use. We have already looked how we can use Spring Dependency Injection to implement IoC in our applications.

Spring Framework IoC container classes are part of org.springframework.beans and org.springframework.context packages and provides us different ways to decouple the object dependencies.

 

BeanFactory is the root interface of Spring IoC container. ApplicationContext is the child interface of BeanFactory interface that provide Spring’s AOP features, internationalization etc. Some of the useful child-interfaces of ApplicationContext are ConfigurableApplicationContext and WebApplicationContext. Spring Framework provides a number of useful ApplicationContext implementation classes that we can use to get the context and then the Spring Bean.

Some of the useful ApplicationContext implementations that we use are;

  • AnnotationConfigApplicationContext: If we are using Spring in standalone java applications and using annotations for Configuration, then we can use this to initialize the container and get the bean objects.
  • ClassPathXmlApplicationContext: If we have spring bean configuration xml file in standalone application, then we can use this class to load the file and get the container object.
  • FileSystemXmlApplicationContext: This is similar to ClassPathXmlApplicationContext except that the xml configuration file can be loaded from anywhere in the file system.
  • AnnotationConfigWebApplicationContext and XmlWebApplicationContext for web applications.

Usually if you are working on Spring MVC application and your application is configured to use Spring Framework, Spring IoC container gets initialized when application starts and when a bean is requested, the dependencies are injected automatically.

However for standalone application, you need to initialize the container somewhere in the application and then use it to get the spring beans.

Spring Bean

Spring Bean is nothing special, any object in the Spring framework that we initialize through Spring container is called Spring Bean. Any normal Java POJO class can be a Spring Bean if it’s configured to be initialized via container by providing configuration metadata information.

Spring Bean Scopes

There are five scopes defined for Spring Beans.

  1. singleton – Only one instance of the bean will be created for each container. This is the default scope for the spring beans. While using this scope, make sure bean doesn’t have shared instance variables otherwise it might lead to data inconsistency issues.
  2. prototype – A new instance will be created every time the bean is requested.
  3. request – This is same as prototype scope, however it’s meant to be used for web applications. A new instance of the bean will be created for each HTTP request.
  4. session – A new bean will be created for each HTTP session by the container.
  5. global-session – This is used to create global session beans for Portlet applications.

Spring Framework is extendable and we can create our own scopes too, however most of the times we are good with the scopes provided by the framework.

Spring Bean Configuration

Spring Framework provide three ways to configure beans to be used in the application.

  1. Annotation Based Configuration – By using @Service or @Component annotations. Scope details can be provided with @Scope annotation.
  2. XML Based Configuration – By creating Spring Configuration XML file to configure the beans. If you are using Spring MVC framework, the xml based configuration can be loaded automatically by writing some boiler plate code in web.xml file.
  3. Java Based Configuration – Starting from Spring 3.0, we can configure Spring beans using java programs. Some important annotations used for java based configuration are @Configuration, @ComponentScan and @Bean.

Spring IoC and Bean Example Project

Let’s look at the different aspects of Spring IoC container and Spring Bean configurations with a simple Spring project.

For my example, I am creating Spring MVC project in Spring Tool Suite. If you are new to Spring Tool Suite and Spring MVC, please read Spring MVC Tutorial with Spring Tool Suite.

The final project structure looks like below image.

Let’s look at different components one by one.

XML Based Bean Configuration

MyBean is a simple Java POJO class.

package com.journaldev.spring.beans;

public class MyBean {

    private String name;

    public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
} }

MyBean.java

 

Spring Configuration XML File

<?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="http://www.springframework.org/schema/mvc"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:beans="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> <!-- DispatcherServlet Context: defines this servlet's request-processing infrastructure --> <!-- Enables the Spring MVC @Controller programming model -->
<annotation-driven /> <!-- Handles HTTP GET requests for /resources/** by efficiently serving up static resources in the ${webappRoot}/resources directory -->
<resources mapping="/resources/**" location="/resources/" /> <!-- Resolves views selected for rendering by @Controllers to .jsp resources in the /WEB-INF/views directory -->
<beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<beans:property name="prefix" value="/WEB-INF/views/" />
<beans:property name="suffix" value=".jsp" />
</beans:bean> <context:component-scan base-package="com.journaldev.spring" /> <beans:bean name="myBean" class="com.journaldev.spring.beans.MyBean" scope="singleton" ></beans:bean> </beans:beans>

servlet-context.xml

Notice that MyBean is configured using bean element with scope as singleton.

Annotation Based Bean Configuration

package com.journaldev.spring.beans;

import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Service;
import org.springframework.web.context.WebApplicationContext; @Service
@Scope(WebApplicationContext.SCOPE_REQUEST)
public class MyAnnotatedBean { private int empId; public int getEmpId() {
return empId;
} public void setEmpId(int empId) {
this.empId = empId;
} }

MyAnnotatedBean.java

MyAnnotatedBean is configured using @Service and scope is set to Request.

Controller Class

HomeController class will handle the HTTP requests for the home page of the application. We will inject our Spring beans to this controller class through WebApplicationContext container.

package com.journaldev.spring.controller;

import java.text.DateFormat;
import java.util.Date;
import java.util.Locale; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod; import com.journaldev.spring.beans.MyAnnotatedBean;
import com.journaldev.spring.beans.MyBean; @Controller
@Scope("request")
public class HomeController { private MyBean myBean; private MyAnnotatedBean myAnnotatedBean; @Autowired
public void setMyBean(MyBean myBean) {
this.myBean = myBean;
} @Autowired
public void setMyAnnotatedBean(MyAnnotatedBean obj) {
this.myAnnotatedBean = obj;
} /**
* Simply selects the home view to render by returning its name.
*/
@RequestMapping(value = "/", method = RequestMethod.GET)
public String home(Locale locale, Model model) {
System.out.println("MyBean hashcode="+myBean.hashCode());
System.out.println("MyAnnotatedBean hashcode="+myAnnotatedBean.hashCode()); Date date = new Date();
DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale); String formattedDate = dateFormat.format(date); model.addAttribute("serverTime", formattedDate ); return "home";
} }

HomeController.java

Deployment Descriptor

We need to configure our application for Spring Framework, so that the configuration metadata will get loaded and context will be initialized.

<?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"> <!-- The definition of the Root Spring Container shared by all Servlets and Filters -->
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/root-context.xml</param-value>
</context-param> <!-- Creates the Spring Container shared by all Servlets and Filters -->
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener> <!-- Processes application requests -->
<servlet>
<servlet-name>appServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/appServlet/servlet-context.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet> <servlet-mapping>
<servlet-name>appServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping> </web-app>

web.xml

Almost all the configuration above is boiler-plate code generated by STS tool automatically.

Run the Web Application

Now when you will launch the web application, the home page will get loaded and in the console following logs will be printed when you refresh the page multiple times.

MyBean hashcode=118267258
MyAnnotatedBean hashcode=1703899856
MyBean hashcode=118267258
MyAnnotatedBean hashcode=1115599742
MyBean hashcode=118267258
MyAnnotatedBean hashcode=516457106

Notice that MyBean is configured to be singleton, so the container is always returning the same instance and hashcode is always same. Similarly for each request, a new instance of MyAnnotatedBean is created with different hashcode.

Java Based Bean Configuration

For standalone applications, we can use annotation based as well as xml based configuration. The only requirement is to initialize the context somewhere in the program before we use it.

package com.journaldev.spring.main;

import java.util.Date;

public class MyService {

    public void log(String msg){
System.out.println(new Date()+"::"+msg);
}
}

MyService.java

MyService is a simple java class with some methods.

package com.journaldev.spring.main;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration; @Configuration
@ComponentScan(value="com.journaldev.spring.main")
public class MyConfiguration { @Bean
public MyService getService(){
return new MyService();
}
}

MyConfiguration.java

The annotation based configuration class that will be used to initialize the Spring container.

package com.journaldev.spring.main;

import org.springframework.context.annotation.AnnotationConfigApplicationContext;

public class MyMainClass {

    public static void main(String[] args) {

        AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext(
MyConfiguration.class);
MyService service = ctx.getBean(MyService.class); service.log("Hi"); MyService newService = ctx.getBean(MyService.class);
System.out.println("service hashcode="+service.hashCode());
System.out.println("newService hashcode="+newService.hashCode());
ctx.close();
} }

MyMainClass.java

A simple test program where we are initializing the AnnotationConfigApplicationContext context and then using getBean() method to get the instance of MyService.

Notice that I am calling getBean method two times and printing the hashcode. Since there is no scope defined for MyService, it should be singleton and hence hashcode should be the same for both the instances.

When we run the above application, we get following console output confirming our understanding.

Sat Dec 28 22:49:18 PST 2013::Hi
service hashcode=678984726
newService hashcode=678984726

If you are looking for XML based configuration, just create the Spring XML config file and then initialize the context with following code snippet.

ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext(
"applicationContext.xml");
MyService app = context.getBean(MyService.class);

That’s all for the Spring IoC container and Spring Bean Scopes and Configuration details. We will look into some more features of Spring Beans in future posts. Download the Spring Bean example project from below link and play around with it for better understanding.

Spring IoC Container and Spring Bean Example Tutorial的更多相关文章

  1. Spring IoC Container源码分析(二)-bean初始化流程

    准备 Person实例 @Data public class Person { private String name; private int age; } xml bean配置 <?xml ...

  2. Spring IOC Container

    All the notes are from Spring Framework 5 Doc. 一.Introduction to the Spring IOC Container and Beans ...

  3. Spring IOC Container原理解析

    Spring Framework 之 IOC IOC.DI基础概念 关于IOC和DI大家都不陌生,我们直接上martin fowler的原文,里面已经有DI的例子和spring的使用示例 <In ...

  4. Spring IOC(八)bean 的创建

    Spring IOC(八)bean 的创建 Spring 系列目录(https://www.cnblogs.com/binarylei/p/10198698.html) 参考: 每天用心记录一点点.内 ...

  5. Spring IoC源码解析——Bean的创建和初始化

    Spring介绍 Spring(http://spring.io/)是一个轻量级的Java 开发框架,同时也是轻量级的IoC和AOP的容器框架,主要是针对JavaBean的生命周期进行管理的轻量级容器 ...

  6. 从启动日志看Spring IOC的初始化和Bean生命周期

    一.Tomcat中启动IoC容器的日志 启动Tomcat等容器时,控制台每次都打印出一些日志. 最近刚好在研究Spring源码,所以换个角度,从启动日志来简单的看看Spring的初始化过程! 以下是T ...

  7. Spring IOC容器分析(4) -- bean创建获取完整流程

    上节探讨了Spring IOC容器中getBean方法,下面我们将自行编写测试用例,深入跟踪分析bean对象创建过程. 测试环境创建 测试示例代码如下: package org.springframe ...

  8. Spring IOC 一——容器装配Bean的简单使用

    下文:SpringIOC 二-- 容器 和 Bean的深入理解 写在前面 这篇文章去年写的,缘起于去年某段时间被领导临时"抓壮丁"般的叫过去做java开发,然后在网上找了一个 Sp ...

  9. Spring IOC(3)----bean实例化

    前面一节说到invokeBeanFactoryPostProcessors方法的调用来注册bean定义,这次来看看finishBeanFactoryInitialization这个方法实例化非懒加载的 ...

随机推荐

  1. 洛谷 P4139 上帝与集合的正确用法 解题报告

    P4139 上帝与集合的正确用法 题目描述 根据一些书上的记载,上帝的一次失败的创世经历是这样的: 第一天, 上帝创造了一个世界的基本元素,称做"元". 第二天, 上帝创造了一个新 ...

  2. sql或oracle插入数据时进行md5加密

    1.sql简单直接调用: SELECT hashbytes(') ; 2.oracle要复杂些 首写需要建函数: CREATE OR REPLACE FUNCTION MD5( passwd IN V ...

  3. 从K近邻算法、距离度量谈到KD树、SIFT+BBF算法

    转载自:http://blog.csdn.net/v_july_v/article/details/8203674/ 从K近邻算法.距离度量谈到KD树.SIFT+BBF算法 前言 前两日,在微博上说: ...

  4. College student reflects on getting started in open source(二)

    My budding interest grew into a full-time obsession: creating artwork on my clunky, laggy laptop. 我萌 ...

  5. 除了IE浏览器,其他浏览器都联不上网怎么办~转载百度经验

    百度师傅最快的到家服务,最优质的电脑清灰 百度经验:jingyan.baidu.com 有个网友遇到一个非常奇怪的上网问题,刚才始,发现QQ不能登录,后来接着发现火狐浏览器也打不开网页,刚开始,以为只 ...

  6. Access数据库 INSERT INTO 失败

    一次操作Access数据库,插入一条数据,总是失败,如下: 通过赋值,一个字段一个字段的排查,最终确定是UserAge字段处有问题. 最初,UserAge字段是 %d 类型的,赋值20,可成功插入数据 ...

  7. Android BroadcastReceiver使用

    1. 介绍 BroadcastReceiver用于接收广播事件(Intent), 是Android四大组件之一 2. 使用 2.1  实现广播接收类 实现一个广播收类继承BroadcastReceiv ...

  8. mysq 中 information_schema 库

    information_schema这个库,这个在mysql安装时就有了,提供了访问数据库元数据的方式.那什么是元数据库呢?元数据是关于数据的数据,如数据库名或表名,列的数据类型,或访问权限等.有些时 ...

  9. ZOJ 3820:Building Fire Stations(树的直径 Grade C)

    题意: n个点的树,边长全为1,求找出两个点,使得树上离这两个点距离最远的那个点,到这两个点(中某个点就行)的距离最小. 思路: 求树直径,找中点,删除中间那条边(如果直径上点数为奇数,则删任何一侧都 ...

  10. jmeter 多机负载压测与服务器性能监测

    环境: jmeter: apache-jmeter-3.3 jdk: 负载生成: 被测机: 一. 多机负载压测: 概述: 1.修改jmeter.properties配置文件 remote_hosts= ...