如何不借助app.config直接从DLL访问SQLite数据库?
解决EF6从DLL连接SQLite时的提供者名称错误问题
你遇到的这个报错Unable to determine the provider name for provider factory of type 'System.Data.SQLite.SQLiteFactory',核心原因是Entity Framework 6无法找到对应的SQLite EF6提供者配置,尤其是在类库(DLL)项目中,配置文件的生效逻辑和主应用不同,下面是具体的解决步骤:
1. 确认安装正确的NuGet包
首先确保你的项目(包括主应用和DLL)都安装了适配EF6的SQLite包:
- 安装
System.Data.SQLite.EF6(EF6专用的提供者包) - 安装
System.Data.SQLite.Core(核心SQLite驱动)
2. 配置主应用的配置文件(关键!)
因为DLL项目的配置文件不会直接生效,所有配置必须放在主应用的app.config/web.config中:
添加DbProviderFactories注册
在<configuration>节点内添加:
<system.data> <DbProviderFactories> <!-- 先移除可能存在的重复注册 --> <remove invariant="System.Data.SQLite.EF6" /> <add name="SQLite Data Provider (Entity Framework 6)" invariant="System.Data.SQLite.EF6" description=".NET Framework Data Provider for SQLite (Entity Framework 6)" type="System.Data.SQLite.EF6.SQLiteProviderFactory, System.Data.SQLite.EF6" /> <remove invariant="System.Data.SQLite" /> <add name="SQLite Data Provider" invariant="System.Data.SQLite" description=".NET Framework Data Provider for SQLite" type="System.Data.SQLite.SQLiteFactory, System.Data.SQLite" /> </DbProviderFactories> </system.data>
注册EF6提供者
在<entityFramework>节点内添加SQLite的提供者配置:
<entityFramework> <providers> <provider invariantName="System.Data.SQLite.EF6" type="System.Data.SQLite.EF6.SQLiteProviderServices, System.Data.SQLite.EF6" /> <!-- 如果需要SQL Server,保留这个,否则可以移除 --> <provider invariantName="System.Data.SqlClient" type="System.Data.Entity.SqlServer.SqlProviderServices, EntityFramework.SqlServer" /> </providers> </entityFramework>
3. 修正代码中的工厂和连接字符串
使用EF6专用的工厂
替换原来的SQLiteFactory.Instance为EF6版本的工厂:
DbProviderFactory fac = System.Data.SQLite.EF6.SQLiteProviderFactory.Instance;
检查连接字符串路径
你的代码中可能存在路径重复的问题:
// 原代码:DB_PATH已经包含DB_FILENAME,又额外加了"\SQLiteDatabase.db" conn.ConnectionString = "data source =" + DB_PATH + @"\SQLiteDatabase.db";
如果DB_FILENAME就是SQLiteDatabase.db,那么路径会变成xxx\Datastore\SQLiteDatabase.db\SQLiteDatabase.db,这显然是错误的。修正为:
// 确保DB_PATH是完整的数据库文件路径 conn.ConnectionString = $"data source={DB_PATH}"; // 或者如果DB_PATH是目录路径: // conn.ConnectionString = $"data source={Path.Combine(DB_PATH, "SQLiteDatabase.db")}";
4. 确保DbContext配置正确
你的ReportsContext构造函数需要正确处理传入的连接,并且确保EF能识别SQLite:
public class ReportsContext : DbContext { // 传入连接时,第二个参数设为false,避免EF自动关闭连接(因为我们用using管理) public ReportsContext(DbConnection connection) : base(connection, false) { // 可选:禁用延迟加载等,根据需求调整 // this.Configuration.LazyLoadingEnabled = false; } public DbSet<Datastore.Report> Reports { get; set; } protected override void OnModelCreating(DbModelBuilder modelBuilder) { // 显式指定表名(如果需要) modelBuilder.Entity<Datastore.Report>().ToTable("Reports"); // 配置主键(如果Report类的主键不是默认的Id) // modelBuilder.Entity<Datastore.Report>().HasKey(r => r.YourPrimaryKeyProperty); } }
5. 不要忽略异常信息
空的catch块会隐藏关键错误信息,建议修改为:
catch (System.Exception ex) { // 输出错误到日志或控制台,便于调试 Console.WriteLine($"Error: {ex.Message}"); if (ex.InnerException != null) { Console.WriteLine($"Inner Error: {ex.InnerException.Message}"); } throw; // 或者根据需求处理异常 }
按照这些步骤调整后,应该就能解决提供者名称的错误,成功向SQLite数据库添加记录了。
内容的提问来源于stack exchange,提问作者erotavlas
相关产品推荐
相关产品推荐

