-3

We are developing Data access framework library to be called by Business components to access SQLlite DB for Xamarin app. To execute SELECT Sql against DB, following method have been written. Am new to anonymous methods and using new features, so need suggestions Am looking for anyways to improve efficiency in this implementation.

 private static readonly Lazy<AppDB> Lazy =  new Lazy<AppDB>(() => new AppDB());

        public static AppDB Instance => Lazy.Value;
        private SQLiteAsyncConnection _conn =null;
        static object locker = new object();
        private SQLiteAsyncConnection DbConnection
        {
            get
            {
                if (_conn == null)
                {
                    LazyInitializer.EnsureInitialized(ref _conn, DependencyService.Get<ISQLite>().GetAsyncConnection);
                }
                return _conn;
            }
        }
     public List<T> ExecuteQuery<T>(string sqlQuery, object[] parameters = null) where T: class
            {
                List<T> l = new List<T>();
                try
                {
                    l = parameters !=null ? DbConnection.QueryAsync<T>(sqlQuery,parameters).Result : DbConnection.QueryAsync<T>(sqlQuery).Result;
                }
                catch (Exception e)
                { }
                return l;
            }
Sarav
  • 117
  • 1
  • 13

3 Answers3

1

Your code should be more like this:

public List<T> ExecuteQuery<T>(string sqlQuery, object[] parameters = null) where T : class
{
    if (parameters != null)
    {
        return DbConnection.Query<T>(sqlQuery, parameters)
    }
    else
    {
        return DbConnection.Query<T>(sqlQuery);
    }
}

Or better yet, something like this:

public List<T> ExecuteQuery<T>(string sqlQuery, object[] parameters = null) where T : class
{
    using (var dbc = new DbConnection())
    {
        if (parameters != null)
        {
            return dbc.Query<T>(sqlQuery, parameters).ToList();
        }
        else
        {
            return dbc.Query<T>(sqlQuery).ToList();
        }
    }
}

There are just so many issues in your existing code. You really should post more of your code if you really want to get some good guidance.

Enigmativity
  • 113,464
  • 11
  • 89
  • 172
0

In the catch block, you can assign null value to list so that you can do proper message and error handling on the screen based on the null condition.

catch (Exception e)
{
  l = null;
  //You can log the exception details in windows event viewer to see complete details.
}
Yeldar Kurmangaliyev
  • 33,467
  • 12
  • 59
  • 101
Aman Sahni
  • 212
  • 1
  • 8
0

You should rethrow exception or throw new exception and catch it when you call it.

public List<T> ExecuteQuery<T>(string sqlQuery, object[] parameters = null) where T: class
{
    try
    {
        var l = parameters !=null ? DbConnection.QueryAsync<T>(sqlQuery,parameters).Result : DbConnection.QueryAsync<T>(sqlQuery).Result;
        return l;
    }
    catch (Exception e)
    { 
        throw;
        // or throw new MyCustomRepositoryException(e);
    }
}

// Usage:
try
{
    var documents = myClass.ExecuteQuery<Document>(...);
}
catch (Exception ex) // or catch (MyCustomRepositoryException ex) 
{
    // do whatever your system is expected to do in case of error
}

Tehnically, you can just ignore error and return null or new List<T>, but in most cases it is wrong architecturally:

  • "give me list or throw exception" is an expected behavior for a method with List<T> return value
  • a callee won't be able to distinguish empty list and error (in case of List<T>) / not found object or error (in case of T)
  • it adds some requirements on DbConnection, it should be recoverable. some objects cannot recover from exceptions, and therefore you can try to continue working with object in faulted state
  • it does not guarantee to stop code execution and it can cause unexpected behavior in callee method or even other places of code
  • etc.
Yeldar Kurmangaliyev
  • 33,467
  • 12
  • 59
  • 101