本文主题是 制作一个远程printer系统
1. 设计slice文件
1.1 因安装了Ice Visual Studio Add-In,做如下处理:
打开工程的ICE配置,enable,输出路径 ./..
创建Printer.ice文件
加入到工程中。
修订Printer内容为:
///
module Demo{
interface Printer{
void PrintString(string s);
};
};
///
保存即可生成Printer.h和Printer.cpp
Printer.h和Printer.cpp 文件在客户和服务器端都需要编译和链接
1.2 若没有安装add-in,则执行如下命令即可
slice2cpp Printer.ice
slice2cpp Printer.ice --impl 命令会附加的生成服务器用的实现代码printer servant框架skeleton,(PrinterI.h和PrinterI.cpp)。
2. 服务端编写
2.1 实现PrinterI.cpp(自动生成的)中的接口
/
void
Demo::PrinterI::PrintString(const ::std::string& s,
const Ice::Current& current)
{
std::cout<<"Server say:"<<s<<"/n";
}
/
2.2 编写服务器端的主程序 PrintServer.CPP文件
/
#include "PrinterI.h"
#include <Ice/Ice.h> //不加报告initialize不是Ice成员函数的错误
#include <ostream>
using namespace std;
int main(int argc,char*argv[])
{
int status = 0;
Ice::CommunicatorPtr ic;
try
{
ic = Ice::initialize(argc, argv);
Ice::ObjectAdapterPtr adapter = ic->createObjectAdapterWithEndpoints(
"SimplePrinterAdapter", "default -p 10000");
Ice::ObjectPtr object = new Demo::PrinterI;
adapter->add(object,ic->stringToIdentity("SimplePrinter"));
adapter->activate();
ic->waitForShutdown();
}
catch(const Ice::Exception& e)
{
cerr << e << endl;
status = 1;
}
catch(const char* msg)
{
cerr << msg << endl;
status = 1;
}
if(ic)
{
try
{
ic->destroy();
}
catch(const Ice::Exception& e)
{
cerr << e << endl;
status = 1;
}
}
return status;
}
/
2.3 说明
Every Ice source file starts with an include directive for Ice.h, which
contains the definitions for the Ice run time.
step 1:首先出场ICE运行环境,Ice::initialize(argc, argv)
step 2:创建对象适配器SimplePrinterAdapter,并监听在10000端口接受客户端请求,并派发请求到指定的对象Servant。
step 3:创建N个servant,(Ice::ObjectPtr object = new Demo::PrinterI)并注册到建对象适配器SimplePrinterAdapter中adapter->add(object,ic->stringToIdentity("SimplePrinter"));
step 4:激活建对象适配器SimplePrinterAdapter, adapter->activate();开始工作
step 5:等待服务终止了,就释放资源ic->waitForShutdown();
2.4 linux 上的编译方法
$ c++ -I. -I$ICE_HOME/include -c Printer.cpp PrinterServer.cpp
$ c++ -o server Printer.o PrinterServer.o /
-L$ICE_HOME/lib -lIce -lIceUtil
3. 客户端编写
3.1 工程增加Printer.h 和Printer.cpp文件
3.2 编写PrinterClint.cpp
/
#include "Printer.h"
#include <Ice/Ice.h>
#include <string>
using namespace std;
int main(int argc,char* argv[])
{
int status = 0;
Ice::CommunicatorPtr ic;
try
{
ic = Ice::initialize(argc,argv);
// Ice::ObjectPrx APrx = ic->stringToProxy("SimplePrinter"); //运行出错,找不到ice运行环境
Ice::ObjectPrx APrx = ic->stringToProxy("SimplePrinter:default -p 10000");
if (APrx == NULL)
return -1;
Demo::PrinterPrx APrintPrx = Demo::PrinterPrx::checkedCast(APrx);
if (APrintPrx == NULL)
return -1;
APrintPrx->PrintString("hello, world!");
}
catch(const Ice::Exception& ex)
{
cerr << ex << endl;
status = 1;
}
catch(const char* msg)
{
cerr << msg << endl;
status = 1;
}
if(ic)
{
try
{
ic->destroy();
}
catch (const Ice::Exception& ex)
{
cerr << ex << endl;
status = 1;
}
return status;
}
}
/
3.3 说明
step 1. initialize the Ice run time by calling Ice::initialize.
step 2. obtain a proxy for the remote printer. ic->stringToProxy("SimplePrinter:default -p 10000"); 格式为 对象名称:对象适配器信息
step 3. down-cast 对象,将基类指针变为子类指针Demo::PrinterPrx APrintPrx = Demo::PrinterPrx::checkedCast(APrx);
step 4. 用对象代理做实事,远程调用
step 5. 释放资源 ic->destroy();
3.4 linux上编译
$ c++ -I. -I$ICE_HOME/include -c Printer.cpp PrinterClient.cpp
$ c++ -o client Printer.o PrinterClient.o -L$ICE_HOME/lib -lIce -lIceUtil
4. 运行测试
打开命令提示符
设置path路径 set path=%path%;C:/Ice-3.4.1/bin
打开子命令提示符号 cmd /c start
分别运行 PrintServer 和PrinterClint
5. AMI支持
ICE 支持AMI方式,即为每个接口Func,自动增加begin_Func() 和 end_Func()两个接口
Ice::AsyncResultPtr r = APrintPrx->begin_PrintString("hello,world"); // 不阻塞
APrintPrx->end_PrintString(r); //因为PrintString没有返回值 //阻塞