mirror of
https://github.com/bitwarden/android.git
synced 2024-10-31 07:05:35 +03:00
background thread full/incremental sync operations. pool sqlconnection. sqlconnection to FullMutex mode for multithread environment. try/catch decryption errors.
This commit is contained in:
parent
0be15d7a34
commit
29c7a0ccf0
4 changed files with 104 additions and 71 deletions
|
@ -1,22 +1,29 @@
|
|||
using System;
|
||||
using System.IO;
|
||||
using Bit.App.Abstractions;
|
||||
using SQLite;
|
||||
|
||||
namespace Bit.Android.Services
|
||||
{
|
||||
public class SqlService : ISqlService
|
||||
{
|
||||
public SQLite.SQLiteConnection GetConnection()
|
||||
private SQLiteConnection _connection;
|
||||
|
||||
public SQLiteConnection GetConnection()
|
||||
{
|
||||
if(_connection != null)
|
||||
{
|
||||
return _connection;
|
||||
}
|
||||
|
||||
var sqliteFilename = "bitwarden.db3";
|
||||
var documentsPath = Environment.GetFolderPath(Environment.SpecialFolder.Personal); // Documents folder
|
||||
var path = Path.Combine(documentsPath, sqliteFilename);
|
||||
|
||||
Console.WriteLine(path);
|
||||
var conn = new SQLite.SQLiteConnection(path);
|
||||
|
||||
// Return the database connection
|
||||
return conn;
|
||||
_connection = new SQLiteConnection(path,
|
||||
SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.Create | SQLiteOpenFlags.FullMutex | SQLiteOpenFlags.SharedCache);
|
||||
return _connection;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
117
src/App/App.cs
117
src/App/App.cs
|
@ -57,35 +57,7 @@ namespace Bit.App
|
|||
MessagingCenter.Subscribe<Application, bool>(Current, "Resumed", async (sender, args) =>
|
||||
{
|
||||
await CheckLockAsync(args);
|
||||
if(_connectivity.IsConnected)
|
||||
{
|
||||
var attempt = 0;
|
||||
do
|
||||
{
|
||||
try
|
||||
{
|
||||
await _syncService.IncrementalSyncAsync();
|
||||
break;
|
||||
}
|
||||
catch(WebException)
|
||||
{
|
||||
Debug.WriteLine("Failed to sync.");
|
||||
if(attempt >= 1)
|
||||
{
|
||||
await _userDialogs.AlertAsync("Unable to automatically sync.");
|
||||
}
|
||||
else
|
||||
{
|
||||
await Task.Delay(1000);
|
||||
}
|
||||
attempt++;
|
||||
}
|
||||
} while(attempt <= 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
Debug.WriteLine("Not connected.");
|
||||
}
|
||||
await Task.Run(() => IncrementalSyncAsync()).ConfigureAwait(false);
|
||||
});
|
||||
|
||||
MessagingCenter.Subscribe<Application, bool>(Current, "Lock", async (sender, args) =>
|
||||
|
@ -99,30 +71,7 @@ namespace Bit.App
|
|||
// Handle when your app starts
|
||||
await CheckLockAsync(false);
|
||||
_databaseService.CreateTables();
|
||||
if(_connectivity.IsConnected)
|
||||
{
|
||||
var attempt = 0;
|
||||
do
|
||||
{
|
||||
try
|
||||
{
|
||||
await _syncService.FullSyncAsync();
|
||||
break;
|
||||
}
|
||||
catch(WebException)
|
||||
{
|
||||
if(attempt >= 1)
|
||||
{
|
||||
await _userDialogs.AlertAsync("Unable to automatically sync. Manual sync required.");
|
||||
}
|
||||
else
|
||||
{
|
||||
await Task.Delay(1000);
|
||||
}
|
||||
attempt++;
|
||||
}
|
||||
} while(attempt <= 1);
|
||||
}
|
||||
await Task.Run(() => FullSyncAsync()).ConfigureAwait(false);
|
||||
|
||||
Debug.WriteLine("OnStart");
|
||||
}
|
||||
|
@ -155,6 +104,68 @@ namespace Bit.App
|
|||
}
|
||||
}
|
||||
|
||||
private async Task IncrementalSyncAsync()
|
||||
{
|
||||
if(_connectivity.IsConnected)
|
||||
{
|
||||
var attempt = 0;
|
||||
do
|
||||
{
|
||||
try
|
||||
{
|
||||
await _syncService.IncrementalSyncAsync();
|
||||
break;
|
||||
}
|
||||
catch(WebException)
|
||||
{
|
||||
Debug.WriteLine("Failed to incremental sync.");
|
||||
if(attempt >= 1)
|
||||
{
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
await Task.Delay(1000);
|
||||
}
|
||||
attempt++;
|
||||
}
|
||||
} while(attempt <= 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
Debug.WriteLine("Not connected.");
|
||||
}
|
||||
}
|
||||
|
||||
private async Task FullSyncAsync()
|
||||
{
|
||||
if(_connectivity.IsConnected)
|
||||
{
|
||||
var attempt = 0;
|
||||
do
|
||||
{
|
||||
try
|
||||
{
|
||||
await _syncService.FullSyncAsync();
|
||||
break;
|
||||
}
|
||||
catch(WebException)
|
||||
{
|
||||
Debug.WriteLine("Failed to full sync.");
|
||||
if(attempt >= 1)
|
||||
{
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
await Task.Delay(1000);
|
||||
}
|
||||
attempt++;
|
||||
}
|
||||
} while(attempt <= 1);
|
||||
}
|
||||
}
|
||||
|
||||
private async Task CheckLockAsync(bool forceLock)
|
||||
{
|
||||
// Only lock if they are logged in
|
||||
|
|
|
@ -1,7 +1,9 @@
|
|||
using System;
|
||||
using System.Diagnostics;
|
||||
using System.Text;
|
||||
using Bit.App.Abstractions;
|
||||
using Bit.App.Models;
|
||||
using Org.BouncyCastle.Crypto;
|
||||
using Org.BouncyCastle.Crypto.Digests;
|
||||
using Org.BouncyCastle.Crypto.Engines;
|
||||
using Org.BouncyCastle.Crypto.Generators;
|
||||
|
@ -113,14 +115,20 @@ namespace Bit.App.Services
|
|||
throw new ArgumentNullException(nameof(encyptedValue));
|
||||
}
|
||||
|
||||
var keyParamWithIV = new ParametersWithIV(_keyParameter, encyptedValue.InitializationVectorBytes, 0, InitializationVectorSize);
|
||||
|
||||
_cipher.Init(false, keyParamWithIV);
|
||||
byte[] comparisonBytes = new byte[_cipher.GetOutputSize(encyptedValue.CipherTextBytes.Length)];
|
||||
var length = _cipher.ProcessBytes(encyptedValue.CipherTextBytes, comparisonBytes, 0);
|
||||
_cipher.DoFinal(comparisonBytes, length);
|
||||
|
||||
return Encoding.UTF8.GetString(comparisonBytes, 0, comparisonBytes.Length).TrimEnd('\0');
|
||||
try
|
||||
{
|
||||
var keyParamWithIV = new ParametersWithIV(_keyParameter, encyptedValue.InitializationVectorBytes, 0, InitializationVectorSize);
|
||||
_cipher.Init(false, keyParamWithIV);
|
||||
byte[] comparisonBytes = new byte[_cipher.GetOutputSize(encyptedValue.CipherTextBytes.Length)];
|
||||
var length = _cipher.ProcessBytes(encyptedValue.CipherTextBytes, comparisonBytes, 0);
|
||||
_cipher.DoFinal(comparisonBytes, length);
|
||||
return Encoding.UTF8.GetString(comparisonBytes, 0, comparisonBytes.Length).TrimEnd('\0');
|
||||
}
|
||||
catch(Exception e)
|
||||
{
|
||||
Debug.WriteLine("Could not decrypt '{0}'. {1}", encyptedValue, e.Message);
|
||||
return "[error: cannot decrypt]";
|
||||
}
|
||||
}
|
||||
|
||||
public byte[] MakeKeyFromPassword(string password, string salt)
|
||||
|
|
|
@ -2,24 +2,31 @@
|
|||
using System.IO;
|
||||
using Bit.App.Abstractions;
|
||||
using Foundation;
|
||||
using SQLite;
|
||||
|
||||
namespace Bit.iOS.Core.Services
|
||||
{
|
||||
public class SqlService : ISqlService
|
||||
{
|
||||
public SQLite.SQLiteConnection GetConnection()
|
||||
private SQLiteConnection _connection;
|
||||
|
||||
public SQLiteConnection GetConnection()
|
||||
{
|
||||
if(_connection != null)
|
||||
{
|
||||
return _connection;
|
||||
}
|
||||
|
||||
var sqliteFilename = "bitwarden.db3";
|
||||
var fileManager = new NSFileManager();
|
||||
var appGroupContainer = fileManager.GetContainerUrl("group.com.8bit.bitwarden");
|
||||
var libraryPath = Path.Combine(appGroupContainer.Path, "Library"); // Library folder
|
||||
var path = Path.Combine(libraryPath, sqliteFilename);
|
||||
|
||||
Console.WriteLine(path);
|
||||
var conn = new SQLite.SQLiteConnection(path);
|
||||
|
||||
// Return the database connection
|
||||
return conn;
|
||||
_connection = new SQLiteConnection(path,
|
||||
SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.Create | SQLiteOpenFlags.FullMutex | SQLiteOpenFlags.SharedCache);
|
||||
return _connection;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue