SQLiteでできたDBにパスワードをつけたいと思ったのですが、System.Data.SQLiteでは対応していないようです。
using (var con = new SQLiteConnection("Data Source=" + DBName + ";Version=3;Password=passwd;"))
Password構文が使えないらしく、暗号化libraryが組み込まれていないと怒られてしまう。
System.Data.SQLite.SQLiteException: 'SQL logic error Cannot use "Password" connection string property: library was not built with encryption support, please see "https://www.sqlite.org/see" for more information'
を見ると、SQLite Encryption Extension
ダウンロードしてコンパイルしないといけないの?なんかめんどくさそう。
ここがポイント!
dbファイルにパスワード暗号を利用したいのであれば、System.Data.SQLiteを使わないようにします。
これは、Entity Framework Core(EFCore)を使用してSQLite暗号化データベースを使用する方法を示す実際の例です。
Visualstudio .NetアプリケーションでEntity Framework Coreを利用しSQLiteで暗号化できる事が記載してあります。
Entity Framework チームは、Brice のプロトタイプに基づいて Microsoft.Data.Sqlite を作成することを決定しました。 これにより、.NET Core の目標に沿った、軽量で最新の新たな実装を作成
System.Data.SQLite との比較
もっと端的にいうなら
DataAdapter,DataTableが使えない(回避方法について後述)
DBType(データ型)が4種類しかない
って事です。
.NET framework 4.7.2にてテストを行います。新しいWPFプロジェクトを作成します。
NuGetするもの
Microsoft.EntityFrameworkCore
Microsoft.EntityFrameworkCore.Design
Microsoft.EntityFrameworkCore.Sqlite.Core
SQLitePCLRaw.bundle_e_sqlcipher
の4つです。
NuGetパッケージの管理をクリック
Microsoft.EntityFrameworkCore 3.1.10をインストール
Microsoft.EntityFrameworkCore.Design 3.1.10をインストール
Microsoft.EntityFrameworkCore.Sqlite.Core 3.1.10をインストール
SQLitePCLRaw.bundle_e_sqlcipher 2.0.4をインストール
DB作成 パスワード暗号付きでSQLiteDBを作成します
DB書込 パスワード暗号付きSQLiteDBへレコードを書き込みます
DB読込 パスワード暗号付きSQLiteDBからテーブルをDataAdapterで接続TableにFillします
SqliteConnectionStringBuilder を使います
使用例
var connectionString = new SqliteConnectionStringBuilder(baseConnectionString)
{
Mode = SqliteOpenMode.ReadWriteCreate,
Password = password
}.ToString();
using System.Windows;
using System.Data;
using Microsoft.Data.Sqlite;
namespace sqliteMS
{
/// <summary>
/// MainWindow.xaml の相互作用ロジック
/// </summary>
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
}
string connectionString = new SqliteConnectionStringBuilder("Data Source = test1.db ; Cache = Shared")
{
Mode = SqliteOpenMode.ReadWriteCreate,
Password = "pass"
}.ToString();
private void B_MakeDB_Click(object sender, RoutedEventArgs e)
{
// コネクションを開いてテーブル作成して閉じる
using (var con = new SqliteConnection(connectionString))
{
con.Open();
using (SqliteCommand command = con.CreateCommand())
{
command.CommandText = "create table t_product(CD INTEGER PRIMARY KEY AUTOINCREMENT, productname TEXT, price INTEGER)";
command.ExecuteNonQuery();
}
con.Close();
}
}
private void V_DBWrite_Click(object sender, RoutedEventArgs e)
{
using (var con = new SqliteConnection(connectionString))
{
con.Open();
using (SqliteTransaction trans = con.BeginTransaction())
{
SqliteCommand cmd = con.CreateCommand();
// インサート
cmd.CommandText = "INSERT INTO t_product (productname, price) VALUES (@Product, @Price)";
// パラメータセット
cmd.Parameters.Add("Product", SqliteType.Text);
cmd.Parameters.Add("Price", SqliteType.Integer);
// データ追加
cmd.Parameters["Product"].Value = t_Product.Text;
cmd.Parameters["Price"].Value = int.Parse(t_Price.Text);
cmd.ExecuteNonQuery();
// コミット
trans.Commit();
}
}
}
Microsoft.Data.Sqliteを利用していると、DataAdapter,DataTableが使えないのですが、DataAdapter,DataTableを使う方法があります。
ここでSystem.Data.SQLiteを使ってDataAdapter,DataTableを拝借します。
System.Data.SQLiteをNuGETします。
private void B_DBRead_Click(object sender, RoutedEventArgs e)
{
System.Data.Common.DbProviderFactory factory = System.Data.Common.DbProviderFactories.GetFactory("System.Data.SQLite");
using (SqliteConnection con = new SqliteConnection(connectionString))
{
// DataTableを生成します。
var dataTable = new DataTable();
// コマンドを作る
System.Data.Common.DbCommand command = con.CreateCommand();
command.CommandText = "SELECT * FROM t_product";
command.CommandType = CommandType.Text;
command.Connection = con;
// SQLの実行
var adapter = factory.CreateDataAdapter();
adapter.SelectCommand = command;
adapter.Fill(dataTable);
dataGrid.DataContext = dataTable;
}
}
※dataGrid.DataContext にdataTableをBindingするためには XAML側に
ItemSource=”{Binding}”
と指定しておく必要があります
<DataGrid x:Name="dataGrid" HorizontalAlignment="Left" Height="900" Margin="96,52,0,0" VerticalAlignment="Top" Width="1614" ItemsSource="{Binding}"/>
A5:SQL Mk-2を使って作成したDBファイルが読込できるか確認してみました。
とりあえず、読込はできません。パスワードを指定しても読み込めません。