SQLiteCrypt

Safe, simple, fast, really fast...

SQLiteCrypt adds transparent AES 256 encryption support for SQLite, World most popular database. SQLiteCrypt is really fast, it just slows down SQLite by few percent, so your users won't even notice it's presense.

Why SQLiteCrypt?

secure your data and your users data

If your server, desktop/ mobile app or whatever else, is using SQLite, now it's time to protect it with SQLiteCrypt for your peace of mind.

Crazy fast

SQLiteCrypt is really fast. Performance is not just an afterthought, we baked it in from the start!

Easy to use

Same API as original SQLite means you just need to replace SQLite runtime

It's safe

AES-256 is reliable. Beside that SQLiteCrypt only decrypts one block (page) at time, so even memory dump is useless for hackers

It just works

SQLiteCrypt works everywhere SQLite works. Just rebuild and replace SQLite runtime and add 2 PRAGMA

Zero configuration

Leverage simplicity of SQLite. Cannot be any simpler. Just copy db file anywhere you need

5-star support

We normally response to any support request within one business day, often lots lots faster

How to use SQLiteCrypt

SQLiteCrypt Native API

SQLiteCrypt is very easy to use. SQLiteCrypt is based on SQLite with all API functions remain unchanged. All encryption/ decryption routines are performed transparently. SQLiteCrypt uses three PRAGMA statements to work with encrypted database:

PRAGMA key = 'the passphrase' // passphrase 
PRAGMA rekey = 'new passphrase' // change passphrase 
PRAGMA lic = 'the license key' // the software key

The first PRAGMA statement is used to create/ access encrypted database. The second one will re-write database with new passphrase. The third one used to identify legal copy of SQLiteCrypt software. Remark 1: These PRAGMA must be called before any query, right after opening database. You cannot do some query, then run these PRAGMA. Remark 2: rekey decrypts whole database using old passphrase, then encrypt using new passphrase. You can continue to use SQLite API functions, no need of closing and re-opening database. This is time-consuming operation. Remark 3: SQLiteCrypt has limitation on PRAGMA page_size command. You cannot change page size of encrypted database. If you want to change page size of your encrypted database, you must remove encryption first, then change page size of unencrypted database, then encrypt it again. See Example 6.

Example 1: Create/ open encrypted SQLite database

sqlite3_open_v2("data.db", &db, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL);
sqlite3_stmt* stm;
const char *pzTail;
int res = sqlite3_prepare(db, "PRAGMA key = 'ac23';", -1, &stm, &pzTail); //ac23 is database passphrase
res = sqlite3_step(stm);
res = sqlite3_prepare(db, "PRAGMA lic = '77523-009-0000007-72328';", -1, &stm, &pzTail); //software license key
res = sqlite3_step(stm);
//now you have all access to data.db

Example 2: Decrypt SQLite database (remove encryption, so any other SQLite application can open it)

sqlite3_open_v2("data.db", &db, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL);
sqlite3_stmt* stm;
const char *pzTail;
int res = sqlite3_prepare(db, "PRAGMA key = 'ac23';", -1, &stm, &pzTail); //ac23 is current passphrase
res = sqlite3_step(stm);
res = sqlite3_prepare(db, "PRAGMA lic = '77523-009-0000007-72328';", -1, &stm, &pzTail); //software license key
res = sqlite3_step(stm);
//now you have all access to encrypted data.db
res = sqlite3_prepare(db, "PRAGMA rekey = '';", -1, &stm, &pzTail); // new empty passphrase
res = sqlite3_step(stm);
//now data.db is NOT encrypted

Example 3: Change encryption key on-the-fly

sqlite3_open_v2("data.db", &db, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL);
sqlite3_stmt* stm;
const char* pzTail;
int res = sqlite3_prepare(db, "PRAGMA key = 'ac23';", -1, &stm, &pzTail); //ac23 is current passphrase
res = sqlite3_step(stm);
res = sqlite3_prepare(db, "PRAGMA lic = '77523-009-0000007-72328';", -1, &stm, &pzTail); //software license key
res = sqlite3_step(stm);
//now you have all access to encrypted data.db
res = sqlite3_prepare(db, "PRAGMA rekey = 'abc123';", -1, &stm, &pzTail); //abc123 is new passphrase
res = sqlite3_step(stm);
//now data.db re-written using new passphrase

Example 4: Encrypt SQLite database (add encryption to regular SQLite database)

sqlite3_open_v2("data.db", &db, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL);
sqlite3_stmt* stm;
const char* pzTail;
int res  = sqlite3_prepare(db, "PRAGMA lic = '77523-009-0000007-72328';", -1, &stm, &pzTail); //software license key
res = sqlite3_step(stm);
//now you have all access to regular data.db
res = sqlite3_prepare(db, "PRAGMA rekey = 'abc123';", -1, &stm, &pzTail); // encrypt database using abc123 passphrase
res = sqlite3_step(stm);
//now data.db is encrypted

Example 5: Using SQLiteCrypt command line tool Opening encrypted db without passphrase:

D:\>sqlite.exe data.db
SQLite version 3.23.0
Enter ".help" for instructions
Enter SQL statements terminated with a ";"
sqlite> select * from _MapPropertyA;
Error: file is encrypted or is not a database

Querry on an encrypted database

D:\>sqlite.exe data.db
SQLite version 3.23.0
Enter ".help" for instructions
Enter SQL statements terminated with a ";"
sqlite> PRAGMA key = 'ac23';
sqlite> PRAGMA lic = '77523-009-0000007-72328';
sqlite> select * from _MapPropertyA;
3.0|8.0
3.0|8.0

