5
respostas

.ToList() retorna erro quando acha campo com valor nulo

Olá,

Estou tentando trazer informações de um banco de dados MySql através do comando ".ToList()", e está ocorrendo erro devido a um dos campos da tabela possuir valor nulo "null" e não sei como contornar este problema. Abaixo segue um trecho do código e o erro retornado:

Código:

            using (var repo = new SenhaContext())
            {
                IList<Senha> senhas = repo.Senhas.ToList();
                foreach (var item in senhas)
                {
                    lblSenhaChamada.Text = item.senha.ToString();
                }
            }

Erro retonado: "System.InvalidCastException: 'Conversão especificada não é válida.'"

Obrigado.

5 respostas

Olá Sandro!

Esse erro quer dizer que você não consegue converter um valor nulo em uma string. O que você pode fazer é verificar se o campo é nulo (que no banco deveria ser NOT NULL, por se tratar de senhas :) e atribuir uma string sem valor.

foreach (var item in senhas)
{
    if (! item.senha.Equals(DBNull.Value)) // ou if (!DBNull.Value.Equals(item.senha))
    {
        lblSenhaChamada.Text = item.senha.ToString();
    }
    else
    {
        lblSenhaChamada.Text = ""; // ou lblSenhaChamada.Text = String.Empty;
    }
}

Neste link tem mais informações sobre o DBNull, caso meu código dê algum problema.

Espero ter ajudado!

Bons estudos!

Bom dia Fabiano,

A tabela de senha possui "not null" no login e senha, mas possuo outros campos de controle em que aceitam null, pois o preenchimento será posterior com o uso do programa, como exemplo data de alteração.

O que ocorre é que devido a estes campos com valor nulo e que aceitam este valor, quando tento recuperar os valores dos campos da tabela o erro ocorre, mas não dentro do "foreach" e sim na chamada do .ToList() (IList senhas = repo.Senhas.ToList();), o que me parece é que o EF não converte automaticamente campos nulos no carregamento da lista, portanto a pergunta, como fazer o EF receber os dados do banco com valores nulos em alguns campos da tabela?

Obrigado.

Sandro, boa tarde.

Coloca aqui pra gente a pilha de execução com o erro para analisarmos o problema. Quero saber em qual coluna e com que tipo está dando esse erro, além da propriedade que deveria ser mapeada.

Se possível coloca também a classe de contexto e a classe com a entidade.

Fico no aguardo.

Olá Daniel, como vai?

Seguem os dados:

  • DDL do banco de dados (MySql):

CREATE TABLE senhas ( id int(11) NOT NULL AUTO_INCREMENT, codcoligada int(11) NOT NULL, codfilial int(11) NOT NULL, codsetor int(11) NOT NULL, senhaespecial int(11) NOT NULL, senha int(11) NOT NULL, sigla varchar(10) DEFAULT NULL, guiche varchar(6) NOT NULL, datasenha datetime(6) NOT NULL, datachamada datetime(6) DEFAULT NULL, codatendente int(11) DEFAULT NULL, PRIMARY KEY (id) ) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci

  • Classe SenhaContext:

namespace Senha_Usuario { public class SenhaContext : DbContext { public DbSet Senhas { get; set; }

    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseMySql("Server=localhost;User Id=root;Password=root;Database=senha");
    }
}

}

  • Insert na tabela:

INSERT INTO senha.senhas (codcoligada, codfilial, codsetor, senhaespecial, senha, sigla, guiche, datasenha) VALUES ('1', '7', '1', '0', '12', 'SECR', '01', '2019-08-12 21:00:23') --> Perceba que os campos datachamada e codatendente não foram inclusos valores

  • Ao executar o programa ocorre o erro abaixo, mas se eu incluir valor nos dois campos nulos o programa funciona corretamente - será que é um problema com o Pomelo ou com o EF?:

System.InvalidCastException: 'Conversão especificada não é válida.' System.InvalidCastException HResult=0x80004002 Message=Conversão especificada não é válida. Source=MySqlConnector StackTrace: em MySqlConnector.Core.Row.GetInt32(Int32 ordinal) em C:\projects\mysqlconnector\src\MySqlConnector\Core\Row.cs:linha 177 em MySql.Data.MySqlClient.MySqlDataReader.GetInt32(Int32 ordinal) em C:\projects\mysqlconnector\src\MySqlConnector\MySql.Data.MySqlClient\MySqlDataReader.cs:linha 181 em Microsoft.EntityFrameworkCore.Storage.Internal.TypedRelationalValueBufferFactory.Create(DbDataReader dataReader) em Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable1.Enumerator.BufferlessMoveNext(DbContext _, Boolean buffer) em Pomelo.EntityFrameworkCore.MySql.Storage.Internal.MySqlExecutionStrategy.Execute[TState,TResult](TState state, Func3 operation, Func3 verifySucceeded) em Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable1.Enumerator.MoveNext() em Microsoft.EntityFrameworkCore.Query.Internal.LinqOperatorProvider.<TrackEntities>d__172.MoveNext() em Microsoft.EntityFrameworkCore.Query.Internal.LinqOperatorProvider.ExceptionInterceptor1.EnumeratorExceptionInterceptor.MoveNext() em System.Collections.Generic.List1..ctor(IEnumerable1 collection) em System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source) em SenhaUsuario.frmSenhaUsuario.btChamarLista_Click(Object sender, EventArgs e) em C:\Projetos\VS2017\Senha\Senha_Usuario\frmChamadaSenha.cs:linha 57 em System.Windows.Forms.Control.OnClick(EventArgs e) em System.Windows.Forms.Button.OnClick(EventArgs e) em System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent) em System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks) em System.Windows.Forms.Control.WndProc(Message& m) em System.Windows.Forms.ButtonBase.WndProc(Message& m) em System.Windows.Forms.Button.WndProc(Message& m) em System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m) em System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m) em System.Windows.Forms.NativeWindow.DebuggableCallback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam) em System.Windows.Forms.UnsafeNativeMethods.DispatchMessageW(MSG& msg) em System.Windows.Forms.Application.ComponentManager.System.Windows.Forms.UnsafeNativeMethods.IMsoComponentManager.FPushMessageLoop(IntPtr dwComponentID, Int32 reason, Int32 pvLoopData) em System.Windows.Forms.Application.ThreadContext.RunMessageLoopInner(Int32 reason, ApplicationContext context) em System.Windows.Forms.Application.ThreadContext.RunMessageLoop(Int32 reason, ApplicationContext context) em System.Windows.Forms.Application.Run(Form mainForm) em Senha_Usuario.Program.Main() em C:\Projetos\VS2017\Senha\Senha_Usuario\Program.cs:linha 19

Sandro, desculpe pela demora.

Tô desconfiado que tem a ver com a conversão para inteiro... Achei essa issue aqui no repositório do Pomelo: https://github.com/PomeloFoundation/Pomelo.EntityFrameworkCore.MySql/issues/408

É em FSharp mas pode ser o msm problema. Qual o tipo de dado que você está usando na propriedade que mapeia para codatendente? Int ou Long?

Fico no aguardo.