分享
 
 
 

实战COM(07)----COM+的特性之建立者字符串

王朝vc·作者佚名  2006-01-08
窄屏简体版  字體: |||超大  

本文欢迎转载,唯请注明出处及作者 blackcolor@263.net

---------------------------------------------------

实战COM(07)----COM+的特性之建立者字符串

本文以上一节的例子为基础介绍在COM+中如何使用“建立者字符串”。所谓建立者字符串,有些

书将其命名为“构造字符串”,实际上是在实例化COM+组件时,由COM+环境传递给COM+组件的一个字

符串,一般可用于设置连接数据库的DSN。

一、打开COM工程Step04

1)给接口ISimple04增加一个函数

HRESULT GetConstructString(BSTR *bString)

2)修改Simple04.h文件:

// Simple04.h : Declaration of the CSimple04

#include <comsvcs.h> // 头文件来自于SDK--新

#include <atldbcli.h> // 数据库操作

#ifndef __SIMPLE04_H_

#define __SIMPLE04_H_

#include "resource.h" // main symbols

// 定义一个新类

class CAuthors

{

public:

// 数据--宽度来源于表Authors

CHAR m_szAu_Id[11];

CHAR m_szAu_lName[40];

CHAR m_szAu_fName[20];

// 输出绑定

BEGIN_COLUMN_MAP(CAuthors)

COLUMN_ENTRY(1, m_szAu_Id)

COLUMN_ENTRY(2, m_szAu_lName)

COLUMN_ENTRY(3, m_szAu_fName)

END_COLUMN_MAP()

// 参数绑定

BEGIN_PARAM_MAP(CAuthors)

COLUMN_ENTRY(1, m_szAu_lName)

END_PARAM_MAP()

};

/////////////////////////////////////////////////////////////////////////////

// CSimple04

class ATL_NO_VTABLE CSimple04 :

public CComObjectRootEx<CComSingleThreadModel>,

public CComCoClass<CSimple04, &CLSID_Simple04>,

public IObjectConstruct, // 新

public IDispatchImpl<ISimple04, &IID_ISimple04, &LIBID_STEP04Lib>

{

public:

CSimple04()

{

strcpy(m_szConstruct, "In CSimple04"); // 新

m_hr = E_FAIL; // 初始化

}

DECLARE_REGISTRY_RESOURCEID(IDR_SIMPLE04)

DECLARE_PROTECT_FINAL_CONSTRUCT()

BEGIN_COM_MAP(CSimple04)

COM_INTERFACE_ENTRY(ISimple04)

COM_INTERFACE_ENTRY(IDispatch)

COM_INTERFACE_ENTRY(IObjectConstruct) // 新

END_COM_MAP()

// 加入变量

public:

CDataSource m_Connection;

CSession m_session;

CCommand<CAccessor<CAuthors> > m_Authors;

HRESULT m_hr;

char m_szConstruct[30]; // 可以根据需要修改大小--新

// ISimple04

public:

STDMETHOD(DisConnect)(void);

STDMETHOD(MoveNext)(void);

STDMETHOD(GetAu_fname)(/*[out, retval]*/BSTR * bAu_fname);

STDMETHOD(GetAu_lname)(/*[out, retval]*/BSTR * bAu_lname);

STDMETHOD(GetAu_id)(/*[out, retval]*/BSTR * bAu_id);

STDMETHOD(ConnectToSQL)(void);

STDMETHOD(GetConstructString)(/*[out, retval]*/BSTR * bString); // 新

// IObjectConstruct

public:

STDMETHODIMP Construct(IDispatch * pUnk); // 新

};

#endif //__SIMPLE04_H_

3)修改Simple04.cpp文件

// Simple04.cpp : Implementation of CSimple04

#include "stdafx.h"

#include "Step04.h"

#include "Simple04.h"

// 加入comutil支持

#include <comutil.h>

#pragma comment( lib, "comsupp.lib" )

#pragma comment( lib, "svcguid.lib" ) // 来自于SDK -- 新

