尝试创建一个受密码保护的sqlite db,如Password protected SQLite with Entity Framework Core
但是当使用EnsureCreated();
创建数据库时,它会抛出一个处置异常的对象。
我不知道为什么应该有一个处理过的SQLiteCommand对象?
添加了nuget包
Microsoft.EntityFrameworkCore.Sqlite v1.1.0
System.Data.SQLite.Core v1.0.104
DbContext类
using Microsoft.EntityFrameworkCore;
using System.Data.SQLite;
class TestMenuDataContext : DbContext
{
public SQLiteConnection Connection { get; set; }
public SQLiteCommand Command { get; set; }
public TestMenuDataContext()
{
//Database.Migrate();
//Database.EnsureCreated();
}
public DbSet<Test> TestMenu { get; set; }
... and some more other tables ...
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
Connection = new SQLiteConnection(@"Data Source=TestMenu.db;");
Connection.Open();
Command = Connection.CreateCommand();
Command.CommandText = "SELECT quote($password);";
Command.Parameters.AddWithValue("$password", "TheUltimatePasswordPhraseWillBeAddedLaterHere");
var escapedPassword = (string)Command.ExecuteScalar();
Command.Parameters.Clear();
Command.CommandText = "PRAGMA key = " + escapedPassword + ";";
Command.ExecuteNonQuery();
optionsBuilder.UseSqlite(Connection);
// instead of password configuration above with this single line (no pw) below everything is fine
//optionsBuilder.UseSqlite("Filename=./TestMenu.db");
}
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
... some key constraints
}
}
WPF Gui中的调用部分(无MVVM)
private TestMenuDataContext _Db;
private void Window_Loaded(object sender, RoutedEventArgs e)
{
//Do not load your data at design time.
if (!System.ComponentModel.DesignerProperties.GetIsInDesignMode(this))
{
_Db = new TestMenuDataContext();
_Db.Database.EnsureCreated();
在此之前,我有本地上下文对象和本地连接和命令对象。像:
using (var db = new TestMenuDataContext())
{
db.Database.EnsureCreated();
和
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
var conn = new SQLiteConnection(@"Data Source=yourSQLite.db;");
conn.Open();
var command = conn.CreateCommand();
command.CommandText = "PRAGMA key = password;";
command.ExecuteNonQuery();
optionsBuilder.UseSqlite(conn);
编辑28Feb2017:
另外经过测试,如C# SQLite, database being left locked after a read
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
using (SQLiteConnection connection = new SQLiteConnection(@"Data Source=TestMenu.db;"))
using (SQLiteCommand command = connection.CreateCommand())
{
connection.Open();
command.CommandText = "SELECT quote($password);";
command.Parameters.AddWithValue("$password", "TheUltimatePasswordPhraseWillBeAddedHere");
var escapedPassword = (string)command.ExecuteScalar();
command.Parameters.Clear();
command.CommandText = "PRAGMA key = " + escapedPassword + ";";
command.ExecuteNonQuery();
optionsBuilder.UseSqlite(connection);
}