vc pode mudar da hql.
Exemplo que eu tenho usando JPA, porém é a mesma coisa pra Hibernate.
Query query = em.createQuery("from Contato as c left outer join fetch c.telefones join fetch c.status where c.dtProximoContato <= ? and c.status.id = 1");
O principio do Lazy e Eager, um é o tal preguiçozo que vc. tem que pedir pra ele trazer e o outro já traz o relacionamento entre a entidade. Eu vejo, que para mapeamentos OneToMany podemos usar Lazy e para ManyToOne, Eager. Tenho feito os relacionamento via Annotations e desconheço uma forma de fazer isso runtime. A sugestão do “marcelo_mococa” funciona para querys, mas se vc. precisar remover os objetos na forma de CASQUEDE.
Mudar em Runtime eu não sei se tem jeito, eu acho que não. Acho que a melhor opção é deixar o relacionamento definido como LAZY, claro que isso depende de caso a caso, e quando você precisar que os relacionamentos venham carregados (EAGER) utilizar um método que busca a entidade através de uma HQL usando o join fetch como o Marcelo falou.
O mapeamento de relacionamentos c/ JPA já traz definido a estratégia de fetching (lazy/eager), por padrão, no caso das annotations para coleções. Isso pode ser sobrescrito, via atributo “fetch”, e ainda “aprimorado”, com annotations específicas do Hibernate (caso ele seja o seu persistence provider).
Esse debate de inicialização de relacionamentos em tempo de execução é antigo, e separa a maioria dos desenvolvedores em duas “trincheiras”: Uns defendem que é preciso desenvolver mecanismos de “fetching transparente”, ou seja, o próprio hibernate inicializa relacionamentos lazy quando eles são requeridos, abrindo uma nova sessão se for necessário. Outros, com os quais eu particularmente concordo, defendem que a responsabilidade de inicializar relacionamentos é do próprio desenvolvedor, em seu caso de uso.
Usar o left join é uma boa; Você busca os objetos no grafo no momento em que precisa deles, e usa apenas proxies de objetos em memória na maior parte do tempo. Entretanto, quando você não tem o luxo de efetuar uma busca na camada onde está programando, o jeito é apelar pela inicialização via Hibernate.initialize(), uso de uma sessão corrente (e abertura/manutenção de uma nova, caso necessário), e outros recursos.
Uma proposta interessante que surgiu entre os que defendem que a inicialização deve ser transparente é o =http://h3t.sourceforge.net/H3T. Mas ele tem problemas que você vai identificar assim que tentar usar (i.e, uso “duvidoso” de AOP). Além de ser um projeto com baixa atividade, sem test cases maduros, etc…