"Cannot find entry point sqlite3_open_v2 in DLL sqlite3" when using System.Data.Sqlite - sqlite

I am having problems connecting to a Sqlite database through System.Data.Sqlite. I was trying to use FluentNhibernate but that didn't work, so I went back to basics but got the same error: Cannot find entry point sqlite3_open_v2 in DLL sqlite3.
This is my (fairly simple I believe) code:
using (SQLiteConnection connection = new SQLiteConnection("Data Source=Stripper.s3db;Initial Catalog=main;"))
{
using (SQLiteCommand cmd = new SQLiteCommand("select * from album", connection))
{
cmd.Connection.Open();
object t = cmd.ExecuteScalar();
cmd.Connection.Close();
}
}
I have a reference to System.Data.SQLite so everything seems fine to me. The few explanations (you can barely call them tutorials) on the internet haven't helped me out.

It may be the version of Sqlite3 you are working against. The V2 methods are relatively new - introduced in v3.5

Another possible explanation is that you're using a 32 bit version of the provider in a 64 bit application.

I just downloaded v1.0.60.0 from the System.Data.Sqlite website (sqlite.phxsoftware.com/) which leads to http://sourceforge.net/project/showfiles.php?group_id=132486. As you can see there isn't much choice, so I can't think I'm doing anything wrong there. If I am not mistaken, Sqlite3 is included in System.Data.Sqlite so one would expect it to be the good version.
I am definitely working with the 32bit version on a 32bit application.
I have downloaded the installer and will try with that (I was using the binaries).

Related

Unable to open SQLite database file from local data store of UWP app

I'm using this section of this official MSDN tutorial: Use a SQLite database in a UWP app but I'm getting the following error:
REMARK: There are many online posts related (or similar) to this issue but none seems to have a solution. Most of these posts are a few years old so I thought this issue would have been resolved by now. Moreover, the above mentioned tutorial is using .NET Standard Class library project, as well. And the online posts regarding the issue do not have .NET Standard involved. So, I was wondering if the issue is caused by the use of .NET Standard library. Regardless, a solution will be greatly appreciated.
SQLite Error 14: 'unable to open database file'
Error occurs at line db.Open() of this code:
public static void InitializeDatabase()
{
using (SqliteConnection db =
new SqliteConnection("Filename=sqliteSample.db"))
{
db.Open();
String tableCommand = "CREATE TABLE IF NOT " +
"EXISTS MyTable (Primary_Key INTEGER PRIMARY KEY, " +
"Text_Entry NVARCHAR(2048) NULL)";
SqliteCommand createTable = new SqliteCommand(tableCommand, db);
createTable.ExecuteReader();
}
}
NOTES:
The line just below the above code reads: This code creates the SQLite database and stores it in the application's local data store. That means the app should have access to that local data store.
I'm using latest version 16.3.5 of VS2019 on Windows 10. The target version on the project is selected as Windows 10 1903 and min version as Windows 10 1903
UPDATE
This similar official 3 years old sample works fine. So, the problem seems to be related to newer versions of .NET Core. But I need to use latest version of .NET Core for other features my app is using that are not available in the older versions.
I also tried this similar old tutorial, but it did not on new version of .NET Core work either - giving exact same error.
The old problem reported in 2016 here to Microsoft seems to have resurfaced again with the new version of .NET Core.
This is a misunderstanding, SqliteConnection db = new SqliteConnection("Filename=sqliteSample.db") can not create a Sqlite file, but access the existing Sqlite database file through the path.
So you need to create a valid sqliteSample.db file and place it in the root directory of the UWP project. Select the content in the Properties -> Build operation to ensure it will be loaded into the application directory.
Update
Please create the sqliteSample.db file in LocalFolder first.
await ApplicationData.Current.LocalFolder.CreateFileAsync("sqliteSample.db", CreationCollisionOption.OpenIfExists);
Then use the path to access the database file
string path = Path.Combine(ApplicationData.Current.LocalFolder.Path, "sqliteSample.db");
using (SqliteConnection db =
new SqliteConnection($"Filename={path}"))
{
// ...
}
Best regards.

SQLite no longer seems to work on xamarin android

