我正在尝试创建一个可以帮助我减少样板代码的泛型类。我正在使用Spring 3(MVC)和Hibernate 4。
类看起来像这样:
@Repository("AutoComplete")
public class AutoComplete<T extends Serializable> implements IAutoComplete {
@Autowired
private SessionFactory sessionFactory;
private Class<T> entity;
public AutoComplete(Class<T> entity) {
this.setEntity(entity);
}
@Transactional(readOnly=true)
public List<String> getAllFTS(String searchTerm) {
Session session = sessionFactory.getCurrentSession();
return null;
}
public Class<T> getEntity() {
return entity;
}
public void setEntity(Class<T> entity) {
this.entity = entity;
}
}
我正在实例化这样的bean:
IAutoComplete place = new AutoComplete<Place>(Place.class);
place.getAllFTS("something");
如果我运行代码,我得到“没有找到默认构造函数”的异常。如果我添加一个默认构造函数,我在这一行得到空指针异常:
Session session = sessionFactory.getCurrentSession();
为什么会这样,我该如何解决这个问题呢?我猜这个问题是因为bean没有被Spring本身实例化,所以它不能自动装配字段。我想自己实例化bean,但如果可能的话仍然可以进行Spring管理。
答案 0 :(得分:1)
确保您在xml bean定义文件中添加了<context:component-scan base-package='package name'>
。
由于@Repository是构造型,Spring容器将进行类路径扫描,添加它的bean定义并注入它的依赖项。
稍后您可以使用bean名称(AutoComplete)从ApplicationContext获取bean的句柄。
答案 1 :(得分:0)
Spring容器会为你实例化这个bean,在这种情况下,会注入sessionFactory。您可以使用自己的代码实例化此bean:new AutoComplete(),当然sessionFactory为null。
答案 2 :(得分:0)
永远不要使用具有@Autowired注释的字段来实例化类。如果您这样做,将导致null。你应该做的是你应该获得对Spring的ApplicationContext的引用(你可以通过实现ApplicationContextAware接口来实现)并在你的AutoComplete类的默认构造函数中使用以下代码。
public AutoComplete() {
sessionFactory = (SessionFactory) applicationContext.getBean("sessionFactory");
}
使用Spring时的一个主要做法是自己消除对象的即时消息。我们应该在spring配置中指定所有内容,以便Spring在需要时为我们实例化对象。但在您使用Generic方法的情况下,您需要。