C# Xamarin-Entity Framework-SqLite-GetItemsAsync:无法打开数据库文件
在Visual studio 2017中,我创建了一个跨平台移动应用程序(Xamarin.Forms)C# Xamarin-Entity Framework-SqLite-GetItemsAsync:无法打开数据库文件,c#,sqlite,xamarin,xamarin.forms,entity-framework-core,C#,Sqlite,Xamarin,Xamarin.forms,Entity Framework Core,在Visual studio 2017中,我创建了一个跨平台移动应用程序(Xamarin.Forms) NetStandard2.0 Microsoft.Data.Sqlite.Core 2.2.0 Microsoft.EntityFrameworkCore 2.2.0 Microsoft.EntityFrameworkCore.Sqlite 2.2.0 Microsoft.EntityFrameworkCore.Tools 2.2.0 我首先用实体框架将代码迁移到Sqlite。所有表都已成
- NetStandard2.0
- Microsoft.Data.Sqlite.Core 2.2.0
- Microsoft.EntityFrameworkCore 2.2.0
- Microsoft.EntityFrameworkCore.Sqlite 2.2.0
- Microsoft.EntityFrameworkCore.Tools 2.2.0
[XamlCompilation(XamlCompilationOptions.Compile)]
公共部分类项目页面:ContentPage
{
ItemsViewModel视图模型;
公共项目
{
初始化组件();
//1代码从这里开始
BindingContext=viewModel=newitemsviewmodel();
}
已选择异步(对象发送方,SelectedItemChangedEventArgs args)
{
var item=args.SelectedItem作为项目;
如果(项==null)
返回;
等待Navigation.PushAsync(newitemDetailPage(newitemDetailViewModel(item));
ItemsListView.SelectedItem=null;
}
已单击异步无效添加项(对象发送方,事件参数e)
{
wait Navigation.PushModalAsync(new NavigationPage(new NewItemPage());
}
//添加“async”并不能解决问题
受保护的异步重写void OnAppearing()
{
base.OnAppearing();
if(viewModel.Items.Count==0)
//2代码在此继续
viewModel.LoadItemsCommand.Execute(null);
}
}
公共类ItemsViewModel:BaseViewModel
{
公共ObservableCollection项{get;set;}
公共命令LoadItemsCommand{get;set;}
public ItemsViewModel()
{
Title=“浏览”;
Items=新的ObservableCollection();
//3代码在此继续
LoadItemsCommand=new命令(async()=>await ExecuteLoadItemsCommand());
订阅(此“AddItem”,异步(obj,item)=>
{
var newItem=作为项目的项目;
项目。添加(新项目);
等待DataStore.AddItemAsync(newItem);
});
}
//我的测试方法
公共异步任务TestSqLiteDataStoreAsync()
{
SqLiteDataStore SqLiteDataStore=新SqLiteDataStore();
返回wait-SqLiteDataStore.GetItemsAsync(false);
}
异步任务ExecuteLoadItemsCommand()
{
如果(忙)
返回;
IsBusy=true;
尝试
{
Items.Clear();
//4代码在此继续
var items=await DataStore.GetItemsAsync(true);
foreach(项目中的var项目)
{
项目。添加(项目);
}
}
捕获(例外情况除外)
{
Debug.WriteLine(ex);
}
最后
{
IsBusy=false;
}
}
}
公共类SqLiteDataStore:IDataStore
{
公共字符串dbFolder=System.Environment.GetFolderPath(System.Environment.SpecialFolder.Personal);
公共字符串fileName=“TestSqLite.db”;
公共SqLiteDataStore(){}
公共异步任务GetItemsAsync(bool forceRefresh=false)
{
尝试
{
使用(var db=new Models.MyContext(Path.Combine(dbFolder,fileName)))
{
List list1=新列表();
List list2=新列表();
//我在这里得到了错误
list1=await db.Person.toListSync();
foreach(列表1中的人员)
{
项目=新项目(人);
清单2.添加(项目);
}
返回列表2;
}
}
捕获(例外)
{
投掷;
}
}
公共异步任务AddItemAsync(项)
{
抛出新的NotImplementedException();
}
公共任务更新同步(项目)
{
抛出新的NotImplementedException();
}
公共任务DeleteItemAsync(字符串id)
{
抛出新的NotImplementedException();
}
公共任务GetItemAsync(字符串id)
{
抛出新的NotImplementedException();
}
}
根据获取
“无法打开数据库文件”
错误-可能是将代码指向不存在的文件
“未找到表”错误意味着它找到了数据库,但没有找到您要查找的表。另一方面,“无法打开数据库文件”意味着它甚至找不到数据库,甚至懒得寻找表。当您得到“找不到表”时,您离它正常工作更近了。正如我们前面提到的,只需将
环境.SpecialFolder.Personal
替换为环境.SpecialFolder.LocalApplicationData[XamlCompilation(XamlCompilationOptions.Compile)]
public partial class ItemsPage : ContentPage
{
ItemsViewModel viewModel;
public ItemsPage()
{
InitializeComponent();
//1 code starts here
BindingContext = viewModel = new ItemsViewModel();
}
async void OnItemSelected(object sender, SelectedItemChangedEventArgs args)
{
var item = args.SelectedItem as Item;
if (item == null)
return;
await Navigation.PushAsync(new ItemDetailPage(new ItemDetailViewModel(item)));
ItemsListView.SelectedItem = null;
}
async void AddItem_Clicked(object sender, EventArgs e)
{
await Navigation.PushModalAsync(new NavigationPage(new NewItemPage()));
}
//adding 'async' did not solve the problem
protected async override void OnAppearing()
{
base.OnAppearing();
if (viewModel.Items.Count == 0)
//2 code continues here
viewModel.LoadItemsCommand.Execute(null);
}
}
public class ItemsViewModel : BaseViewModel
{
public ObservableCollection<Item> Items { get; set; }
public Command LoadItemsCommand { get; set; }
public ItemsViewModel()
{
Title = "Browse";
Items = new ObservableCollection<Item>();
//3 code continues here
LoadItemsCommand = new Command(async () => await ExecuteLoadItemsCommand());
MessagingCenter.Subscribe<NewItemPage, Item>(this, "AddItem", async (obj, item) =>
{
var newItem = item as Item;
Items.Add(newItem);
await DataStore.AddItemAsync(newItem);
});
}
//My test method
public async Task<List<Item>> TestSqLiteDataStoreAsync()
{
SqLiteDataStore SqLiteDataStore = new SqLiteDataStore();
return await SqLiteDataStore.GetItemsAsync(false);
}
async Task ExecuteLoadItemsCommand()
{
if (IsBusy)
return;
IsBusy = true;
try
{
Items.Clear();
//4 code continues here
var items = await DataStore.GetItemsAsync(true);
foreach (var item in items)
{
Items.Add(item);
}
}
catch (Exception ex)
{
Debug.WriteLine(ex);
}
finally
{
IsBusy = false;
}
}
}
public class SqLiteDataStore : IDataStore<Item>
{
public string dbFolder = System.Environment.GetFolderPath(System.Environment.SpecialFolder.Personal);
public string fileName = "TestSqLite.db";
public SqLiteDataStore() { }
public async Task<List<Item>> GetItemsAsync(bool forceRefresh = false)
{
try
{
using (var db = new Models.MyContext(Path.Combine(dbFolder, fileName)))
{
List<Person> list1 = new List<Person>();
List<Item> list2 = new List<Item>();
//5 I get the error here
list1 = await db.Person.ToListAsync();
foreach (Person person in list1)
{
Item item = new Item(person);
list2.Add(item);
}
return list2;
}
}
catch (Exception)
{
throw;
}
}
public async Task<bool> AddItemAsync(Item item)
{
throw new NotImplementedException();
}
public Task<bool> UpdateItemAsync(Item item)
{
throw new NotImplementedException();
}
public Task<bool> DeleteItemAsync(string id)
{
throw new NotImplementedException();
}
public Task<Item> GetItemAsync(string id)
{
throw new NotImplementedException();
}
}
[3/10/2019 4:26:28 PM Informational] [xUnit.net 00:00:00.02] xUnit.net VSTest Adapter v2.4.0 (64-bit .NET Core 4.6.27129.04)
[3/10/2019 4:26:31 PM Informational] [xUnit.net 00:00:03.41] Discovering: XUnitTestProject1
[3/10/2019 4:26:31 PM Informational] [xUnit.net 00:00:03.61] Discovered: XUnitTestProject1
[3/10/2019 4:26:31 PM Informational] ========== Discover test finished: 1 found (0:00:11.5651246) ==========
[3/10/2019 4:26:31 PM Informational] ------ Run test started ------
[3/10/2019 4:26:32 PM Informational] [xUnit.net 00:00:00.00] xUnit.net VSTest Adapter v2.4.0 (64-bit .NET Core 4.6.27129.04)
[3/10/2019 4:26:33 PM Informational] [xUnit.net 00:00:00.63] Discovering: XUnitTestProject1
[3/10/2019 4:26:33 PM Informational] [xUnit.net 00:00:00.70] Discovered: XUnitTestProject1
[3/10/2019 4:26:33 PM Informational] [xUnit.net 00:00:00.70] Starting: XUnitTestProject1
[3/10/2019 4:26:35 PM Informational] [xUnit.net 00:00:02.60] Finished: XUnitTestProject1
[3/10/2019 4:26:35 PM Informational] ========== Run test finished: 1 run (0:00:03.9952011) ==========
Microsoft.Data.Sqlite.SqliteException (0x80004005): SQLite Error 14: 'unable to open database file'.
at Microsoft.Data.Sqlite.SqliteException.ThrowExceptionForRC(Int32 rc, sqlite3 db)
at Microsoft.Data.Sqlite.SqliteConnection.Open()
at System.Data.Common.DbConnection.OpenAsync(CancellationToken cancellationToken)
C:\Users\SomeUser\AppData\Local\Packages\0eea1ae6-65c3-42e9-9a50-869730e52f63_2ft3g98yvwh70\LocalState