Connect to sql lite db in windows store app - c#

Hi can someone recommend me how I can connect to sql lite db in Windows store app? I add my file called database.sqlite to my app like new item. But I cannot find how I can connect to my existing file. I find this:
StorageFile DataFile =
await ApplicationData.Current.LocalFolder.GetFileAsync("database.sqlite");
But I dont know how write correct path to file. Does anyone have some idea.

When you add a database file to your project, it is considered an asset of your project. The file is stored with your application, and is in a read-only location.
To access the read-only version, you have to use this:
StorageFile file = await StorageFile.GetFileFromApplicationUriAsync(
new Uri("ms-appx:///relative/path/to/db/database.sqlite"));
Where relative/path/to/db is the path relative from the top level of your project. For example if your project has a folder called Data that has your db file in it, then you would use "ms-appx:///Data/database.sqlite".
Since the file is read-only, you cannot write to it. If you need to do so, you must first make a copy of it into a writeable location (e.g. ApplicationData.Current.LocalFolder):
// get reference to read-only copy
StorageFile readonlyDb = await StorageFile.GetFileFromApplicationUriAsync(
new Uri("ms-appx:///Data/database.sqlite"));
StorageFolder localFolder = ApplicationData.Current.LocalFolder;
// make a copy in a writeable location
StorageFile DataFile = await readonlyDb.CopyAsync(localFolder, "database.sqlite");
// now open a sqlite connection to DataFile...

Related

Open SQLite connection in UWP right after moving StorageFile

Prologue:
I am writing SQLite GUI client for UWP. I use Microsoft.Data.Sqlite library for SQLite API with C#. Also I use a redirection table to be able to open database within my sandbox app which is published in Microsoft Store. Redirection table replaces CreateFileW to CreateFileFromAppW calls and similar.
Problem:
User has File -> Save as feature. When user creates a new database file is created inside app local directory. Next when user saves his/her database as I need to move this file. I use StorageFile API cause I cannot use any other file API within a sandbox app. So I call:
var savePicker = new Windows.Storage.Pickers.FileSavePicker();
savePicker.SuggestedStartLocation = Windows.Storage.Pickers.PickerLocationId.DocumentsLibrary;
savePicker.FileTypeChoices.Add("SQLite3 Database", new List<string>() { ".sqlite", ".db" });
savePicker.SuggestedFileName = "Database";
var file = await savePicker.PickSaveFileAsync();
if(null != file)
{
Windows.Storage.AccessCache.StorageApplicationPermissions.FutureAccessList.Add(file);
sqliteConnection.Close(); // it is important cause if I skip this moving a file will fail
var localFolder = ApplicationData.Current.LocalFolder;
var currentStorageFile = await localFolder.GetFileAsync(App.UnsavedDatabaseFileName); // here I obtain StorageFile for opened database
await currentStorageFile.MoveAndReplaceAsync(file); // here I move a file
sqliteConnection = new SqliteConnection("Data Source=" + file.Path);
sqliteConnection.Open(); // this line fails with error 14: cannot open database file
}
I also tried to skip closing and reopening a connection -> then moving a file fails.
If I call FileOpenPicker between await currentStorageFile.MoveAndReplaceAsync(file); and sqliteConnection = new SqliteConnection("Data Source=" + file.Path); then everything will work fine but showing file open picker right after file save picker is a very bad user experience. I know that sandboxed app gives file access permission only after user selected a file manually. But it looks like that FileSavePicker does not give me a permission just like FileOpenPicker does. I could not find any info about it.
Epilogue:
This is the app https://sqliteman.dev. Please feel free to criticize cause it is what makes my app better.
If it is a permissions issue, then one solution would be to declare broadFileSystemAccess in your app's manifest.
https://learn.microsoft.com/en-us/windows/uwp/files/file-access-permissions
I find it odd that you don't have write access to a file you create.
Try putting MoveAndReplaceAsync() in a using statement, and opening the SQLite connection outside of it.
Update:
I have tested with broadFileSystemAccess capbility, and it doesn't work and still report the exception "cannot open database file". Therefore, it isn't feasible to use broadFileSystemAccess capbility.
If you want to use Sqlite in uwp, there are only two location can be accessed. ApplicationData and Application install directory, the difference is that ApplicationInstallation can only be read, and ApplicationData can be read and written. So it reported the exception when you connnect the file located in another location.
My meaning is that you could store the database file anywhere, but when you operate this database file, you need to move this file to the location that can access.(ApplicationData,Application install directory). OtherWise, you can't insert data to the table of database file, even, you can't connect the database file.

