Recipe15.8.Implementing a CORBA Server and Client


Recipe 15.8. Implementing a CORBA Server and Client

Credit: Duncan Grisby

Problem

You need to implement a CORBA server and client to distribute a processing task, such as the all-important network-centralized fortune-cookie distribution.

Solution

CORBA is a solid, rich, mature object-oriented RPC protocol, and several CORBA ORBs offer excellent Python support. This recipe requires multiple files. Here is the interface definition file, fortune.idl, coded in CORBA's own IDL (Interface Definition Language):

module Fortune {     interface CookieServer {         string get_cookie( );     }; };

This code is quite readable even if you've never seen CORBA's IDL before: it defines a module named Fortune, whose only contents is an interface named CookieServer, whose only contents is a function (method) named get_cookie, which takes no arguments and returns a string. This code says nothing at all about the implementation: IDL is a language for defining interfaces.

The server script is a simple Python program:

import sys, os import CORBA, Fortune, Fortune_ _POA FORTUNE_PATH = "/usr/games/fortune" class CookieServer_i(Fortune_ _POA.CookieServer):     def get_cookie(self):         pipe   = os.popen(FORTUNE_PATH)         cookie = pipe.read( )         if pipe.close( ):             # An error occurred with the pipe             cookie = "Oh dear, couldn't get a fortune\n"         return cookie orb = CORBA.ORB_init(sys.argv) poa = orb.resolve_initial_references("RootPOA") servant = CookieServer_i( ) poa.activate_object(servant) print orb.object_to_string(servant._this( )) # see the Discussion session about what this print statement emits poa._get_the_POAManager( ).activate( ) orb.run( )

And here's a demonstration of client code for this server, using a Python interactive command shell:

>>> import CORBA, Fortune >>> orb = CORBA.ORB_init( ) >>> o = orb.string_to_object( ...   "corbaloc::host.example.com/fortune") >>> o = o._narrow(Fortune.CookieServer) >>> print o.get_cookie( )

Discussion

CORBA has a reputation for being hard to use, but it is really very easy, especially with Python. This example shows the complete CORBA implementation of a fortune-cookie server and its client. To run this example, you need a Python-compatible CORBA implementation (i.e., an ORB)or, if you wish, two such ORBs, since you can use two different CORBA implementations, one for the client and one for the server, and let them interoperate with the CORBA IIOP inter-ORB protocol. Several free CORBA implementations, which fully support Python, are available for you to download and install. The Python language support is part of the CORBA standards, so, if a certain ORB supports Python at all, you can code your Python source for it in just the same way as you can code it for any other compliant ORB, be it free or commercial. In this recipe, we use the free ORB known as omniORB. With omniORB, you can use omniORBpy, which lets you develop CORBA applications from Python.

With most ORBs, you must convert the interface definition coded in IDL into Python declarations with an IDL compiler. For example, with omniORBpy:

omniidl -bpython fortune.idl

This creates Python modules named Fortune and Fortune_ _POA, in files Fortune.py and Fortune_POA.py, to be used by clients and servers, respectively.

In the server, we implement the CookieServer CORBA interface by importing Fortune_ _POA and subclassing the CookieServer class that the module exposes. Specifically, in our own subclass, we need to override the get_cookie method (i.e., implement the methods that the interface asserts we're implementing). Then, we start CORBA to get an orb instance, ask the ORB for a POA (Portable Object Adaptor), instantiate our own interface-implementing object, and pass it to the POA instance's activate_object method. Finally, we call the activate method on the POA manager and the run method on the ORB to start our service.

When you run the server, it prints out a long hex string, such as:

IOR:010000001d00000049444c3a466f7274756e652f436f6f6b69655365727665723 a312e300000000001000000000000005c000000010102000d0000003135382e313234 2e36342e330000f90a07000000666f7274756e6500020000000000000008000000010 0000000545441010000001c0000000100000001000100010000000100010509010100 0100000009010100

Printing this string is the purpose of the object_to_string call that our recipe's server performs just before it activates and runs.

You have to pass this string value as the argument of the client's orb.string_to_object( ) call to contact your server. Such long hex strings may not be convenient to communicate to clients. To remedy this, it's easy to make your server support a simple corbaloc URL string, like the one used in the client example, but doing so involves omniORB-specific code that is not necessarily portable to other ORBs. (See the omniORBpy manual for details of corbaloc URL support.)

See Also

You can download omniORBpy, including its documentation, from http://www.omniorb.org/omniORBpy/.



Python Cookbook
Python Cookbook
ISBN: 0596007973
EAN: 2147483647
Year: 2004
Pages: 420

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net