Usuário com melhor resposta
Erro ao retornar um DataTable usando Access C#

Pergunta
-
Ola pessoal, estou com dificuldade em retornar um data table usando o access como banco . O erro é 'Nome de consulta é esperado depois de EXECUTE.'
private OleDbConnection con = new OleDbConnection();
private OleDbDataReader dataReaderOledDB;
private OleDbCommand com;
private OleDbDataAdapter dap = new OleDbDataAdapter();
private DataTable dat = new DataTable();
private DataSet dset = new DataSet();
public bool Conectar()
{
if ((con.State == ConnectionState.Broken) || (con.State == ConnectionState.Closed))
{
try
{
this.con.ConnectionString = @"Provider=Microsoft.Jet.OLEDB.4.0;Data Source="+
Directory.GetCurrentDirectory().ToString() + "\\Data\\BlockSite.mdb";
return true;
}
catch
{
return false;
}
}
else
{
return true;
}
} public DataTable oledbDataTable(string sql)
{
try
{
this.Conectar();
this.com = new OleDbCommand(sql, con);
this.com.CommandType = CommandType.Text;
this.com.CommandText = sql;
this.com.CommandTimeout = 7200;
dap.SelectCommand = this.com;
dap.Fill(dat);
dap.Dispose();
return dat;
}
catch(System.AccessViolationException ex)
{
Console.WriteLine(ex);
return dat;
}
}- Editado AndreGomesA quinta-feira, 2 de junho de 2016 18:10
Respostas
-
Olá Andre. Com C# e Access uso o seguinte código.
using System.Linq; using System.Text; using System.Threading.Tasks; using System.Data.OleDb; using System.Data; using System.Windows.Forms; namespace Jukebox{ class Conexao{ private const string _strCon = @"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=Dados.mdb"; private string vsql = ""; OleDbConnection objCon = null; #region "Métodos de conexão como o banco" public bool conectar(){ // Cria uma instância para o objeto de conexão "objCon" incluíndo a string de conexão. objCon = new OleDbConnection(_strCon); try{ // Abra a conexão e retorne verdadeiro. objCon.Open(); return true; } catch{ // Se a conexão estiver aberta retorne falso. return false; } } public bool desconectar(){ // Verifica estado da conexão. bool estado = Convert.ToBoolean(objCon.State); // Se o estado for diferente de fechado então feche e limpe da memória e retorne verdadeiro. if (estado != false){ objCon.Close(); objCon.Dispose(); return true; } else{ // Se ele estiver fechado apenas limpe da memória e retorne falso. objCon.Dispose(); return false; } } #endregion public DataTable ListarMusica(){ // Função para Listar dados num DataTable e enviá-lo de volta. // String de consulta. vsql = "SELECT * FROM MUSICAS"; // Cria um objeto de comando vazio. OleDbCommand objcmd = null; // Testa a abertura da conexão. if (this.conectar()){ try{ // O objeto de comando recebe a string de conexão e o objeto de conexão. objcmd = new OleDbCommand(vsql, objCon); // Instancia um DataAdapter com o comando de conexão. OleDbDataAdapter adp = new OleDbDataAdapter(objcmd); // Instanciamos um DataTable vazio. DataTable dt = new DataTable(); // O DataAdapter preenche(Fill) o DataTable. adp.Fill(dt); // A função retorna o DataTable para o método que o chamou. return dt; } // Tratamento de erro e retorna o DataTable nulo. catch { return null; } // Faz a desconexão como passo final. finally{ this.desconectar(); } } // Caso não consiga conectar, retorna DataTable nulo. else return null; } }
É interessante deixar a string de conexão como uma constante no topo da classe e a string de consulta dentro do método.
Se quiser fazer um INSERT uso o seguinte código:
public bool InsertMusica(ArrayList reg){ /* Função que faz um insert de dados no banco. Recebe um ArrayList como parâmetro de dados. Esta função retorna um valor booleano (verdadeiro ou falso) para o método que o chamou. String de consulta. */ vsql = "INSERT INTO MUSICAS(REGISTRO, ARQUIVO, CODARTISTA, TITULO, ANO)" + " VALUES ((SELECT COALESCE(MAX(M.REGISTRO), 0) + 1 FROM MUSICAS M)," + " @Arquivo, @CodArtista, @Titulo, @Ano)"; // Cria um objeto de comando vazio. OleDbCommand objcmd = null; // Tenta abrir a conexão. if (this.conectar()){ try{ // Cria um objeto de comando do OleDb incluíndo a string de consulta e o objeto de conexão. objcmd = new OleDbCommand(vsql, objCon); // Adiciona o arrayList nos parâmetros do objeto de conexão. objcmd.Parameters.Add(new OleDbParameter("@Arquivo", reg[0])); objcmd.Parameters.Add(new OleDbParameter("@CodArtista", reg[1])); objcmd.Parameters.Add(new OleDbParameter("@Titulo", reg[2])); objcmd.Parameters.Add(new OleDbParameter("@Ano", reg[3])); // Envia a string de consulta como objeto de comando. objcmd.ExecuteNonQuery(); // Retorna verdadeiro para o método que o chamou. return true; } catch (OleDbException sqlerr){ // Tratamento de erro. // Exibe na tela o motivo do erro para o usuário. MessageBox.Show("Nome de usuário já cadastrado", "::Erro", MessageBoxButtons.OK, MessageBoxIcon.Error); // Realiza a desconexão do banco. this.desconectar(); // Exibe na tela o motivo do erro. MessageBox.Show(Convert.ToString(sqlerr)); // Retorna falso para o método que o chamou. return false; } finally { this.desconectar(); } } else return false; }
Para criar um auto-incremento na coluna Registro usei o COALESCE dentro de um SELECT MAX, ele escolhe o segundo valor do argumento caso o primeiro seja NULL, depois soma com +1 e faz esse insert.
Espero ter ajudado.
- Marcado como Resposta Thales F Quintas segunda-feira, 6 de junho de 2016 11:55
Todas as Respostas
-
Boa tarde AndreGomesA,
Você chegou a debugar o código para verificar em qual linha o erro é apresentado?
Abraço.
Thales F Quintas
Esse conteúdo e fornecido sem garantias de qualquer tipo, seja expressa ou implícita
TechNet Community Support
Por favor, lembre-se de Marcar como Resposta as postagens que resolveram o seu problema. Essa é uma maneira comum de reconhecer aqueles que o ajudaram e fazer com que seja mais fácil para os outros visitantes encontrarem a resolução mais tarde.
-
Olá Andre. Com C# e Access uso o seguinte código.
using System.Linq; using System.Text; using System.Threading.Tasks; using System.Data.OleDb; using System.Data; using System.Windows.Forms; namespace Jukebox{ class Conexao{ private const string _strCon = @"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=Dados.mdb"; private string vsql = ""; OleDbConnection objCon = null; #region "Métodos de conexão como o banco" public bool conectar(){ // Cria uma instância para o objeto de conexão "objCon" incluíndo a string de conexão. objCon = new OleDbConnection(_strCon); try{ // Abra a conexão e retorne verdadeiro. objCon.Open(); return true; } catch{ // Se a conexão estiver aberta retorne falso. return false; } } public bool desconectar(){ // Verifica estado da conexão. bool estado = Convert.ToBoolean(objCon.State); // Se o estado for diferente de fechado então feche e limpe da memória e retorne verdadeiro. if (estado != false){ objCon.Close(); objCon.Dispose(); return true; } else{ // Se ele estiver fechado apenas limpe da memória e retorne falso. objCon.Dispose(); return false; } } #endregion public DataTable ListarMusica(){ // Função para Listar dados num DataTable e enviá-lo de volta. // String de consulta. vsql = "SELECT * FROM MUSICAS"; // Cria um objeto de comando vazio. OleDbCommand objcmd = null; // Testa a abertura da conexão. if (this.conectar()){ try{ // O objeto de comando recebe a string de conexão e o objeto de conexão. objcmd = new OleDbCommand(vsql, objCon); // Instancia um DataAdapter com o comando de conexão. OleDbDataAdapter adp = new OleDbDataAdapter(objcmd); // Instanciamos um DataTable vazio. DataTable dt = new DataTable(); // O DataAdapter preenche(Fill) o DataTable. adp.Fill(dt); // A função retorna o DataTable para o método que o chamou. return dt; } // Tratamento de erro e retorna o DataTable nulo. catch { return null; } // Faz a desconexão como passo final. finally{ this.desconectar(); } } // Caso não consiga conectar, retorna DataTable nulo. else return null; } }
É interessante deixar a string de conexão como uma constante no topo da classe e a string de consulta dentro do método.
Se quiser fazer um INSERT uso o seguinte código:
public bool InsertMusica(ArrayList reg){ /* Função que faz um insert de dados no banco. Recebe um ArrayList como parâmetro de dados. Esta função retorna um valor booleano (verdadeiro ou falso) para o método que o chamou. String de consulta. */ vsql = "INSERT INTO MUSICAS(REGISTRO, ARQUIVO, CODARTISTA, TITULO, ANO)" + " VALUES ((SELECT COALESCE(MAX(M.REGISTRO), 0) + 1 FROM MUSICAS M)," + " @Arquivo, @CodArtista, @Titulo, @Ano)"; // Cria um objeto de comando vazio. OleDbCommand objcmd = null; // Tenta abrir a conexão. if (this.conectar()){ try{ // Cria um objeto de comando do OleDb incluíndo a string de consulta e o objeto de conexão. objcmd = new OleDbCommand(vsql, objCon); // Adiciona o arrayList nos parâmetros do objeto de conexão. objcmd.Parameters.Add(new OleDbParameter("@Arquivo", reg[0])); objcmd.Parameters.Add(new OleDbParameter("@CodArtista", reg[1])); objcmd.Parameters.Add(new OleDbParameter("@Titulo", reg[2])); objcmd.Parameters.Add(new OleDbParameter("@Ano", reg[3])); // Envia a string de consulta como objeto de comando. objcmd.ExecuteNonQuery(); // Retorna verdadeiro para o método que o chamou. return true; } catch (OleDbException sqlerr){ // Tratamento de erro. // Exibe na tela o motivo do erro para o usuário. MessageBox.Show("Nome de usuário já cadastrado", "::Erro", MessageBoxButtons.OK, MessageBoxIcon.Error); // Realiza a desconexão do banco. this.desconectar(); // Exibe na tela o motivo do erro. MessageBox.Show(Convert.ToString(sqlerr)); // Retorna falso para o método que o chamou. return false; } finally { this.desconectar(); } } else return false; }
Para criar um auto-incremento na coluna Registro usei o COALESCE dentro de um SELECT MAX, ele escolhe o segundo valor do argumento caso o primeiro seja NULL, depois soma com +1 e faz esse insert.
Espero ter ajudado.
- Marcado como Resposta Thales F Quintas segunda-feira, 6 de junho de 2016 11:55