Example 6: Change page size of encrypted database In this example we see how to change encrypted db page size. Changing db page size may improve performance if file system cluster size is different then db page size (e.g. NTFS has default cluster size of 4KB, default SQLite db page size is 1KB). test.db is encrypted database with default page size 1KB and we want to change page size to 4KB. First we remove encryption from test.db:

E:\Source\SQLiteCrypt>sqlite.exe test.db
SQLite version 3.23.0
Enter ".help" for usage hints.
sqlite> PRAGMA key='abcdef'; //current passphrase
sqlite> PRAGMA lic = '77523-009-0000007-72328';
sqlite> PRAGMA rekey=''; //remove encryption
sqlite> .exit

Now change test.db page size to 4KB:

E:\Source\SQLiteCrypt>sqlite.exe test.db
SQLite version 3.23.0
Enter ".help" for usage hints.
sqlite> PRAGMA page_size; //show current page size
1024
sqlite> PRAGMA page_size=4096''; //set new page size
sqlite> VACUUM;//must run VACUUM to apply new page size
sqlite> .exit

Now encrypt test.db again:

E:\Source\SQLiteCrypt>sqlite.exe test.db
SQLite version 3.23.0
Enter ".help" for usage hints.
sqlite> PRAGMA lic = '77523-009-0000007-72328';
sqlite> PRAGMA rekey='newkey';
sqlite> .exit

C#: Windows 8/8.1/10/Phone, Xamarin (all platforms), Android and iOS

Since SQLiteCrypt API is identical as regular SQLite API, it's trivial to migrate from regular SQLite to SQLiteCrypt. Only thing to do is to compile SQLiteCrypt source code (actually only one source file sqlite3.c) for corresponding native OS and replace regular SQLite runtime by SQLiteCrypt runtime (e.g. in Windows replace sqlite3.dll). You can use any SQLite wrapper, just replace SQLite runtime. For Windows/ Windows Phone and Xamarin we recommend - SQLite-Net-PCL. Here is sample source code using SQLite-Net-PCL in Universal Apps:

private async void Button_Click(object sender, RoutedEventArgs e)
{
    var path = Path.Combine(Windows.Storage.ApplicationData.Current.LocalFolder.Path, "RAILRDS.mpl");
    try
    {
        using (SQLite.SQLiteConnection conn = new SQLite.SQLiteConnection(path))
        {
            var query = conn.Query<int>("select mapeID from _MapMetaData");
            foreach (var id in query)
            {
                 MessageDialog msg = new MessageDialog("id =" + id.ToString() + " query regular db success");
                 await msg.ShowAsync();
                 break;
             }
        }
    }
    catch(Exception ex)
    {
    }
}

private async void Button_Click_EncryptDB(object sender, RoutedEventArgs e)
{
    var path = Path.Combine(Windows.Storage.ApplicationData.Current.LocalFolder.Path, "RAILRDS.mpl");
    using (SQLite.SQLiteConnection conn = new SQLite.SQLiteConnection(path))
    {
        var query1 = conn.Query<int>("PRAGMA lic = '77523-009-0000007-72328';");
        var query2 = conn.Query<int>("PRAGMA rekey = 'abc123';");
        var query = conn.Query<int>("select mapeID from _MapMetaData");
        foreach (var id in query)
        {
            MessageDialog msg = new MessageDialog("id =" + id.ToString() + " db encrypted with password abc123");
            await msg.ShowAsync();
            break;
        }
    }
}

private async void Button_Click_QuerryEncryptedDB(object sender, RoutedEventArgs e)
{
    var path = Path.Combine(Windows.Storage.ApplicationData.Current.LocalFolder.Path, "RAILRDS.mpl");
    using (SQLite.SQLiteConnection conn = new SQLite.SQLiteConnection(path))
    {
        var query2 = conn.Query<int>("PRAGMA key = 'abc123';");
        var query1 = conn.Query<int>("PRAGMA lic = '77523-009-0000007-72328';");
        var query = conn.Query<int>("select mapeID from _MapMetaData");
        foreach (var id in query)
        {
            MessageDialog msg = new MessageDialog("id =" + id.ToString() + " query encryption db success");
            await msg.ShowAsync();
            break;
        }
    }
}

private async void Button_RemoveEncryption(object sender, RoutedEventArgs e)
{
     var path = Path.Combine(Windows.Storage.ApplicationData.Current.LocalFolder.Path, "RAILRDS.mpl");
     using (SQLite.SQLiteConnection conn = new SQLite.SQLiteConnection(path))
     {
         var query2 = conn.Query<int>("PRAGMA key = 'abc123';");
         var query1 = conn.Query<int>("PRAGMA lic = '77523-009-0000007-72328';");
         var query3 = conn.Query<int>("PRAGMA rekey = '';");
         var query = conn.Query<int>("select mapeID from _MapMetaData");
         foreach (var id in query)
        {
            MessageDialog msg = new MessageDialog("id =" + id.ToString() + ", encryption removed");
            await msg.ShowAsync();
            break;
        }
    }
}

Java

If you prefer to use Java we provide android-database-sqlitecrypt for Android and JDBC SQLite driver for other platforms with source code and detailed build instructions, so you can easily build android-database-sqlitecrypt and JDBC driver from source.

Demo version

To make sure that SQLiteCrypt meets your needs, please download and try demo builds. The demo version allows only databases with up to 6 character passphrase. Passphrase stored in open text in the database header.

Buy SQLiteCrypt

Windows binary (US$128):

Full source code (US$380):

For inquiries, technical support, please contact sales at sqlite-crypt.com.