Problema com Struts2 + Spring (Injeção de Dependência não localizada)

Boa noite a todos,

Estou criando uma aplicação que se utiliza de Spring e Struts2 (acho que só hoje já abri uns três tópicos sobre - agradeço a todos que me deram uma mão). Estou criando a parte do login - a primeira action do sistema - só que a classe que faz o acesso ao banco de dados não está sendo localizada. O código da action é este:


@Namespace("/login")
public class Login extends ActionSupport{

	private Usuario usuario;
	
	@Inject("UsuarioDAO")
	private UsuarioDAO usuarioDAO;


		@Action(value = "logar", results = {
				@Result(name = "ok", type="redirectAction", params={"actionName", "MenuPrincipal"}),
				@Result(name = "erro", location = "/index.jsp")
		})
	public String login(){
			
			usuario = usuarioDAO.
			logar(usuario.getSenha(), usuario.getLogin());

		if(usuario != null){
			return "ok";	
		}else{
			return "erro";
		}
	}

		public Usuario getUsuario() {
			return usuario;
		}

		public void setUsuario(Usuario usuario) {
			this.usuario = usuario;
		}
		
	
	
}

Eu acredito que o mapeamento esteja sendo realizado pelo Spring, pois no log tem essas informações:


2012-11-10 00:15:49,742 DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory.getSingleton:217 - Creating shared instance of singleton bean 'UsuarioDAO'
2012-11-10 00:15:49,742 DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory.createBean:430 - Creating instance of bean 'UsuarioDAO'
2012-11-10 00:15:49,749 DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory.doCreateBean:504 - Eagerly caching bean 'UsuarioDAO' to allow for resolving potential circular references
2012-11-10 00:15:49,752 DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory.createBean:458 - Finished creating instance of bean 'UsuarioDAO'

A classe UsuarioDAO segue abaixo:


@Qualifier("UsuarioDAO")
//@Repository("UsuarioDAO")
@Component("UsuarioDAO")
public class UsuarioDAO implements ServiceDao<Usuario>{

	static Logger logger = Logger.getLogger(Usuario.class);
	
	
	public UsuarioDAO() {
	}

	private EntityManager em;

	@Inject
	public UsuarioDAO(DAOFactory dao) {
	
		this.em = dao.getEm();
	}
	
	public boolean salvar(Usuario e) {
		logger.debug("Iniciando a tarefa de gravação de uma usuario - Usuario:	" + e.getCodigo());
		if(e.getCodigo() == 0)
			return add(e);
		else
			return alterar(e);
		
	}

	public boolean add(Usuario e) {
		logger.debug("Gravando nova usuario de texto - cod:	" + e.getCodigo());
		EntityTransaction trans = em.getTransaction();
		try{     	
			trans.begin();
			logger.debug("Inserindo usuario");
			em.persist(e);
			trans.commit();
			return true;
		}catch(Exception erro){
			logger.debug("Erro durante a inserção dos dados!!!");
			erro.printStackTrace();
			return false;
		}
	}

