无法打开数据库文件(滥用)SqlLiteAsyncConnection

时间:2019-06-15 22:54:55

标签: c# sqlite xamarin.forms uwp

尝试打开我的SQLite连接时出现异常“无法打开数据库文件:[路径](滥用)”。

我正在创建Xamarin.Forms应用程序,并在UWP中进行调试,这是我遇到异常的地方。

我的数据存储类的构造函数创建连接和表:

internal static string DBPath
{
    get
    {
        const string FILE_NAME = "TheRandomizer.db3";
        if (Device.RuntimePlatform == Device.Android)
        {
            return Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Personal), FILE_NAME);
        }
        else
        {
             return Path.Combine(ApplicationData.Current.LocalFolder.Path, FILE_NAME);
        }
    }
}

public SqliteDataStore()
{
    _database = new SQLiteAsyncConnection(DBPath, SQLiteOpenFlags.Create);
    // Fails trying to perform this action:
    _database.CreateTableAsync<GeneratorTable>().Wait();
    _database.CreateTableAsync<TagTable>().Wait();
}

可以查看here on my GitHub的完整来源。

堆栈跟踪:

  

at System.Threading.Tasks.Task.Wait(Int32 millisecondsTimeout,   的CancellationToken cancelToken()   System.Threading.Tasks.Task.Wait()在   TheRandomizer.Services.SqliteDataStore..ctor()在   TheRandomizer.ViewModels.BaseViewModel.get_DataStore()在   TheRandomizer.ViewModels.GeneratorListViewModel.ExecuteLoadItemsCommand()

1 个答案:

答案 0 :(得分:0)

更新

我已经在本地测试了您的代码,并看到该行为实际上正在发生,并且在进行一些调试之后,我认为我可能有两个原因:

首先,构造函数只有SQLiteOpenFlags.Create标志。显然,这不给您任何其他权限,包括读/写。相反,您可以完全省略第二个参数:

_database = new SQLiteAsyncConnection(DBPath);

或包含显式的ReadWrite标志(由于建议用于异步连接,我还包含了FullMutex标志):

_database = new SQLiteAsyncConnection(
     DBPath, 
     SQLiteOpenFlags.Create | 
     SQLiteOpenFlags.FullMutex | 
     SQLiteOpenFlags.ReadWrite );

在数据库中创建GeneratorTable表时发生第二个问题。 SQLite不知道如何存储Version属性,因为它是自定义的GeneratorVersion类型。因此,您可能必须将其分解为简单的属性或添加一个[Ignore]属性。

原始答案

我检查了您的源代码,发现您正在尝试将数据库存储在Environment.SpecialFolder.Personal文件夹中。对于UWP,它实际上解析为C:\Users\$Username$\Documents,由于UWP应用程序正在沙箱中运行,因此它无权访问。

相反,您必须使用应用程序的数据文件夹(您可能实际上打算这样做):

Path.Combine(ApplicationData.Current.LocalFolder.Path, FILE_NAME);