EF Core跨Windows/Linux平台SQLite迁移报错__EFMigrationsHistory表不存在
EF Core SQLite跨平台路径问题解决方案
问题根源
你通过Environment.SpecialFolder.Personal拼接的数据库路径虽然能正常打印,但EF Core迁移工具(Add-Migration/Update-Database)执行时,实际访问的路径可能和程序运行时不一致,导致找不到迁移历史表__EFMigrationsHistory——本质是迁移工具的工作目录与程序运行时的工作目录不匹配,或者路径拼接存在平台兼容性问题。
正确处理方式
1. 用Path.Combine生成跨平台兼容路径
Windows和Linux的路径分隔符不同,直接字符串拼接容易出错,改用Path.Combine自动适配平台:
private string DbPath => Path.Combine( Environment.GetFolderPath(Environment.SpecialFolder.Personal), "smart_contracts.db"); protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) { optionsBuilder.UseSqlite($"Data Source={DbPath}"); }
2. 统一迁移工具与程序的工作目录
EF Core迁移工具默认以项目文件所在目录为工作目录,而Environment.SpecialFolder.Personal指向用户专属目录(Windows为C:\Users\<用户名>\Documents,Linux为/home/<用户名>),两者不一致会导致迁移工具访问的数据库和程序运行时的不是同一个。
解决办法:
- 通过配置文件统一路径:
在appsettings.json中配置连接字符串:
然后在DbContext中读取配置:{ "ConnectionStrings": { "SmartContractsDb": "Data Source=./smart_contracts.db" } }protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) { var config = new ConfigurationBuilder() .SetBasePath(Directory.GetCurrentDirectory()) .AddJsonFile("appsettings.json") .Build(); optionsBuilder.UseSqlite(config.GetConnectionString("SmartContractsDb")); } - 强制使用绝对路径:
如果必须用用户目录路径,确保生成绝对路径并验证格式:private string DbPath => Path.GetFullPath(Path.Combine( Environment.GetFolderPath(Environment.SpecialFolder.Personal), "smart_contracts.db"));
3. 验证数据库文件位置
执行迁移前,手动检查DbPath指向的路径是否存在smart_contracts.db:
- Windows:打开资源管理器导航到用户Documents目录查看
- Linux:终端执行
ls ~/smart_contracts.db检查
如果文件不存在,说明迁移工具在其他目录创建了空数据库,删除多余文件后重新执行Update-Database。
相对路径正常工作的原因
当使用Data Source=smart_contracts.db时,EF Core默认在当前工作目录(项目目录)创建数据库,迁移工具和程序运行时访问的是同一个文件,因此不会出现找不到表的问题。
内容的提问来源于stack exchange,提问作者Patrick
相关产品推荐
相关产品推荐

