我需要在项目中引用哪个SqlServerCe DLL版本以匹配sqlce.wce4.armv4.CAB中的版本? [英] Which SqlServerCe DLL version do I need to reference in my project to match what's in sqlce.wce4.armv4.CAB?

查看:126
本文介绍了我需要在项目中引用哪个SqlServerCe DLL版本以匹配sqlce.wce4.armv4.CAB中的版本?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

故事的其余部分"在下面详细介绍了所有细节,但是为了追逐,我们将其归结为:

SQLCE 2.0(包含在sqlce.wce4.armv4.CAB中)似乎安装在运行我的应用程序的设备上;源项目使用运行时版本为v2.0.50727和版本为3.5.1.0引用SqlServerCe

这是匹配还是不匹配?如果是后者,我需要在项目中引用哪个版本的SqlServerCe.dll?

通俗故事的其余部分

我的Windows CE应用程序尝试打开SQL CE(.SDF)文件时失败;尽管一个潜在的早期问题显然与版本控制相关联(没有双关语)(调用SqlCeEngine.Upgrade()使我越过了它),现在err msg指示密码问题.请参见

但是我在哪里都看不到在表上设置密码的地方-也没有在指定SQLCE版本的地方.

我们有一个设置实用程序,可以将该应用程序以及必要的辅助文件安装在手持设备上.为了弄清楚这两个应用程序(正确的安装应用程序)在版本控制和密码方面到底在做什么,我在两个代码库中搜索了"SDF"和"SQLCE",这就是我发现的*:

设置实用程序中对"SDF"的唯一引用是:

{_T("OpenNETCF.SDF.WCE4.ARMV4.CAB"),_T("OpenNETCF SDF v1.4"),(DWORD)0,true},

在应用程序本身中唯一对"SDF"的引用不会创建一个SqlCe("SDF")数据库.确实存在此类引用的地方,它们会查找已经存在的特定SDF文件,如下所示:

filename = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Personal), "HHSDB.SDF");

然后实例化并升级引擎数据库引擎,并有条件地创建数据库(在我的情况下,该文件存在,因此未调用CreateDatabase()):

engine = new SqlCeEngine(conStr);
engine.Upgrade(conStr); // <= Recommended by ctacke

if (File.Exists(filename))
{
    MessageBox.Show(string.Format("file {0} exists", filename)); // TODO: Comment out or remove
}
else
{
    engine.CreateDatabase(); 
}

设置实用程序中对"SQLCE"的唯一引用是:

0)

//{{NO_DEPENDENCIES}}
// Microsoft Visual C++ generated include file.
// Used by HHSetupCon.rc
//
. . .
#define IDR_NETCF                       103
#define IDR_SQLCLIENT                   104
#define IDR_SQLCEDEV                    105
#define IDR_SQLCE                       106
. . .

1)

IDR_SQLCLIENT           BIN                     "J:\\sql.wce4.armv4.zip"
IDR_SQLCEDEV            BIN                     "J:\\sqlce.dev.wce4.armv4.zip"
IDR_SQLCE               BIN                     "J:\\sqlce.wce4.armv4.zip"

2)

{_T("sqlce.dev.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0 Dev"),IDR_SQLCEDEV,false},
{_T("sqlce.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0"),IDR_SQLCE,false},

在应用程序本身中对"SQLCE"的引用会创建或查询SDF表,例如:

// This creates a table (a *table*, not the database itself)
public static void CreateSettingsTable()
{
    try
    {
        string sqlddl =
            "create table platypus_settings (setting_id int identity (1,1) Primary key,  setting_name nvarchar(40) not null, setting_value nvarchar(63))";
        DBConnection.GetInstance().DBCommand(sqlddl, false);
    }
    catch (SqlCeException sqlcex)
    {
        SSCS.ExceptionHandler(sqlcex, "DBUtils.CreateSettingsTable");
    }
    catch (Exception ex)
    {
        SSCS.ExceptionHandler(ex, "DBUtils.CreateSettingsTable");
    }
}

注意:DBConnection是一个自定义类,其中包含一些SqlCe *成员:

SqlCeConnection objCon = null;
SqlCeEngine engine;
public SqlCeTransaction SqlTrans;

...因此,util和应用程序本身似乎都没有创建SqlCe 数据库(HHSDB.SDF)-应用程序仅找到.SDF文件,然后从中读取/写入它.

看来,当应用程序创建一个表(如上面的CreateSettingsTable()中的表)和类似的活动时,它将使用SqlCe DLL来执行此操作,并且由于ctacke表示该DLL的版本(设备)必须与该项目的源代码相关联的设备相匹配,因此设备上实际上应该是一个,但是由于我在设备上没有看到任何SqlCe DLL,无法验证设备上的版本和项目构建环境是否匹配...

具体来说:设备上没有sqlserverce.dll;是我应该寻找的其他文件吗?缺少此DLL本身不一定不是问题,否则我将无法通过以下代码(我这样做):

engine = new SqlCeEngine(conStr);