We have a Xamarin.Forms project that needed to use the sqlite local db to store date. EF Core's sqlite library was used to set this up and by different developers from different PCs (vs 2019). Initially, it was used with the Database.EnsureCreated() function and later with ef core's migrations. All went smooth for more than a month.
Last week all of a sudden the android app wouldn't start on any one's PC due to some error with sqlite. It showed the following error:
Fatal signal 11 (SIGSEGV), code 1 (SEGV_MAPERR)
I spent a while trying all kinds of fixes and rollbacks thinking it was an issue with the code. This included the following:
Deleted obj and bin folders, cleaned and rebuilt for all below steps.
Downgraded the version of ef to 2.2.3 (the version we started with)
Rolled back to git commits up to a week back
Upgraded the versions of dependencies of ef core
Removed the past few migrations
Downgraded xamarin forms to 3.6.x
After trying the above and several other fixes, finally upgrading the versions of java and android SDK worked last Friday (on all PCs). Once this fix worked everything went smooth that day. On Tuesday once again the issue was back (no library updates or code changes). A deeper look at EF Cores logging shows that it crashes the moment it attempts to connect to a db.
The issue can be replicated on the android devices but not the emulators. I am not sure if there is some new permission in android we need to request for.
I finally created a new xamarin forms project with sqlite setup. I used the pcl library and ef core. I still found the same error.
Here is the git hub that replicates the issue https://github.com/neville-nazerane/xamarin-site
Update
Just something i noticed. eariler my database file was named "main.db". Now no matter what i change this file name to or no matter what variables i change. it always shows database name as "main" in logs. Not sure if changing the db name would fix the issue. However, never found a way to change this db name. I tried different connection strings, it just said "database" and "db" were unknown keys
Update
Steps to replicate:
using (var db = new AppDbContext())
{
db.Add(new Person {
Age = 55,
Name = "Neville"
});
db.SaveChanges();
Person[] alldata = db.People.ToArray();
}
The definitions of Person and AppDbContext are quite obvious. So, with the spirit of not making the question too long, I am not posting it here. However, if required I can post them too.
This is a bug with the Xamarin.Forms and Mono.
It was detected since a couple of months ago, it was fixed but then there was some regression (with VS 2019 v16.1).
Even with the latest release (v16.1.2) the bug still happens, so we need to wait for a fix.
Sources:
https://github.com/mono/mono/issues/14170
https://github.com/xamarin/xamarin-android/issues/3112
https://github.com/xamarin/xamarin-android/issues/2920
Due to slight differences of the particular file systems on the native side, I would suggest creating an interface to handle the actual database file handling on the native application level.
So here is how I implemented SQLite using the nuget package SQLite.Net-PCL:
In the shared project, create a new interface, for instance FileHandler.cs
public interface IFileHandler
{
SQLite.SQLiteConnection GetDbConnection();
}
You may want to extend that with more methods to save or retrieve various files, but for now we will just have the GetDbConnection Method to retrieve a working SQLite Connection.
Now in your Android implementation, we add the native implementation to that interface:
Create a new class called FileHandler.cs in your android project:
[assembly: Dependency(typeof(FileHandler))]
namespace YourProjectName.Droid
{
public class FileHandler : IFileHandler
{
public SQLite.SQLiteConnection GetDbConnection()
{
string sqliteFilename = "YourDbName.db3";
string path = Path.Combine(GetPersonalPath(), sqliteFilename);
SQLiteConnectionString connStr = new SQLiteConnectionString(path, true);
SQLiteConnectionWithLock connection = new SQLiteConnectionWithLock(connStr, SQLiteOpenFlags.Create | SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.NoMutex);
return connection;
}
private string GetPersonalPath()
{
return Environment.GetFolderPath(Environment.SpecialFolder.Personal);
}
}
}
Now back again in your shared code you can access that connection with the following code:
using (SQLiteConnection connection = DependencyService.Get<IFileHandler>().GetDbConnection())
{
// Do whatever you want to do with the database connection
}
Alright mate, I don't understand what issue you are facing. It might be an issue with your machine, I'd suggest using another computer/laptop.
I took the exact code that you shared on the Github. I was able to build it on my Mac computer in VS 2019 and installed the application in debug mode on my phone. I was able to add a date successfully, as you can see in the picture, and I placed an Exception Catchpoint and faced no exceptions.
I then proceeded to add another entry with the same details and it errored out with the message that you can see here
I would also suggest using Xamarin Profiler or any other Android logger to see the Stack Trace that you aren't able to see in your application output. It will give you details of the error, that you can share here for us to understand better.