////////////////////////////////////////////////////////////////////////////

// CSimple04

// 连接到服务SQL器,并取回Authors数据

STDMETHODIMP CSimple04::ConnectToSQL()

{ // 如果已经建立了连接,先关闭

if(SUCCEEDED(m_hr))

{

m_session.Close();

m_Connection.Close();

// 关闭连接

m_hr = E_FAIL;

}

// 打开数据库

CDBPropSet dbinit(DBPROPSET_DBINIT);

dbinit.AddProperty(DBPROP_INIT_DATASOURCE, OLESTR("GP2000")); // 服务器名

dbinit.AddProperty(DBPROP_AUTH_USERID, OLESTR("sa")); // 用户名

dbinit.AddProperty(DBPROP_AUTH_PASSWORD, OLESTR("123")); // 密码

dbinit.AddProperty(DBPROP_AUTH_PERSIST_SENSITIVE_AUTHINFO, false);

dbinit.AddProperty(DBPROP_INIT_CATALOG, OLESTR("pubs")); // 数据库名

dbinit.AddProperty(DBPROP_INIT_LCID, (long)2052);

dbinit.AddProperty(DBPROP_INIT_PROMPT, (short)4);

m_hr = m_Connection.Open(_T("SQLOLEDB.1"), &dbinit);

if (FAILED(m_hr)) return m_hr;

m_hr = m_session.Open(m_Connection);

if (FAILED(m_hr))

{

m_Connection.Close();

return m_hr;

}

// 设置查询条件

strcpy(m_Authors.m_szAu_lName, "%h%"); // au_lname中包含"h"的作者

m_Authors.Open(m_session,

"select au_id, au_lname, au_fname from authors where au_lname like ?");

return S_OK;

}

// 取结果集

STDMETHODIMP CSimple04::MoveNext()

{

if(SUCCEEDED(m_hr))

{

m_hr=m_Authors.MoveNext();

}

else

{ // 关闭连接

DisConnect();

}

return m_hr;

}

// 取数据

STDMETHODIMP CSimple04::GetAu_id(BSTR *bAu_id)

{

if(SUCCEEDED(m_hr))

{

*bAu_id = _com_util::ConvertStringToBSTR(m_Authors.m_szAu_Id);

}

return S_OK;

}

STDMETHODIMP CSimple04::GetAu_lname(BSTR *bAu_lname)

{

if(SUCCEEDED(m_hr))

{

*bAu_lname = _com_util::ConvertStringToBSTR(m_Authors.m_szAu_lName);

}

return S_OK;

}

STDMETHODIMP CSimple04::GetAu_fname(BSTR *bAu_fname)

{

if(SUCCEEDED(m_hr))

{

*bAu_fname = _com_util::ConvertStringToBSTR(m_Authors.m_szAu_fName);

}

return S_OK;

}

STDMETHODIMP CSimple04::DisConnect()

{

if(SUCCEEDED(m_hr))

{

m_session.Close();

m_Connection.Close();

// 关闭连接

m_hr = E_FAIL;

}

return S_OK;

}

// 取构造字符串--新

STDMETHODIMP CSimple04::Construct(IDispatch * pUnk)

{

if (!pUnk) return E_UNEXPECTED;

IObjectConstructString * pString=NULL;

HRESULT hr = E_FAIL;

hr=pUnk->QueryInterface(IID_IObjectConstructString, (void **)&pString);

if (FAILED(hr)) return hr;

if(pString)

{

BSTR bStr;

pString->get_ConstructString(&bStr);

char *pszString;

pszString = _com_util::ConvertBSTRToString(bStr);

strcpy(m_szConstruct, pszString);

// 释放内存

delete pszString;

SysFreeString(bStr);

pString->Release();

}

else

strcpy(m_szConstruct, "Error!");

return S_OK;

}

// 取构造字符串--新

STDMETHODIMP CSimple04::GetConstructString(BSTR *bString)