	public List<Usuario> getCol() {
		logger.debug("Consultando todas os(as) usuarios");
		try {
			
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findAll", Usuario.class);
			return query.getResultList();
		} catch (NoResultException re) {
			logger.error("A consulta falhou -  Não há resultados", re);
			re.printStackTrace();
			return null;		
		} catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			re.printStackTrace();
			throw re;
		}	}

	public Usuario getProximo(Usuario e) {
		logger.debug("Consultando a próxima usuario após Usuario:	" + e.getCodigo());

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findNext", Usuario.class);
			query.setParameter("Usuario", e.getCodigo());
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há mais áreas de texto após o Usuario:	" + e.getCodigo());
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}		

	}

	public Usuario getAnterior(Usuario e) {
		logger.debug("Consultando a usuario anterior ao código:	" + e.getCodigo());

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findPrevious", Usuario.class);

			query.setParameter("Usuario", e.getCodigo());
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há mais 2s registradas antes do Usuario:	" + e.getCodigo());
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}		
	}

	public Usuario getPorChave(double chave) {
		logger.debug("Consultando a usuario que possua o Usuario:	" + (long)chave);

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findByCodigo", Usuario.class);

			query.setParameter("Usuario", (int)chave);
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há usuario registrada para o Usuario:	" + chave, re);
			re.printStackTrace();
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}		
	}
	
	public Usuario getPrimeiro(){
		logger.debug("Consultando a primeira usuario cadastrada");

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findFirst", Usuario.class);
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há 2s cadastradas no banco de dados");
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}			
		
	}

	public boolean alterar(Usuario e) {
		logger.debug("Iniciando a tarefa de gravação de usuario - Usuario 	" + e.getCodigo());
		EntityTransaction trans = em.getTransaction();
		try{
			trans.begin();

			logger.debug("Atualizando dados na tabela");
			em.merge(e);
			trans.commit();
			return true;
		}catch(Exception erro){
			logger.debug("Erro durante o processo de atualização");
			trans.rollback();
			erro.printStackTrace();
			return false;
		}
	}

	public boolean excluir(Usuario e) {
		logger.debug("Iniciando a exclusão de usuario - Usuario:	" + e.getCodigo());
		EntityTransaction trans = em.getTransaction();
		try{
			
			trans.begin();
			em.remove(e);
			trans.commit();
			logger.debug("Exclusão realizada com sucesso");
			return true;
		}catch(RollbackException er){
			logger.debug("Falha ao excluir\nErro: " + er);
			trans.rollback();
		}
		return false;

	}
	public boolean salvar(Usuario e, Usuario user) {
		logger.debug("Iniciando a tarefa de gravação de uma usuario - Usuario:	" + e.getCodigo());
		if(e.getCodigo() == 0)
			return add(e, user);
		else
			return alterar(e, user);
		
	}

	public boolean add(Usuario e, Usuario user) {
		logger.debug("Gravando nova usuario de texto - cod:	" + e.getCodigo());
		EntityTransaction trans = em.getTransaction();
		try{     	
			trans.begin();
			logger.debug("Inserindo usuario");
			em.persist(e);
			trans.commit();
			return true;
		}catch(Exception erro){
			logger.debug("Erro durante a inserção dos dados!!!");
			erro.printStackTrace();
			return false;
		}
	}

	public List<Usuario> getCol(Usuario user) {
		logger.debug("Consultando todas os(as) usuarios");
		try {
			
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findAll", Usuario.class);
			return query.getResultList();
		} catch (NoResultException re) {
			logger.error("A consulta falhou -  Não há resultados", re);
			re.printStackTrace();
			return null;		
		} catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			re.printStackTrace();
			throw re;
		}	}

	public Usuario getProximo(Usuario e, Usuario user) {
		logger.debug("Consultando a próxima usuario após Usuario:	" + e.getCodigo());

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findNext", Usuario.class);
			query.setParameter("Usuario", e.getCodigo());
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há mais áreas de texto após o Usuario:	" + e.getCodigo());
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}		

	}

	public Usuario getAnterior(Usuario e, Usuario user) {
		logger.debug("Consultando a usuario anterior ao código:	" + e.getCodigo());

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findPrevious", Usuario.class);

			query.setParameter("Usuario", e.getCodigo());
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há mais 2s registradas antes do Usuario:	" + e.getCodigo());
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}		
	}
	
	public Usuario logar(String senha, String login){
		
		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findPorLoginSenha", Usuario.class);

			query.setParameter("login", login);
			query.setParameter("senha", senha);
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			
			re.printStackTrace();
			return null;
		}catch (RuntimeException re) {
			
			throw re;
		}		

	}

	public Usuario getPorChave(double chave, Usuario user) {
		logger.debug("Consultando a usuario que possua o Usuario:	" + (long)chave);

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findByCodigo", Usuario.class);

			query.setParameter("Usuario", (int)chave);
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há usuario registrada para o Usuario:	" + chave, re);
			re.printStackTrace();
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}		
	}
	
	public Usuario getPrimeiro(Usuario user){
		logger.debug("Consultando a primeira usuario cadastrada");

		try {
			TypedQuery<Usuario> query = em.createNamedQuery("Usuario.findFirst", Usuario.class);
			query.setMaxResults(1);
			return (Usuario) query.getSingleResult();
		}catch(NoResultException re){
			logger.debug("Não há 2s cadastradas no banco de dados");
			return null;
		}catch (RuntimeException re) {
			logger.error("A consulta falhou - Falha em tempo de execução", re);
			throw re;
		}			
		
	}

	public boolean alterar(Usuario e, Usuario user) {
		logger.debug("Iniciando a tarefa de gravação de usuario - Usuario 	" + e.getCodigo());
		EntityTransaction trans = em.getTransaction();
		try{
			trans.begin();

			logger.debug("Atualizando dados na tabela");
			em.merge(e);
			trans.commit();
			return true;
		}catch(Exception erro){
			logger.debug("Erro durante o processo de atualização");
			trans.rollback();
			erro.printStackTrace();
			return false;
		}
	}

	public boolean excluir(Usuario e, Usuario user) {
		logger.debug("Iniciando a exclusão de usuario - Usuario:	" + e.getCodigo());
		EntityTransaction trans = em.getTransaction();
		try{
			
			trans.begin();
			em.remove(e);
			trans.commit();
			logger.debug("Exclusão realizada com sucesso");
			return true;
		}catch(RollbackException er){
			logger.debug("Falha ao excluir\nErro: " + er);
			trans.rollback();
		}
		return false;

	}

}

E por fim o erro que o struts gera:

Struts Problem Report

Struts has detected an unhandled exception:
Messages: 	

    No mapping found for dependency [type=jubernate.dao.UsuarioDAO, name='default'] in private jubernate.dao.UsuarioDAO jubernate.actions.Login.usuarioDAO.
    com.opensymphony.xwork2.inject.ContainerImpl$MissingDependencyException: No mapping found for dependency [type=jubernate.dao.UsuarioDAO, name='default'] in private jubernate.dao.UsuarioDAO jubernate.actions.Login.usuarioDAO.
    Unable to instantiate Action, jubernate.actions.Login, defined for 'logar' in namespace '/login'com.opensymphony.xwork2.inject.ContainerImpl$MissingDependencyException: No mapping found for dependency [type=jubernate.dao.UsuarioDAO, name='default'] in private jubernate.dao.UsuarioDAO jubernate.actions.Login.usuarioDAO.

File: 	com/opensymphony/xwork2/inject/ContainerImpl.java
Line number: 	187

Outra coisa que me faz acreditar que o spring esteja mapeando é que no log aparece informações do hibernate, que é acessado somente pela DAOFactory, a qual é injetada na usuárioDAO.
Desculpem esta quantidade de dúvidas que tenho, ainda não consegui pegar essa história de injeção de dependências.

Agradeço toda a ajuda que puderem dar.

Inté…

Bom dia, não sei se tem haver com alguma coisa, mas o spring me obrigou a criar um construtor padrão (aquele vazio) em todas as minhas classes anotadas. E realmente todas as classe são pegas pelo Spring.

Fiz uma gambiarra que deu certo. Transformei a classe DAOFactory, que faz a conexão com o banco através do hibernate, em estática e nos construtores default, aqueles em branco que o spring me fez criar, fiz essa classe carregar uma estância do entity manager para cada classe.

Daí o sistema parou de reclamar.

Inté…

Obs: Se alguém tiver uma solução melhor e puder me falar, eu agradeço.