泛型依赖注入出现required a single bean, but 2 were found
问题描述
项目使用了tkmybatis,然后在service层使用泛型抽取了公共的CRUD操作,结果在Controller层注入的时候提示
Field dao in com.gisquest.mmp.server.api.service.impl.BaseServiceImpl required a single bean, but 2 were found:
- mmpDesignerAppMapper: defined in file [D:\工作\designer\server-java\mmp-server-api\target\classes\com\gisquest\mmp\server\api\mapper\MmpDesignerAppMapper.class]
- mmpDesignerAppReleaseMapper: defined in file [D:\工作\designer\server-java\mmp-server-api\target\classes\com\gisquest\mmp\server\api\mapper\MmpDesignerAppReleaseMapper.class]
BaseService:
public interface BaseService<T extends BaseDomain> {
int insert(T t,String createBy);
int delete(T t);
int update(T t,String updateBy);
int count(T t);
T selectOne(T t);
PageInfo<T> page(int pageNum, int pageSize, T t);
}
AppService:
public interface AppService<T extends BaseDomain> extends BaseService<T> {
}
AppReleaseService:
public interface AppReleaseService<T extends BaseDomain> extends BaseService<T> {
String getStatus(String id);
}
BaseServiceImpl:
@Service
@Transactional(readOnly = true)
public class BaseServiceImpl<T extends BaseDomain,D extends MyMapper<T>> implements BaseService<T> {
@Autowired
private D dao;
@Override
@Transactional(readOnly = false)
public int insert(T t,String createBy) {
t.setCreateBy(createBy);
t.setCreateDate(new Date());
return dao.insert(t);
}
@Override
@Transactional(readOnly = false)
public int delete(T t) {
return dao.delete(t);
}
@Override
@Transactional(readOnly = false)
public int update(T t,String updateBy) {
t.setUpdateBy(updateBy);
t.setUpdateDate(new Date());
return dao.updateByPrimaryKey(t);
}
@Override
public int count(T t) {
return dao.selectCount(t);
}
@Override
public T selectOne(T t) {
return dao.selectOne(t);
}
@Override
public PageInfo<T> page(int pageNum, int pageSize,T t) {
PageHelper pageHelper = new PageHelper();
pageHelper.startPage(pageNum,pageSize);
PageInfo<T> pageInfo = new PageInfo<>(dao.select(t));
return pageInfo;
}
}
AppServiceImpl:
@Service
@Transactional(readOnly = true)
public class AppServiceImpl extends BaseServiceImpl<MmpDesignerApp, MmpDesignerAppMapper> implements AppService<MmpDesignerApp> {
}
AppReleaseServiceImpl:
@Service
@Transactional(readOnly = true)
public class AppReleaseServiceImpl extends BaseServiceImpl<MmpDesignerAppRelease, MmpDesignerAppReleaseMapper> implements AppReleaseService<MmpDesignerAppRelease> {
@Autowired
private MmpDesignerAppReleaseMapper mapper;
@Override
public String getStatus(String id) {
MmpDesignerAppRelease release = new MmpDesignerAppRelease();
release.setAppid(id);
int i = mapper.selectCount(release);
if(i>0)
return AppStatusConstants.RELEASED.getDesc();
return AppStatusConstants.NOT_RELEASED.getDesc();
}
}
AppController:
public class AppController {
@Autowired
private AppService<MmpDesignerApp> appService;
@Autowired
private AppReleaseService<MmpDesignerAppRelease> releaseService;
解决方法
将不能注入的bean也就是BaseServiceImpl变成抽象类
即在BaseServiceImpl类前加abstract
原因
Exception encountered during context initialization - cancelling refresh attempt:
org.springframework.beans.factory.UnsatisfiedDependencyException:
Error creating bean with name 'baseServiceImpl':
Unsatisfied dependency expressed through field 'dao';
nested exception is
org.springframework.beans.factory.NoUniqueBeanDefinitionException:
No qualifying bean of type 'tk.mybatis.mapper.MyMapper<?>' available:
expected single matching bean but found 3:
tbPostsPostMapper,tbSysUserMapper,tbPostsPostExtendMapper
也就是说在创建一个baseServiceImplbean放入容器时候,发现其类内的一个对象不能被明确指示,不能调用其方法。
ps: 参考文档