Mono.Data.Sqlite.SqliteConnection requiring a version of 'System' that doesn't make sense

We're having issues with our Sqlite PCL Project.
The issues
1) Anywhere that references Mono.Data.Sqlite.SqliteConnection shows the following error.
Module 'System, Version 4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089' should be referenced.
2) Anything trying to use File.Exists is showing a compiler error
Cannot resolve symbol 'File'
The particulars
We're using .NET Portable Subset 158
C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETPortable\v4.0\Profile\Profile158\
We've included
Mono.Data.Sqlite
C:\Program Files (x86)\Mono-3.2.3\lib\mono\4.5\Mono.Data.Sqlite.dll
System.Data
C:\Program Files (x86)\Mono-3.2.3\lib\mono\4.5\System.Data.dll
I have no idea where to go from here.
Here's a class file containing the issues with SqliteConnection
using System;
using Mono.Data.Sqlite;
namespace OurApplication.AppCore.Data.Sqlite
{
public class DbConnectionProvider : IDbConnectionProvider
{
private readonly string _connectionString;
public DbConnectionProvider(string sqliteDatabasePath, string databaseName)
{
// the sqliteDatabasePath is hard coded in 'Data.Sqlite.DbProvider'
// _sqliteDatabasePath = "{0}.sqlite3";
_connectionString = string.Format("Data Source=" + sqliteDatabasePath, databaseName);
}
public SqliteConnection GetOpenConnection()
{
var connection = new SqliteConnection(_connectionString);
if (connection == null) throw new Exception("Could not create a database connection.");
connection.Open();
return connection;
}
}
}
Gist with more code examples
If this approach isn't feasible, I'm open to other alternatives. I'm looking into Sqlite.Net but the API doesn't really do what I want with regards to a custom DbReader and such.
I'm also interested in Stuart Lodge's MvvmCross Sqlite stuff, but really have no idea how to integrate the platform specific goodness. Honestly, I can't even figure out how to Execute Parameterized Queries.
I think my preference would be to use MvvmCross-SQLite if I can just get it figured out.
For references, this is how our Solution is structured.
OurApplication.App.Droid
OurApplication.AppCore
OurApplication.AppCore.Data.Sqlite (This is the project I'm working in.)
OurApplication.AppCore.Data.SqlServer
For non-portable APIs MvvmCross generally provides interfaces within PCLs with platform specific implementations on each platform.
The pattern used is called "plugins" - but really these are just a simple layer on top of an IoC container. You can see more about this on:
N=31 video in the tutorials - http://mvvmcross.wordpress.com - http://slodge.blogspot.co.uk/2013/06/n31-injection-platform-specific.html
the wiki - https://github.com/MvvmCross/MvvmCross/wiki/MvvmCross-plugins
For File.Exists, MvvmCross provides an IMvxFileStore api - see https://github.com/MvvmCross/MvvmCross/blob/v3/Plugins/Cirrious/File/Cirrious.MvvmCross.Plugins.File/IMvxFileStore.cs
For SQLite MvvmCross has wrapped the SQLite-net library.
The original attempt to do this is in https://github.com/MvvmCross/MvvmCross/tree/v3/Plugins/Cirrious/Sqlite and is based off an early 2012 version of SQLite-net. A video intro to this is available in N-10 in http://mvvmcross.wordpress.com. This project has now been marked as obsolete simply because I don't plan to do any updates to it.
The newer attempt at portable SQLite-net has been put in its own repo to allow more people to contribute to it without confusing the main MvvmCross repo. It is in https://github.com/MvvmCross/MvvmCross-Sqlite - it is based off the latest SQLite-net (late 2013) which was split into interface and non-interface parts by #jarroda. The same N-10 video intro from http://mvvmcross.wordpress.com should work with this project too - just with a different namespace.
This source is currently live and builds fine here in my stable WinRT/WP7/Xamarin VS2012 environment. There will be changes in the coming weeks to address changes forced on MvvmCross by the latest Xamarin and Microsoft PCL changes. I'm afraid no-one can help with "spewing out errors" - that's not a techie term anyone can really help with.
There is at least one other PCL adaption of SQLite-net I've seen recently - but I can't find a link to that at present.

rdsserver.datafactory converttostring failure

I have a classic ASP application written many years ago that I'm trying to fix.
The following lines recently stopped working after w7 sp1 was applied.
set address = Server.CreateObject("ADOR.Recordset")
count = lo_connection.GetRecordset(sql,address,false, error)
Set RDF2 = Server.CreateObject("RDSServer.DataFactory")
Set teststring = RDF2.ConvertToString(address)
It fails on the last line there saying "Microsoft VBScript runtime error: Class doesn't support Automation"
A bit of searching found several articles like this one
http://blogs.technet.com/b/asiasupp/archive/2011/03/14/changes-in-mdac-adodb-com-components-in-windows-7-service-pack-1.aspx
that described the problem exactly. Where I am failing is that none of the suggested fixes seems to fix the problem. Any suggestions?
The solutions described in the link are not relevant here, since ASP is not early-bound - it uses OLE Automation. It might be worth re-registering the component which creates RDSServer.DataFactory objects (which is C:\Program Files\Common Files\system\msadc\msadcf.dll on my machines).
I looked up this object, and I found this Microsoft web page:
http://msdn.microsoft.com/en-us/library/windows/desktop/ms681447(v=vs.85).aspx
"This feature will be removed in a future version of Windows. Avoid using this feature in new development work, and plan to modify applications that currently use this feature. Applications that use RDS should migrate to WCF Data Service."
Doesn't sound too good.

EF 4.1 Code First Initialization - Alternative

I am building a web application using the entity framework and the code first approach and I really like it so far except one thing. The initialization process and seeding data is crap.
I have set it up as recommended with ASP.NET MVC with the setinitialiser being called in app start and a custom initialization class to add data but it always seems to fail silently and never work. (The database creation works just the data init fails)
Can anyone provide recommended paractice for this or a way to run an sql script from a file.
The given method for adding data, especially for a demo site seems cumbersome and I would prefer the ability to just run a database script directly from a file that is run once as part of an install process rather than depending on a process that fails without any indication that something has gone wrong.
EDIT
I have noticed it throwing exceptions ( idiotic datetime -> datetime2 conversion errors that should be handled by the entity framework.)
But part of the problem may be that my version of express 2010 is not breaking on errors it seems to be very buggy when debugging.
But the issue still stands. I find it a cumbersome and buggy way of essentially running sql scripts on the database. And don't want to end up with a huge set of methods and classes just to setup a demo site when someone installs my web application in IIS.
If you want to run SQL scripts from your initializer I would recommend adding
using Microsoft.SqlServer.Management.Smo;
using Microsoft.SqlServer.Management.Common;
string scriptDirectory = HttpContext.Current.Server.MapPath("~/SqlScripts");
string sqlConnectionString = context.Database.Connection.ConnectionString;
DirectoryInfo di = new DirectoryInfo(scriptDirectory);
FileInfo[] rgFiles = di.GetFiles("*.sql");
foreach (FileInfo fi in rgFiles)
{
FileInfo fileInfo = new FileInfo(fi.FullName);
using (TextReader reader = new StreamReader(fi.FullName))
{
using (SqlConnection connection = new SqlConnection(context.Database.Connection.ConnectionString))
{
Server server = new Server(new ServerConnection(connection));
server.ConnectionContext.ExecuteNonQuery(reader.ReadToEnd());
}
reader.Close();
reader.Dispose();
}
}
The reason for using the SqlServer Management Objects is that you can use "GO" in your scripts. it then becomes incredibly easy to script from SSMS and paste the scripts into your SqlScripts directory.
You can find the SMO Libraries at:
C:\Program Files\Microsoft SQL Server\100\SDK\Assemblies\Microsoft.SqlServer.ConnectionInfo.dll
C:\Program Files\Microsoft SQL Server\100\SDK\Assemblies\Microsoft.SqlServer.Management.Sdk.Sfc.dll
C:\Program Files\Microsoft SQL Server\100\SDK\Assemblies\Microsoft.SqlServer.Smo.dll
and if you need help scripting your data
SP_Generate_Inserts
Until you will show reproducible code snippet where initialization fails without throwing an exception I hardly believe that this happens.
You can always execute any SQL script by falling back to classic ADO.NET with SqlConnection and SqlCommand. Just open the file, load commands into string and execute them with SqlCommand or Database.ExecuteSqlCommand.

Resources