项目中引用的System.Data.SqlServerCe DLL是运行时版本"v2.0.50727",版本"3.5.1.0"

安装项目没有这样的引用AFAICT(它是C ++项目).但是,它确实具有以下代码:

{_T("sqlce.dev.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0 Dev"),IDR_SQLCEDEV,false},
{_T("sqlce.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0"),IDR_SQLCE,false},

因此它安装了SQL CE版本2的cab文件...版本2是否与应用程序引用的SqlServerCE DLL中的运行时版本"或版本"相对应?

我认为应该将这些驱动程序扩展/包含SqlCe DLL,但是,正如我所写的那样,运行此安装实用程序后,我在设备上看不到任何驱动程序(似乎工作正常).

因此,总结一下并重申:

SQLCE 2.0(包含在sqlce.wce4.armv4.CAB中)似乎安装在运行我的应用程序的设备上;源项目使用运行时版本为v2.0.50727和版本为3.5.1.0引用SqlServerCe

这是匹配还是不匹配?如果是后者,我需要在项目中引用哪个版本的SqlServerCe.dll?

  • 入境口岸的警察说..."-对不起,我不由自主(或者更不想这样)

更新

这些是设备上的一些文件:

更新2

从表面上看,很明显,基于文件名,这些是版本3.5,我在JetBrains的dotPeek中打开了它们,以试图验证这一点,但结果却落空了-我得到了那些DLL的(不支持)".

尝试在Reflector中进行相同的操作给了我更多信息:'C:\ Bla \ sqlceca35.dll'不是.NET模块."

解决方案

是的,您不匹配.

您有一个数据库文件,该文件在内部指示它是SQL Compact 2.0文件.

您有一个版本为3.5.1的System.Data.SqlServerCe.dll程序集. 运行时版本"表示它是针对CF运行时构建的,因此它是针对2.0运行时构建的-并不意味着它本身就是2.0.这就是混乱的点-您一直命名两个版本,而程序集只有一个版本.

这是我的怀疑,因为您正在呼叫Upgrade(),其中浏览到您知道正确的System.Data.SqlServerCe.dll并添加引用这样.

The "rest of the story" is told below in all its gory details, but to cut to the chase, it comes down to this:

SQLCE 2.0 (contained in sqlce.wce4.armv4.CAB) seems to be installed on the device on which my app runs; the source project references SqlServerCe with a Runtime Version of v2.0.50727 and a Version of 3.5.1.0

Is this a match or a mismatch? If the latter, which version of SqlServerCe.dll do I need to reference in my project?

THE REST OF THE GORY STORY

My Windows CE app is failing when it attempts to open a SQL CE (.SDF) file; altho an underlying earlier problem was apparently connected (no pun intended) with versioning (calling SqlCeEngine.Upgrade() got me past it), the err msg now indicates a password problem. See this

But nowhere do I see where a password is being set on the table - nor where a SQLCE version is being specified.

We have a setup utility that installs this app along with the necessary ancillary files on the handheld device. In trying to figure out what exactly the two apps (the install app the app proper) are doing regarding versioning and password, I searched for "SDF" and "SQLCE" in both code bases, and here is what I found*:

The only reference to "SDF" in the Setup utility is:

{_T("OpenNETCF.SDF.WCE4.ARMV4.CAB"),_T("OpenNETCF SDF v1.4"),(DWORD)0,true},

The only references to "SDF" in the app itself do not create a SqlCe ("SDF") database. Where such references do exist, they look for a specific SDF file that already exists like so:

filename = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Personal), "HHSDB.SDF");

Then the engine database engine is instantiated and upgraded and a database is conditionally created (in my case, the file exists, so CreateDatabase() is not called):

engine = new SqlCeEngine(conStr);
engine.Upgrade(conStr); // <= Recommended by ctacke

if (File.Exists(filename))
{
    MessageBox.Show(string.Format("file {0} exists", filename)); // TODO: Comment out or remove
}
else
{
    engine.CreateDatabase(); 
}

The only references to "SQLCE" in the Setup utility are:

0)

//{{NO_DEPENDENCIES}}
// Microsoft Visual C++ generated include file.
// Used by HHSetupCon.rc
//
. . .
#define IDR_NETCF                       103
#define IDR_SQLCLIENT                   104
#define IDR_SQLCEDEV                    105
#define IDR_SQLCE                       106
. . .

1)

IDR_SQLCLIENT           BIN                     "J:\\sql.wce4.armv4.zip"
IDR_SQLCEDEV            BIN                     "J:\\sqlce.dev.wce4.armv4.zip"
IDR_SQLCE               BIN                     "J:\\sqlce.wce4.armv4.zip"

2)

{_T("sqlce.dev.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0 Dev"),IDR_SQLCEDEV,false},
{_T("sqlce.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0"),IDR_SQLCE,false},

References to "SQLCE" in the app itself create or query SDF tables, such as:

// This creates a table (a *table*, not the database itself)
public static void CreateSettingsTable()
{
    try
    {
        string sqlddl =
            "create table platypus_settings (setting_id int identity (1,1) Primary key,  setting_name nvarchar(40) not null, setting_value nvarchar(63))";
        DBConnection.GetInstance().DBCommand(sqlddl, false);
    }
    catch (SqlCeException sqlcex)
    {
        SSCS.ExceptionHandler(sqlcex, "DBUtils.CreateSettingsTable");
    }
    catch (Exception ex)
    {
        SSCS.ExceptionHandler(ex, "DBUtils.CreateSettingsTable");
    }
}

Note: DBConnection is a custom class that contains, among other things, some SqlCe* members:

SqlCeConnection objCon = null;
SqlCeEngine engine;
public SqlCeTransaction SqlTrans;

...so, neither the util nor the app itself seem to create the SqlCe database (HHSDB.SDF) - the app simply locates the .SDF file and then reads from it/writes to it.

It would seem that when the app creates a table (as in CreateSettingsTable() above) and suchlike activity, it would use a SqlCe DLL to do that, and since ctacke said that the version of that DLL (the one on the device) has to match the one affiliated with the project's source code, there should actually be one on the device, but since I do not see any SqlCe DLL on the device, it's impossible to verify that the versions on the device and the project build environment match...

Specifically: There is no sqlserverce.dll on the device; is it some other file I should be looking for? The lack of this DLL must not be a problem in itself, otherwise I would not get past the following code (which I do):

engine = new SqlCeEngine(conStr);

The System.Data.SqlServerCe DLL referenced in the project is Runtime Version "v2.0.50727", Version "3.5.1.0"

The setup project has no such references, AFAICT (it's a C++ project). However, it does have this code:

{_T("sqlce.dev.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0 Dev"),IDR_SQLCEDEV,false},
{_T("sqlce.wce4.armv4.CAB"),_T("Microsoft SQLCE 2.0"),IDR_SQLCE,false},

So it installs cab files for SQL CE version 2...does version 2 here correspond with "Runtime Version" or "Version" in the app's referenced SqlServerCE DLL?

I would think these cabs are supposed to be expanded/contain the SqlCe DLL[s] but, as I wrote, I don't see any on the device subsequent to running this setup util (which seems to work fine).

So, to sum up and reiterate:

SQLCE 2.0 (contained in sqlce.wce4.armv4.CAB) seems to be installed on the device on which my app runs; the source project references SqlServerCe with a Runtime Version of v2.0.50727 and a Version of 3.5.1.0

Is this a match or a mismatch? If the latter, which version of SqlServerCe.dll do I need to reference in my project?

  • "The po-lice at the port of entry say..." - sorry, couldn't help myself (or didn't want to is more like it)

UPDATE

These are some files on the device:

UPDATE 2

Altho it's superficially obviously, based on the filenames, that these are version 3.5, I opened them in JetBrains' dotPeek in an attempt to verify that, but that fell flat - I get, "(not supported)" for those DLLs.

Attempting the same thing in Reflector gave me a little more info: "'C:\Bla\sqlceca35.dll' is not a .NET module."

解决方案

Yes, you have a mismatch.

You have a database file that internally indicates that it is a SQL Compact 2.0 file.

You have a System.Data.SqlServerCe.dll assembly that is version 3.5.1. The "runtime version" means what CF runtime was it built against, so it was built against the 2.0 runtimes - it doesn't mean that it is 2.0 itself. This was the point of confusion - you kept naming two versions and an assembly has only one version.

This was my suspicion because you're calling Upgrade() which doesn't even exist in SQL Compact 2.0.

If you want to open the original database, in it's original state, and allow it to still be accessible by the original creator (and there has to be code that creates it or it's deployed already-built in a CAB file, there's no implicit way it could happen) then one again I reiterate, you must use the same version of SQL Compact to do so.

In your specific case what this means is that you should do the following:

  1. Change the project reference (this means in Studio, on your PC) to point to a System.Data.SqlServerCe.dll that has an assembly version of 2.0.xxx.
  2. Make sure that the device has the exact same version (2.0.xxx) numbered SQL Compact files on it. This includes System.Data.SqlServerCe.dll as well as all of the sscexx.dll native files. There are about a half dozen.

You do not need to call Upgrade() unless you want to make it a 3.5 database, at which point you can't go back, plus you'll be trying to upgrade every time you run, which I doubt is what you want anyway. That method is generally for utilities or one-time use.

It doesn't matter how many other versions of the assemblies are on your PC, and in fact you can have multiples on the device too. The important thing is that what you have in your project reference, meaning what the app is linked to, is the same DLL that gets loaded by the application on the device when it actually executes.

Generally I do 2 things to make sure this happens:

  1. Put all of the SQL CE stuff right into the app folder on the device, not distributed via CAB but deploy each individual file, to make sure this is what happens.
  2. Reference directly to the file on your PC. Don't use Studio's "magic" method of finding a .NET reference, but browse directly to the System.Data.SqlServerCe.dll you know is right and add the reference that way.

这篇关于我需要在项目中引用哪个SqlServerCe DLL版本以匹配sqlce.wce4.armv4.CAB中的版本?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