OleDbException (0x80004005): неизвестно

У меня есть следующий код (часть формы Windows), который успешно подключается к файлу Excel на моей машине, но в другом окне это не удается.

var fd = new OpenFileDialog();
if (fd.ShowDialog() == DialogResult.OK)
{
    var extendedProperties = string.Empty;
    if (fd.FileName.Contains(".xlsx"))
    {
        // excel 2007 xml format file, IMEX = import data as text avoids data conversion errors
        extendedProperties = "Excel 12.0 Xml;IMEX=1";
    }
    else if (fd.FileName.Contains(".xls"))
    {
        // excel 2003 format file, IMEX: import data as text avoids data conversion errors
        extendedProperties = "Excel 8.0;IMEX=1";
    }

    var connectionString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source='" + fd.FileName + "';Extended Properties='" + extendedProperties + "'";
    using (var objXConn = new OleDbConnection(connectionString))
    {
        objXConn.Open();

        var selectStatement = string.Format("SELECT * FROM [tabName$] WHERE FormType IS NOT NULL");
        var dataTable = new DataTable("test");
        using (var objCommand = new OleDbCommand(selectStatement, objXConn))
        {
            var dataReader = objCommand.ExecuteReader();
            if (dataReader != null)
            {
                dataTable.Load(dataReader);
            }
        }
        using (var stringWriter = new StringWriter())
        {
            dataTable.WriteXml(stringWriter);
            this.textBox1.Text = stringWriter.ToString();
        }
    }
}

Поведение воспроизводимо с использованием OleDbDataAdapter а не OleDbCommand.ExecuteReader(),

using (var dataAdapter = new OleDbDataAdapter(selectStatement, objXConn))
{
    dataAdapter.Fill(dataTable);
}

Под неудачей я имею в виду получение следующей ошибки на линии dataTable.Load(dataReader);

При запуске / сборке программы с конфигурацией x86 я получаю следующую ошибку.

System.Data.OleDb.OleDbException (0x80004005): Unknown
   at System.Data.OleDb.OleDbDataReader.ProcessResults(OleDbHResult hr)
   at System.Data.OleDb.OleDbDataReader.GetRowHandles()
   at System.Data.OleDb.OleDbDataReader.ReadRowset()
   at System.Data.OleDb.OleDbDataReader.Read()
   at System.Data.Common.DataAdapter.FillLoadDataRow(SchemaMapping mapping)
   at System.Data.Common.DataAdapter.FillFromReader(DataSet dataset, DataTable datatable, String srcTable, DataReaderContainer dataReader, Int32 startRecord, Int32 maxRecords, DataColumn parentChapterColumn, Object parentChapterValue)
   at System.Data.Common.DataAdapter.Fill(DataTable[] dataTables, IDataReader dataReader, Int32 startRecord, Int32 maxRecords)
   at System.Data.Common.LoadAdapter.FillFromReader(DataTable[] dataTables, IDataReader dataReader, Int32 startRecord, Int32 maxRecords)
   at System.Data.DataTable.Load(IDataReader reader, LoadOption loadOption, FillErrorEventHandler errorHandler)
   at ExcelTest.Form1.button1_Click(Object sender, EventArgs e)
   at System.Windows.Forms.Control.OnClick(EventArgs e)
   at System.Windows.Forms.Button.OnClick(EventArgs e)
   at System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent)
   at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
   at System.Windows.Forms.Control.WndProc(Message& m)
   at System.Windows.Forms.ButtonBase.WndProc(Message& m)
   at System.Windows.Forms.Button.WndProc(Message& m)
   at System.Windows.Forms.Control.ControlNativeWindow.OnMessage(Message& m)
   at System.Windows.Forms.Control.ControlNativeWindow.WndProc(Message& m)
   at System.Windows.Forms.NativeWindow.Callback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)

При запуске / сборке программы с конфигурацией AnyCPU/x64 я получаю следующую ошибку на обеих машинах.