Saving byte array to file

I have a byte array and need to save it to a file.
I have tried the below code:
File.WriteAllBytes("form.txt", byteArray);
string filename = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "form.txt");
I have referred https://stackoverflow.com/a/19455387/15265496 for the implementation.
I am looking for the file in Android emulator. Where will the file get saved from first line?
Should I create a form.txt in the application local folder?
Is there any alternative way to do the same?
You can find the appropriate folder using Environment.SpecialFolder.LocalApplicationData
string fileExactLocation = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData), "form.txt");
You can find more information at https://learn.microsoft.com/en-us/xamarin/xamarin-forms/data-cloud/data/files?tabs=windows
You cannot access the file system of an Android emulator instance via explorer or finder.
As per the Microsoft docs, if you want to store a file in Android, you can always use the application's files folder which is accessible through:
var path = Environment.GetFolderPath(Environment.SpecialFolder.Personal);
A file saved to that folder will go to
/data/user/0/com.companyname/files

C# UWP Copy database from installed location to local folder

I have a database on "ms-appx:///Assets/mydbfile.db" . I want to copy it to the local application folder when the application will start the first time. Database Contain a large number of data.
I try with this Code. but it gives me an exception.
StorageFile file = await StorageFile.GetFileFromApplicationUriAsync(
new Uri("ms-appx:///Assets/mydbfile.db"));
await file.CopyAsync(ApplicationData.Current.LocalFolder, "mydbfile.db");
Here Is My Db File
I tried with a text file and your code worked fine.
Do you have the Build Action in the file properties set to Content?
Where are you trying to run your code within your app?

How to use the existing SQLite database in my local to retrieve values in WP 8 emulator?

Object reference error
in below part (it couldn't find my local DB file 1st, in order to copy). Db file is inside my project folder - Assets ; Properties window, have set the Build action to Content.
StorageFile databaseFile = await Package.Current.InstalledLocation.GetFileAsync("people.sqlite");
await databaseFile.CopyAsync(ApplicationData.Current.LocalFolder)
I think you need to use Application.GetResourceStream.
"Returns a resource file from a location in the application package.
The GetResourceStream method enables you to load resource files with Content or Resource set as the Build Action property value."
This is for WP8 but should explain the process.

how to create sqlite database in windows store app located at a specific folder

Need help, I can't seem to access any other .sqlite database if its not located in the apps localfolder. Every tutorial I look at they always use
Path.Combine(Windows.Storage.ApplicationData.Current.LocalFolder.Path, "Example.sqlite");
I tried this:
const string testing = #"C:\Users\***\AppData\Local\Packages\*************\LocalState";
this.DBPath = Path.Combine(testing, "Example.sqlite");
using (var db = new SQLite.SQLiteConnection(this.DBPath))
{
db.CreateTable<Customer>();
}
and it worked. but when I change it to:
const string testing = #"C:\Databases";
It can't open the database even if I copied the database from the local folder of the app.
Any suggestions ? I'm still trying to learn.
You can't access the C: drive for windows store apps. It's part of the store's sandbox. Each app is limited to which files and folders can be viewed. If you have a local database file you need to access, define the file as content in your app and access it using the path "ms-appx:///..."
use file picker to select which folder you want to save the db file.
refer this article:
http://msdn.microsoft.com/en-us/library/windows/apps/hh967755.aspx?cs-save-lang=1&cs-lang=csharp#code-snippet-1

Categories

Resources