Reputation: 79
Dao tier. I have abstract jpa dao interface, extended interface, and I added abstract implementation, from which I extend other real used implementations. These classes as follows:
public interface AbstractDao<E> {
E findById(Long id);
List<E> findAll();
void save(E entity);
void update(E entity);
void delete(E entity);
void deleteById(Long entityId);
}
public interface UserDao extends AbstractDao<User> {
}
public abstract class AbstractDaoImpl<E> implements AbstractDao<E> {
private final Class<E> clazz;
@PersistenceContext
protected EntityManager entityManager;
public AbstractDaoImpl(Class<E> clazz) {
this.clazz = clazz;
}
@Override
public E findById(Long id) {
return entityManager.find(clazz, id);
}
@SuppressWarnings("unchecked")
@Override
public List<E> findAll() {
return entityManager
.createQuery("from " + clazz.getName())
.getResultList();
}
@Override
public void save(E entity){
entityManager.persist(entity);
}
@Override
public void update(E entity){
entityManager.merge(entity);
}
@Override
public void delete(E entity) {
entityManager.remove(entity);
}
@Override
public void deleteById(Long entityId){
E entity = findById(entityId);
delete(entity);
}
}
@Repository
public class UserDaoImpl extends AbstractDaoImpl<User> implements UserDao {
public UserDaoImpl() {
super(User.class);
}
}
Service tier. Here I also have abstract service interface, one extended interface (UserService) and its abstract and real implementations:
public interface AbstractService<E, DTO> {
E findById(Long id);
List<E> findAll();
void save(E entity);
void update(E entity);
void delete(E entity);
void deleteById(Long entityId);
DTO convertToDTO(E entity);
}
public interface UserService extends AbstractService<User, UserDTO> {
}
@Getter @Setter @AllArgsConstructor
public abstract class AbstractServiceImpl<E, D extends AbstractDao<E>, DTO> implements AbstractService<E, DTO> {
private D dao;
private ModelMapper mapper;
@Override
public E findById(Long id) {
return dao.findById(id);
}
@Override
public List<E> findAll() {
return dao.findAll();
}
@Override
public void save(E entity) {
dao.save(entity);
}
@Override
public void update(E entity) {
dao.update(entity);
}
@Override
public void delete(E entity) {
dao.delete(entity);
}
@Override
public void deleteById(Long entityId) {
dao.deleteById(entityId);
}
}
@Service
public class UserServiceImpl extends AbstractServiceImpl<User, UserDao, UserDTO> implements UserService {
@Autowired
public UserServiceImpl(UserDao dao, ModelMapper mapper) {
super(dao, mapper);
}
@Override
public UserDTO convertToDTO(User entity) {
return getMapper().map(entity, UserDTO.class);
}
}
In my real project I got many extended interfaces from AbstractDao and AbstractServie. You can see the actual hierarchy:
I can't understand why spring can't create @Service annotated beans and autowire those in my Controllers. Any help would be appreciated.
Upvotes: 1
Views: 176
Reputation: 216
I took the liberty to look into your project in github https://github.com/tuanalexeu/JavaSchoolFinalTask
The problem is how you initialize your spring contexts, The AppConfig context is not read at all. This context has all your configurations.
By modifying your initializer to include your AppConfig as root, all beans should be present in the same context. (You can also choose to have parent -> child contexts as well, but that too should be done in the initializer). Hope it helps. Good luck.
public class MainWebAppInitializer implements WebApplicationInitializer {
@Override
public void onStartup(final ServletContext sc) throws ServletException {
AnnotationConfigWebApplicationContext root = new AnnotationConfigWebApplicationContext();
root.register(AppConfig.class);
Dynamic servlet = sc.addServlet("dispatcher", new DispatcherServlet(root));
servlet.setLoadOnStartup(1);
servlet.addMapping("/");
sc.addListener(new ContextLoaderListener(root));
sc.addFilter("securityFilter", new DelegatingFilterProxy("springSecurityFilterChain"))
.addMappingForUrlPatterns(null, false, "/*");
}
}
Upvotes: 1