[RESOLVIDO] - Merge de classeUm que contem uma classeDois com uma List<classeTres>

Boa tarde galera,

Bem, estou tendo um problema desde sexta-feira, e pode até ser que seja até facil, (sabe quando voce nao acha o erro e chama outra pessoa para que te ajude e de repente ela diz, o problema ta alí ó!!..rsrsrs) mas imagino que por ficar obcecado para que funcione nao estou vendo a solução e nem as pessoas que perguntei entao recorro a vocês superGujianos!

Tenho uma classe Funcionário

public class Funcionario implements Serializable {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @Column(name = "funcodigo", nullable = false)
    private Integer funcodigo;
    @Column(name = "funlogin", length = 30)
    private String funlogin;
    @Column(name = "funsenha", length = 30)
    private String funsenha;
    @JoinColumn(name = "pescodigo", referencedColumnName = "pescodigo", nullable = false)
    @ManyToOne(cascade = CascadeType.MERGE)
    private Pessoa pescodigo = new Pessoa();
    @JoinColumn(name = "carcodigo", referencedColumnName = "carcodigo")
    @ManyToOne
    private Cargo carcodigo = new Cargo();

//Getters and Setters existem mas nao os colocarei para que a visualização se torne mais facil...
}

E uma classe Pessoa

public class Pessoa implements Serializable {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @Column(name = "pescodigo", nullable = false)
    private Integer pescodigo;
    //Campo que define se a pessoa esta Ativa ('A') ou Inativa ('I')
    @Column(name = "pesstatus")
    private Character pesstatus;
    @Column(name = "pesnome", length = 60)
    private String pesnome;
    @Column(name = "pesfantasia", length = 120)
    private String pesfantasia;
    @Column(name = "pesemail", length = 120)
    private String pesemail;
    @Column(name = "pescpfcnpj", length = 18)
    private String pescpfcnpj;
    @Column(name = "pesrgie", length = 17)
    private String pesrgie;
    @Column(name = "pestipo")
    private Character pestipo;
    @Column(name = "pessite", length = 120)
    private String pessite;
    @OneToMany(mappedBy = "pescodigo")
    private List<Fornecedor> fornecedorList;
    @OneToMany(mappedBy = "pescodigo")
    private List<Transportadora> transportadoraList;
    @OneToMany(mappedBy = "pescodigo")
    private List<Funcionario> funcionarioList;
    @OneToMany(mappedBy = "pescodigo")
    private List<Cliente> clienteList;
    @OneToMany(mappedBy = "pescodigo", cascade = CascadeType.MERGE, targetEntity = EnderecoPessoa.class)
    private List<EnderecoPessoa> enderecoPessoaList = new ArrayList<EnderecoPessoa>();
    @OneToMany(mappedBy = "pescodigo", cascade = CascadeType.MERGE, targetEntity = Telefone.class)
    private List<Telefone> telefoneList = new ArrayList<Telefone>();
    @OneToMany(mappedBy = "pescodigo", cascade = CascadeType.MERGE, targetEntity = PessoaInscricaomunicipal.class)
    private List<PessoaInscricaomunicipal> pessoaInscricaomunicipalList = new ArrayList<PessoaInscricaomunicipal>();

//Getters and Setters existem mas nao os colocarei para que a visualização se torne mais facil...

}

e uma classe Telefone

public class Telefone implements Serializable {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @Column(name = "telcodigo", nullable = false)
    private Integer telcodigo;
    @Column(name = "telcontato", length = 60)
    private String telcontato;
    @Column(name = "telnumero", length = 14)
    private String telnumero;
    @JoinColumn(name = "pescodigo", referencedColumnName = "pescodigo", nullable=false)
    @ManyToOne
    private Pessoa pescodigo;

//Getters and Setters existem mas nao os colocarei para que a visualização se torne mais facil...

}

