2

最近,一个程序创建了一个Access db(我们下游合作伙伴的要求),添加了一个包含所有备忘录列的表,然后插入了一堆停止工作的记录。奇怪的是,我可以看到环境没有任何变化,任何差异中也没有任何可能影响它的变化。此外,这在我尝试过的任何机器上都可以重现,无论它是否有 Office,是否有 Office,无论是 32 位还是 64 位。

问题是当您在程序运行后打开数据库时,目标表是空的,而是有一个包含一堆行的 MSysCompactError 表。

这是蒸馏代码:

var connectionString = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=corrupt.mdb;Jet OLEDB:Engine Type=5";

// create the db and make a table
var cat = new ADOX.Catalog();
try
{
    cat.Create(connectionString);

    var tbl = new ADOX.Table();
    try
    {
        tbl.Name = "tbl";
        tbl.Columns.Append("a", ADOX.DataTypeEnum.adLongVarWChar);
        cat.Tables.Append(tbl);
    }
    finally
    {
        Marshal.ReleaseComObject(tbl);
    }
}
finally
{
    cat.ActiveConnection.Close();
    Marshal.ReleaseComObject(cat);
}

using (var connection = new OleDbConnection(connectionString))
{
    connection.Open();

    // insert a value
    using (var cmd = new OleDbCommand("INSERT INTO [tbl] VALUES ( 'x' )", connection))
        cmd.ExecuteNonQuery();
}

以下是我偶然发现的一些解决方法:

  1. 如果在创建表和插入值之间插入断点(上面的第 28 行),然后使用 Access 打开 mdb 并再次关闭它,那么当应用程序继续运行时,它不会损坏数据库。
  2. 将引擎类型从 5 更改为 4(第 1 行)将创建一个未损坏的 mdb。您最终会得到一个过时的 mdb 版本,但该表有值并且没有 MSysCompactError。请注意,我尝试过以这种方式创建数据库,然后最后以编程方式将其升级到 5,但没有成功。我最终在最新版本中得到了一个损坏的数据库。
  3. adLongVarWChar如果您通过将第13 行更改为 将备注更改为文本字段adVarWChar,则数据库没有损坏。不过,您最终text会得到 db 中的字段而不是memo

最后一点:在我的旅行中,我看到 MSysCompactError 与压缩数据库有关,但我没有做任何明确的事情来使数据库紧凑。

有任何想法吗?

4

1 回答 1

0

正如我对 HasUp 的回复:根据 MS 支持,不推荐以编程方式创建 Jet 数据库。我最终签入了一个空的模型数据库,然后在需要新的时候复制它。有关详细信息,请参阅http://support.microsoft.com/kb/318559

于 2012-11-12T21:48:14.117 回答