我最近在用IntraWeb开发一个项目,开始是使用 EXE 方式开发调试,由于使用ADO连接 MS SQL-Server,因此参考了网上普遍认为的解决方案将 ServerController 的 ComInitialization 属性设置为 ciMultiThreaded。今天我将部分完成的程序转化为 Dll 方式,打算放在IIS中看看效果,也是参照了网上的方案,将工程文件修改为DLL 模式(由于6.0.22的结构与5.X的结构不同,我手头的资料都是介绍的5.X的转换方法),编译通过后,放在我的本机IIS的虚拟目录中(已设置允许使用ISAPI)。在IE中输入地址后,满心期待着出现已经看过很多次的界面,结果,没有,出现错误提示“服务器内部错误”。我靠,这是怎么回事,是不是我转换的问题啊,仔细查看了半天,眼珠子都快瞪到显示器里了,最后的结论是:没有任何问题。虽然认为没有道理,但我还是重新新建了一个ISAPI工程,然后将原工程中的单元全部加进来,编译后放入IIS,打开IE,输入地址,故障依旧,我靠!!!我开始怀疑可能是数据库连接的问题,开始以为是无法连接数据库,于是新建了一个新程序,做了一个简单的数据显示小程序,结果数据显示正常。我靠,数据库连接没问题啊。仔细想~~~,突然闪过一丝念头,刚才这个测试程序我好像没设置 ComInitialization 啊,怎么可以连的,立刻,改成 ciMultiThreaded 再试,哈,故障重现了,因为 ComInitialization 默认是 ciNone,这在 EXE 模式下是无法使用 ADO 的,在 DLL 模式下居然可以,又改成 ciNormal 再试,居然也没有问题。连忙把我的项目中的 ComInitialization 设置为 ciNormal,重新编译放入IIS,打开IE,输入地址,哈哈,我可爱的界面终于出来了~~~ :)至此,得出结论:
1、EXE 模式下使用 ADO,ServerController 的 ComInitialization 属性应设置为 ciMultiThreaded 或 ciNormal。 2、DLL 模式下使用 ADO,ServerController 的 ComInitialization 属性应设置为 ciNormal 或 ciNone。 3、综合以上两点,ServerController 的 ComInitialization 属性建议设置为 ciNormal,两全其美,呵呵:)但是,对于 ComInitialization 属性的这三个值我并没有很透彻的理解,他们究竟是什么含义,有什么区别,在 EXE 和 DLL 两种模式下为什么会出现上述的现象,不知有没有高人来解释一下呢!我使用的开发环境为:Delphi 7 + IntraWeb 6.0.22 + Windows 2003 Server + IIS 6.0
1、EXE 模式下使用 ADO,ServerController 的 ComInitialization 属性应设置为 ciMultiThreaded 或 ciNormal。 2、DLL 模式下使用 ADO,ServerController 的 ComInitialization 属性应设置为 ciNormal 或 ciNone。 3、综合以上两点,ServerController 的 ComInitialization 属性建议设置为 ciNormal,两全其美,呵呵:)但是,对于 ComInitialization 属性的这三个值我并没有很透彻的理解,他们究竟是什么含义,有什么区别,在 EXE 和 DLL 两种模式下为什么会出现上述的现象,不知有没有高人来解释一下呢!我使用的开发环境为:Delphi 7 + IntraWeb 6.0.22 + Windows 2003 Server + IIS 6.0
只是线程中使用COM的问题,关于几种线程模式的区别,你可以在网上找到具体细致的文档.建议你先不要去改缺省的线程模式.
而是使用该用的
CoInitialize(nil);//或者 CoInitializeEx(...);
...(这儿你调用COM的代码)
CoUnInitialize;
exe状态下设的就是ciMultiThreaded,后转为dll老提示interface not supported,我试试
,我用的版本是intraweb7.0.9
但事实上跟是不是EXE和DLL没什么关系.确切说,区别在主线程与非主线程..
你使用EXE测试的时候,调用ADO的线程是用的主线程.
你使用DLL的时候,DLL里面调用ADO的线程是非主线程.你可以做这两个测试验证.
1,做一个EXE型的COM组件(自动化对象,或者远程数据模块)都行..在远程方法里面
调用ADO.
2,做一个DLL,实现一个调用ADO的组件, EXE程序主线程里面调用它..
不过我这儿没有装D7,它一些具体实现的东西现在没分析.不过有几点可以补充一下,
在IIS在处理请求的时候,你可以在进程观察器里面看看它有几个线程产生.
IIS调用你的DLL时候,不是直接调用,而通过DLLHOST.EXE调用(这样可以做到调到者与
你的DLL不在一个进程,你的DLL崩溃不会造成IIS进程崩溃)