Tenho um ManagedBean pessoaMB com o código para salvar funcionario

 public void salvarFuncionario() {
        this.funcionario.getPescodigo().setPesstatus('A');
        this.funcionario.getPescodigo().setPestipo('F');
        this.funcionario.getPescodigo().setTelefoneList(getPessoa().getTelefoneList());
        this.funcionario.getPescodigo().setEnderecoPessoaList(getPessoa().getEnderecoPessoaList());
        //Verifico se o que retorna do salvar tem código, pois se NÃO tiver ocorreu alguma falha
        if (FuncionarioDAO.getInstance().salvar(funcionario).getFuncodigo() != null) {
            this.setFuncionario(new Funcionario());
            this.setPessoa(new Pessoa());
            this.setModal(new Modal("Cadastrado com sucesso!", "250", "100", "margin-left: 38%;"));
        } else {
            this.setModal(new Modal("Ops, ocorreu um erro. Tente novamente!", "340", "100", "margin-left: 42%;"));
        }
    }

Bem. esta é a estrutura do meu código e quero salvar este objeto Funcionário mas infelizmente me ocorre o erro:

java.lang.IllegalStateException: org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: br.com.mottabox.modelo.Pessoa

Mas ao tentar salvar apenas uma pessoa com a listagem de telefones esta pessoa é salva. E porque eu tento salvar o funcionário que contém a pessoa com a listagem de telefones e o JPA nao salva?
Busquei ajuda na internet e achei no blog da caelum um artigo do Paulo: http://blog.caelum.com.br/transientobjectexception-lazyinitializationexception-e-outras-famosas-do-hibernate/
e também aki no forum achei duvidas como esta: http://www.guj.com.br/java/142805-object-references-an-unsaved-transient-instance—save-the-transient-instance-before-flushing

Mas ao tentar resolver eu nao estou conseguindo, por favor ajudem-me.

Obrigado pela atenção de todos.

e fiquem na Paz de DEUS.

Se não me engano, este erro acontece pelo fato de um dos objetos do relacionamento não estar na sessao do hibernate.
Vc precisa primeiro salvar o objeto pessoa e depois o funcionario.

É o que o Renato disse: precisa ter todos os objetos managed.

Ao persistir alguem transient, na ausencia de cascade, ele nao vai aceitar grava-lo no caso de algum relacionamento seu conter entidades transientes. A solucao aqui seria usar o cascade (eu evito) ou chamar o save para pessoa antes.

uma sugestao: seu modelo está crescendo muito. as classes estao ganhando muito atributos, indicando que voce poderia quebra-las em outras entidades ou objetos @Embeddable.

Obrigado Renato pela atenção que disponibilizou com este meu tópico e foi de muita serventia.

E Paulo,

Muito obrigado pela ajuda, mas eu fiquei muito chateado de nao conseguir salvar apenas meu funcionario e o hibernate fazer o resto. Acabei por fazer como me disse e salvei um de cada vez :frowning: .

Abusando de sua boa vontade, aih vai uma pergunta: como o Hibernate se comporta quando eu tento salvar uma classe como a Pessoa (no meu caso)? ele salva Pessoa e depois as extremidades (endereco e telefone)? teria como ver isso sendo feito ou pelo menos ver o log disso acontecendo?

Gostaria de aproveitar para tirar dúvidas sobre aplicações web, posso lhe passar uma explicacao de como faço o básico, para que nós possamos continuar a conversar sobre isso? Aprendi muito na raça, e, gostaria de verificar com alguem se o que faço hoje é viável ou ainda é arcaico, essa pessoa poderia ser vc? rsrs…Pois tenho muitas dúvidas e gostaria de esmaga-las com conhecimento! rsrsrs…papo NERD, nao?? rsrsrsr

Mais uma vez obrigado pela atenção.

DEUS abençoe!

Ola Vinicius!

Voce pode ver sim! Basta ligar a opcao hibernate.show_sql para true! E voce poderia evitar de invocar o save nos dois usando o cascade… mas como ja te avisei, eu prefiro nao fazer.

sobre as duvidas de web, pode postar aqui no GUJ! eu estarei de ferias mas me mande o link, e aqui todos podem ajudar.

abracos