System.InvalidOperationException: The 'Microsoft.ACE.OLEDB.12.0' provider is not registered on the local machine.
   at System.Data.OleDb.OleDbServicesWrapper.GetDataSource(OleDbConnectionString constr, DataSourceWrapper& datasrcWrapper)
   at System.Data.OleDb.OleDbConnectionInternal..ctor(OleDbConnectionString constr, OleDbConnection connection)
   at System.Data.OleDb.OleDbConnectionFactory.CreateConnection(DbConnectionOptions options, DbConnectionPoolKey poolKey, Object poolGroupProviderInfo, DbConnectionPool pool, DbConnection owningObject)
   at System.Data.ProviderBase.DbConnectionFactory.CreateNonPooledConnection(DbConnection owningConnection, DbConnectionPoolGroup poolGroup, DbConnectionOptions userOptions)
   at System.Data.ProviderBase.DbConnectionFactory.TryGetConnection(DbConnection owningConnection, TaskCompletionSource`1 retry, DbConnectionOptions userOptions, DbConnectionInternal oldConnection, DbConnectionInternal& connection)
   at System.Data.ProviderBase.DbConnectionInternal.TryOpenConnectionInternal(DbConnection outerConnection, DbConnectionFactory connectionFactory, TaskCompletionSource`1 retry, DbConnectionOptions userOptions)
   at System.Data.ProviderBase.DbConnectionInternal.OpenConnection(DbConnection outerConnection, DbConnectionFactory connectionFactory)
   at System.Data.OleDb.OleDbConnection.Open()
   at ExcelTest.Form1.button1_Click(Object sender, EventArgs e)
   at System.Windows.Forms.Button.OnMouseUp(MouseEventArgs mevent)
   at System.Windows.Forms.Control.WmMouseUp(Message& m, MouseButtons button, Int32 clicks)
   at System.Windows.Forms.Control.WndProc(Message& m)
   at System.Windows.Forms.ButtonBase.WndProc(Message& m)
   at System.Windows.Forms.Button.WndProc(Message& m)
   at System.Windows.Forms.NativeWindow.Callback(IntPtr hWnd, Int32 msg, IntPtr wparam, IntPtr lparam)

Файл Excel, используемый для тестирования, является одним и тем же файлом на обеих машинах. Я смог воспроизвести проблему с несколькими файлами (оба .xls анс .xlsx).

Я попытался следующие вещи, чтобы исправить проблему.

Какие дополнительные шаги я могу предпринять, чтобы устранить проблему или решить эту проблему?

1 ответ

Решение

Для первого использования проблемы OleDbDataAdapter а также Fill() метод или Update(),

        DataTable newTbl = new DataTable()
        using(OleDbDataAdapter ad = new OleDbDataAdapter(
            @"SELECT * FROM [tabName$] WHERE FormType IS NOT NULL", objXConn))
        {
           OleDbCommandBuilder builder = new OleDbCommandBuilder(ad);

           builder.QuotePrefix = "[";
           builder.QuoteSuffix = "]";

           // Saves the data set
           ad.Update(newTbl);
        }

Драйверы OLEDB для 32-разрядных и 64-разрядных приложений различаются.

Если у вас установлен только 32-разрядный драйвер, то попытка его использовать 64-разрядными приложениями приведет к следующей ошибке: Microsoft.ACE.OLEDB.12.0' provider is not registered on the local machine, Точно так же, если у вас установлена ​​только 64-битная версия и 32-битные приложения пытаются использовать ее, вы получите эту ошибку.

Чтобы понять, что происходит, вы должны проверить, что ваша заявка. Я думаю, что эта строка поможет: Environment.Is64BitProcess

Если проблема возникает с файлом xls(Excel 2003), попробуйте использовать строку подключения JET!

РЕДАКТИРОВАТЬ: Вот ссылка для обоих драйверов:

Другие вопросы по тегам