Entity Framework 6 return cast error

Asked

Viewed 61 times

1

I have two entities that inherit from the same abstract class.

public class Empresa : PessoaJuridica
  {
    private Empresa()
    { 

    }
    public Empresa(string CNPJ, string RazaoSocial, Status Situacao, byte MaxNumeroUsuarios)
    {
        base.CNPJ = CNPJ;
        base.RazaoSocial = RazaoSocial;
        base.Situacao = Situacao;
        //.. simplificado para facilitar
    }

       //.. simplificado para facilitar
  }

The other class

public class ClientePJ : PessoaJuridica
{
    private long _empresa_id;

    private ClientePJ()
    {

    }
    public ClientePJ(long IdEmpresa, string CNPJ, string RazaoSocial, Status Situacao)
    {
        this.Empresa_Id = IdEmpresa;
        base.CNPJ = CNPJ;
        base.RazaoSocial = RazaoSocial;
        base.Situacao = Situacao;
        //.. simplificado para facilitar
    }

       //.. simplificado para facilitar
}

The abstract class

public abstract class PessoaJuridica : EntidadeBase, IDataCadastro, IDataUltimaModificacao, INaoExcluivel
{
    public string NomeFantasia { get; set; }
    public string RazaoSocial { get; set; }
    public string CNPJ { get; set; }
    public Status Situacao { get; set; }
    public string Website { get; set; }
    public DateTime? DataCadastro { get; set; }
    public DateTime? DataUltimaModificacao { get; set; }
    public long IdLoginCadastro { get; set; }
    public long? IdLoginUltimaModificacao { get; set; }
    public Endereco Endereco { get; set; }
    public ICollection<Contato> Contatos { get; set; }
}

All 3 classes are mapped in the Entity Framework separately

    public PessoaJuridicaMap()
    {
        HasKey(pj => pj.Id);

        Property(pj => pj.Id).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
        Property(pj => pj.NomeFantasia).HasMaxLength(255);
        Property(pj => pj.RazaoSocial).IsRequired().HasMaxLength(255);
        Property(pj => pj.Situacao).HasColumnName("Status").IsRequired();
        Property(pj => pj.CNPJ).IsRequired().IsFixedLength().HasMaxLength(14);
        Property(pj => pj.Website).HasMaxLength(255);
        Property(pj => pj.DataCadastro).IsRequired();
        Property(pj => pj.IdLoginCadastro).IsRequired();
        HasMany(pj => pj.Contatos).WithMany().Map(m => {
            m.ToTable("PessoasJuridicas_Contatos", "Admin");
            m.MapLeftKey("PessoaJuridica_Id");
            m.MapRightKey("Contato_Id");
        });

        HasOptional(pj => pj.Endereco);

        ToTable("PessoasJuridicas", "Base");
    }
//
      public EmpresaMap()
    {

        HasKey(e => e.Id);

        Property(e => e.Id).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
        Property(e => e.Situacao).HasColumnName("Status").IsRequired();
        Property(e => e.MaxNumeroUsuarios).IsRequired();
        Property(e => e.DataCadastro).IsRequired();

        ToTable("Empresas", "Admin");
    }
//
    public ClientePJMap() {

        HasKey(cpj => cpj.Id);
        Property(cpj => cpj.Id).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
        Property(cpj => cpj.Empresa_Id).IsRequired();
        ToTable("ClientesPJ", "Clientes");
    }

I use a generic repository for all classes, as below

 public RepositorioBase(D contexto)
    {
        this.conexao = contexto;
    }
    #endregion

    #region Métodos do Repositorio

    public void Salvar(T entidade)
    {
        conexao.Entry(entidade).State = EntityState.Added;
    }

    public T BuscarPorId(long? id)
    {

        return conexao.Set<T>().Find(id);
    }

    public ICollection<T> BuscarTodos()
    {
        ICollection<T> lista = conexao.Set<T>().ToList();
        return (lista.Count == 0) ? null : lista;
    }

    public T FiltrarUmPor(Func<T, bool> predicado)
    {
        return conexao.Set<T>().Where(predicado).Single();
    }

    public ICollection<T> FiltrarVariosPor(Func<T, bool> predicado)
    {
        return conexao.Set<T>().Where(predicado).ToList();
    }

My test suite has the following tests

    [TestMethod]
    [Description("Busca todos os Clientes")]
    [TestCategory("Testes de repositorio")]
    public void BuscarTodosClientes()
    {
        ICollection<ClientePJ> lista = repositorioCliente.BuscarTodos();

        Assert.IsNotNull(lista);
    }


    [TestMethod]
    [Description("Busca cliente por Id")]
    [TestCategory("Testes de repositorio")]
    public void BuscarClientePorId()
    {
        ClientePJ cliente = repositorioCliente.BuscarPorId(1);

        Assert.IsNotNull(cliente);
    }

I have similar tests for all repositories and all run perfect, but when I get to the above test of Buscarclienteporid, I take the following cast error:

System.Invalidoperationexception: The specified cast from a materialized 'Dominio.Entidades.Empresa' type to the 'Dominio.Entidades.Clientepj' type is not Valid.

I don’t know what’s going on since the search for all the ClientePJ works and does not give error, and is pointing to the same repository.

Has anyone ever seen this?

  • Try to change ClientePJ cliente = repositorioCliente.BuscarPorId(1); for var cliente = db.ClientesPJ.FirstOrDefault(c => c.Empresa_Id == 1). What happens?

  • I was bumping my head here and I found out, actually Id 1 belongs to a Personal Corporation that points to a Company, not to a Clientepj, so EF was doing the 'wrong' cast. I’ll change the test to get a random Clientepj ID.

No answers

Browser other questions tagged

You are not signed in. Login or sign up in order to post.