{

*bString = _com_util::ConvertStringToBSTR(m_szConstruct);

return S_OK;

}

4)编译连接Step04工程,并将其配置成COM+组件Step04,请参考“实战COM(05)----创建一个COM+应用”

二、建立客户端

1)客户端文件如下:

// Client.cpp 文件 -- 取构造字符串

#include <windows.h>

#include <stdio.h>

#include <winerror.h>

// 加入comutil支持

#include <comutil.h>

#pragma comment( lib, "comsupp.lib" )

// 包含com的定义文件,以下两个文件从step04中拷贝出来

#include "..\step04\step04.h"

#include "..\step04\step04_i.c"

void main()

{

ISimple04 * pISimple04=NULL; // 我们定义的接口

BSTR bString;

// 初始化

HRESULT hr = CoInitialize(NULL);

if(FAILED(hr))

{

printf("Coinitialize failed! hr=0x%x", hr);

return ;

}

// 创建COM对象

hr = CoCreateInstance(CLSID_Simple04, NULL, CLSCTX_ALL,

IID_ISimple04, (void **)&pISimple04);

if(FAILED(hr))

{

printf("create com failed! hr=0x%x", hr);

CoUninitialize();

return ;

}

// 取字符串 bString

hr = pISimple04->GetConstructString(&bString);

if(FAILED(hr))

{

printf("pISimple04->GetConstructString() failed! hr=0x%x", hr);

pISimple04->Release();

CoUninitialize();

return ;

}

char *pszConstruct;

pszConstruct = _com_util::ConvertBSTRToString(bString);

printf("The Construct is %s\n", pszConstruct);

// 释放分配的内存

SysFreeString(bString);

delete pszConstruct;

pISimple04->Release();

CoUninitialize();

return ;

}

三、配置组件Step04

1)打开“组件服务”,展开刚才建立的组件“Step04”,如下图:

2)右击图中的COM对象“Step04.Simple04.1”,从菜单中选择“属性”

3)单击窗口“Step04.Simple04.1 属性”中的“激活”标签,选中“启用对象结构”,在下面的

编辑框中输入“My String”,然后确定,如下图

四、运行

1)从服务器导出该组件的客户端,并安装到WINDOWS 98上

2)在该98上运行上面的客户端client.exe,应该出现下面的提示:

The Construct is My String

五、说明

1)上面文件中,凡注明“新”,说明是本次修改的部分

2)如果你是在同一台98上编译Step04的COM对象,可能需要先注销Step04.dll,再安装导出的客户端,

否则运行结果可能会出现:“The Construct is In CSimple04”

3)由于接口“IObjectConstruct”是COM+新增的内容,而VC6没有上面所提到的头文件与库文件,你可能

需要安装一个Platform SDK,如果你没有SDK,请用下列文件替换,替换时删除原来文件中的

#include <comsvcs.h>和#pragma comment( lib, "svcguid.lib" )两句

// my_construct.h 用于替换SDK的文件,by blackcolor. 2001.08

#ifndef __MY_CONSTRUCT_H_

#define __MY_CONSTRUCT_H_

const IID IID_IObjectConstructString =

{0x41C4F8B2,0x7439,0x11D2,{0x98,0xCB, 0x00,0xC0,0x4F,0x8E,0xE1,0xC4}};

MIDL_INTERFACE("41C4F8B3-7439-11D2-98CB-00C04F8EE1C4")

IObjectConstruct : public IUnknown

{

public:

virtual HRESULT STDMETHODCALLTYPE Construct(

/* [in] */ IDispatch __RPC_FAR *pCtorObj) = 0;

};

MIDL_INTERFACE("41C4F8B2-7439-11D2-98CB-00C04F8EE1C4")

IObjectConstructString : public IDispatch

{

public:

virtual /* [helpstring][id][propget] */ HRESULT STDMETHODCALLTYPE get_ConstructString(

/* [retval][out] */ BSTR __RPC_FAR *pVal) = 0;

};

#endif //__MY_CONSTRUCT_H_

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有