2016-12-14 2 views
0

Я использую библиотеку sqlite-net-pcl в своем проекте Android Xamarin (the one by Frank Krueger, а не this fork by Øystein Krog). Похоже, что на данный момент SQLiteAsyncConnection не имеет метода Close или Dispose according to the author.Закрытие SQLiteAsyncConnection

У меня есть два вопроса. Во-первых, используя соединение в качестве одноэлементного ресурса? Во-вторых, я могу использовать sqliteAsyncConnection.GetConnection(). Закрыть(), чтобы закрыть соединение?

Я планирую сделать что-то вроде:

public static async Task CloseDbConnectionAsync(SQLiteAsyncConnection dbConnection) 
{ 
    await Task.Factory.StartNew(() => dbConnection.GetConnection().Close()); 
} 
+0

Владелец sqlite-net-pcl ответил на вопрос [здесь] (https://github.com/praeclarum/sqlite-net/issues/480). –

+0

@ ElvisXia-MSFT Да, автор был достаточно любезен, чтобы ответить мне. См. Мой ответ ниже. благодаря –

ответ

0

Чтобы ответить на мой собственный вопрос на две части:

а) бы с помощью [базы данных SQLite] соединение как одноточечного экономии ресурсов?

Да, в соответствии с this article, что делает экземпляр базы данных экземпляром одиночного объекта по всему жизненному циклу приложения может помешать вам открыть слишком много соединений и забыть закрыть их.

Это, как я реализовал это в C#:

private static SQLiteAsyncConnection _conn; 
private static readonly AsyncLock _mutex = new AsyncLock(); 

private static async Task<SQLiteAsyncConnection> GetDb(Context context) 
{ 
    try 
    { 
     using (await _mutex.LockAsync()) 
     { 
      if (_conn != null) 
      { 
       return _conn; 
      } 

      _conn = new SQLiteAsyncConnection(GetDbPath(context), storeDateTimeAsTicks: false); 

      return _conn; 
     } 
    } 
    catch (Exception e) 
    { 
     throw; 
    } 
} 

AsycnLock является частью библиотеки Nito.AsyncEx.

b) Можно использовать sqliteAsyncConnection.GetConnection(). Закрыть(), чтобы закрыть соединение?

Автор библиотеки ответил мне here. В настоящее время мой метод удаления выглядит (хотя я его нигде не использую).

private static async Task DisposeDbConnectionAsync() 
{ 
    using (await _mutex.LockAsync()) 
    { 
     if (_conn == null) 
     { 
      return; 
     } 

     await Task.Factory.StartNew(() => 
     { 
      _conn.GetConnection().Close(); 
      _conn.GetConnection().Dispose(); 
      _conn = null; 

      GC.Collect(); 
      GC.WaitForPendingFinalizers(); 
     }); 
    } 
} 

Причина, почему я звоню GC, потому что я не уверен, что метод Dispose Освобождает соединение немедленно или до запуска GC.