Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

@Autowired and @Service working from controller but not from a different package

I need help understanding the concept behind @Autowired and @Service. I have a DAO defined with @Service and controller with @Autowired and everything seems fine, however, I use the same @Autowired in a different class then it does not work.

Example:

Service

@Service
public class MyService {
    private JdbcTemplate jdbcTemplate;

    @Autowired
    public void setDataSource (DataSource myDataSource) {
        this.jdbcTemplate = new JdbcTemplate(myDataSource);
    } 

    public void testUpdate(){
            jdbcTemplate.update("some query");
    }
}

Controller

package com.springtest.mywork.controller;

@Controller
@RequestMapping(value = "/test.html")
public class MyController
{
  @Autowired
  MyService myService;

  @RequestMapping(method = RequestMethod.GET)
  public String test(Model model)
  {
    systemsService.testUpdate();
    return "view/test";
  }
}

The above all works fine. However, If I want to use MyService in a POJO then it just doesn't work. Example:

package com.springtest.mywork.pojos;
public class MyPojo {

    @Autowired
    MyService myService;

    public void testFromPojo () {
        myService.someDataAccessMethod(); //myService is still null
    }
}

Spring Config:

<beans>
    <mvc:annotation-driven />
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/WEB-INF/views/"/>
        <property name="suffix" value=".jsp"/>
    </bean>
    <context:component-scan base-package="com.springtest.mywork" />
    <bean id="dataSource" destroy-method="close" class="org.apache.commons.dbcp.BasicDataSource">
        <property name="driverClassName" value="com.mysql.jdbc.Driver" />
        <property name="url" value="jdbc:mysql://127.0.0.1:3306/mydb" />
        <property name="username" value="hello" />
        <property name="password" value="what" />
    </bean>

    <bean name="jdbcTemplate" class="org.springframework.jdbc.core.simple.SimpleJdbcTemplate">
        <constructor-arg ref="dataSource"/>
    </bean>
 </beans>
like image 697
birdy Avatar asked Oct 12 '12 15:10

birdy


People also ask

Why Autowired is not working?

When @Autowired doesn't work. There are several reasons @Autowired might not work. When a new instance is created not by Spring but by for example manually calling a constructor, the instance of the class will not be registered in the Spring context and thus not available for dependency injection.

How does @autowired works internally?

Autowiring happens by placing an instance of one bean into the desired field in an instance of another bean. Both classes should be beans, i.e. they should be defined to live in the application context. What is "living" in the application context? This means that the context instantiates the objects, not you.

Can we use Autowire in controller?

Create a Controller Now lets add our class in our Controller. We have create a simple Controller that has the variable userService that has @autowired annotation. For simplicity, we just made the request method to be GET and that the request parameters are included in the URL.

Can @autowired work without @component?

So the answer is: No, @Autowired does not necessarily mean you must also use @Component . It may be registered with applicationContext. xml or @Configuration+@Bean .


2 Answers

Include this in applicationContext.xml file

<context:annotation-config />
like image 131
NPKR Avatar answered Nov 13 '22 11:11

NPKR


It is because your POJO class is not managed by spring container.

@Autowire annotation will work only those objects which are managed by spring (ie created by the spring container).

In your case the service and controller object are managed by spring, but your POJO class is not managed by spring, that is why the @Autowire is not producing the behavior expected by you.

Another problem I noticed is, you are using the @Service annotation in the DAO layer when spring has the @Repository annotation specifically created for this purpose.

Also it is not desirable to allow spring to manage the POJO classes since normally it will be data storage elements which has to be created outside the container.

like image 30
Arun P Johny Avatar answered Nov 13 '22 11:11

Arun P Johny