在 SQLite-.NET 操作 SQLite 一节中,我们介绍了引用 dll,但是这种情况下,平台不能使用 Any CPU,必须使用 x86,这就不方便。
我们可以换用 Microsoft.Data.Sqlite。
1、NuGet 中搜索 Microsoft.Data.Sqlite,安装。
2、前述引用的 System.Data.SQLite 换成 Microsoft.Data.Sqlite。
3、SQLite 换成 Sqlite,比如:SQLiteConnection 换成 SqliteConnection。
其他一样。
换成 Microsoft.Data.Sqlite 之后,还有一个非常大的变化,就是:
SqliteConnection 是派生自 System.Data.Common.DbConnection 的。
这样的话,它就和其他数据库连接是同一个基类了,咱们做多数据库适配时,就可以轻松实现了。
不过,不支持 .NET Framework 3.5。
同时,它不支持 DataAdapter 了,使用 DataView/DataTable 不方便了
那就手工写一个 DataReader 到 DataView 的代码:
DataView result = new DataView(new DataTable()); using (SqliteCommand cmd = new SqliteCommand(sql, conn)) { using (SqliteDataReader reader = cmd.ExecuteReader()) { // 字段。 for (int i = 0; i < reader.FieldCount; i++) { result.Table.Columns.Add(reader.GetName(i), reader.GetFieldType(i)); } // 行记录。 while (reader.Read()) { DataRow dr = result.Table.Rows.Add(); for (int i = 0; i < reader.FieldCount; i++) { dr[i] = reader.GetValue(i); } } } } return result;
有错误?
我第一个项目中,一次成功了,没怎么在意。
后来再建项目的时候,出现错误。
当 Microsoft.Data.Sqlite 在另一个类项目中,引用之,运行时错误:
You need to call SQLitePCL.raw.SetProvider(). If you are using a bundle package, this is done by calling SQLitePCL.Batteries.Init().
当 Microsoft.Data.Sqlite 在本项目中,运行时错误:
Library e_sqlite3 not found
怎么解决了?
换 .NET Framework 4.6.1、4.6.2、4.8,均无效。
改 Debug、Release、Any CPU、x86 均无效。
后来将 Microsoft.Data.Sqlite 换成 2.1.14 这个版本成功了,换成 3.x、6.x、均无效。
这个 Microsoft.Data.Sqlite 2.2.0 - 2.2.6 版本是被弃用了的,所以我选择 2.1.14 这个版本。
我很奇怪的是:
2.1.14 是 2019 年的版本,第一次成功时,应该不会选择这个版本。
7.0.5 是第一次成功前两周发布的版本,应该选择的就是这个版本。
那当时是为何成功了呢?唯一不同就是电脑不同。两台电脑都是 Windows 10,都安装了 SQLite Expert Personal。到底哪里不同,待研究。
小结一下:
Microsoft.Data.Sqlite.Core 是基于 SQLitePCLRaw 的,SQLitePCLRaw 有两类:捆绑、提供程序,推荐使用捆绑。
捆绑前缀是:SQLitePCLRaw.bundle_(注意是下划线)。
提供程序前缀是:SQLitePCLRaw.provider.(注意是点)。
也就是说我们要安装时,至少要安装 Microsoft.Data.Sqlite.Core,和对应的 SQLitePCLRaw,安装时注意版本对应。
当然,为了方便,也给我们提供了集成的,我们就只需要安装一个就是了,比如:
Microsoft.Data.Sqlite v2.1.14 = Microsoft.Data.Sqlite.Core v2.1.14 + SQLitePCLRaw.bundle_green v1.1.12
……
Microsoft.Data.Sqlite v7.0.5 = Microsoft.Data.Sqlite.Core v7.0.5 + SQLitePCLRaw.bundle_e_sqlite3 v2.1.4
使用捆绑则调用:SQLitePCL.Batteries.Init();
使用提供程序则调用:SQLitePCL.raw.SetProvider(),比如:SQLitePCL.raw.SetProvider(new SQLitePCL.SQLite3Provider_e_sqlite3());
一定要调用吗?我发现在同一项目中,可以不调用,但是如果将数据库操作放在另一项目中,则要调。
更多请参见:自定义 SQLite 版本 - Microsoft.Data.Sqlite | Microsoft Learn
奇怪的问题,原来跟我们无关
前面提到了奇怪的问题,其实还有各类奇奇怪怪的问题,比如除了上面的,还有 SQLitePCLRaw.core 无法加载。
删 bin、obj,清解决方案,NuGet 重来,啥都试过了,没用。
后来复制一模一样的项目,居然成功了。
再后来,把之前有问题的项目,移除任何一个文件夹,再加进来,也成功了。
……
这在多台电脑上都是一样,可以说明是 VS 的问题了,跟我们无关。
相关阅读