Portable Object Adaptor
Significant news in CORBA
• Objects By Value
• CORBA Components
• CORBA scripting
• Metadata and modeling
• Quality of Service
• Portable Object Adaptor
CORBA Object Adaptors
• a piece of CORBA architecture dispatching
client requests to the
servants
(implementations)
• object adaptors are only on the server side
• key functions are
– they create CORBA object references
– they ensure that target objects are incarnated by servants
– they direct requests to the servants (they connect orb with the servants - locating and marshaling)
remember this term, use this term
remember this term, use this term
remember: object references and servants are two different things
BOA and POA
• BOA was the original CORBA object adaptor
• BOA was under-specified and therefore less
portable between ORBs
• BOA had no servant management
• BOA has been removed from CORBA!
• POA is everything else
– portable
POA abstract model
Client Server
servant
POA
POA ORB
Object Id
logical connection to the target
CORBA object
Object Reference
servant
Three key Entities
[CORBA Object is a programming entity with an identity, an interface and an implementation]
• Servant
– a programming language object implementing requests on
one or more CORBA objects (modifier “native” in IDL)
• Object Id
– a value identifying a particular CORBA object within the scope of its POA
– Ids are hidden from clients, encapsulated by object references
• Object Reference
– a usual reference to a CORBA object
A simplified picture
ORB POA
Manager
POAPOA POA
Servant Servant
Servant Servant
Servant Servant
Servant Servant
Servant
Server Application
How to code Server
import org.omg.CORBA.*;
// Initialize ORB and BOA
ORB orb = ORB.init (args, props); BOA boa = orb.BOA_init(args, props);
// Create a servant and activate it
HelloWorldImpl hw = new HelloWorldImpl();
// Wait for requests
boa.impl_is_ready(null);
with BOA
import org.omg.CORBA.*;
import org.omg.PortableServer.*;
// Initialize ORB and POA
ORB orb = ORB.init (args, props); POA rootPOA = POAHelper.narrow (
orb.resolve_initial_references ("RootPOA"));
// Get a reference to the POA manager
POAManager manager = rootPOA.the_POAManager();
// Create a servant and activate it
HelloWorldImpl hwImpl = new HelloWorldImpl(); HelloWorld hw = hwImpl._this (orb);
// Wait for incoming requests ("run the implementation")
manager.activate();
Server
overview
CORBA.Object CORBA.Object HelloWorld HelloWorld CORBA.<skeleton> CORBA.<skeleton> _HelloWorldImplBase _HelloWorldImplBase HelloWorldImpl get_text() HelloWorldImpl get_text() extends extends implements extendsThe old way - with BOA
HelloWorld Operations HelloWorld Operations PortableServer.Servant PortableServer.Servant HelloWorldPOA HelloWorldPOA HelloWorldImpl get_text() HelloWorldImpl get_text() extends extends implements extends HelloWorld HelloWorld CORBA.Object portable.IDLEntity CORBA.Object portable.IDLEntity extends
The new way - with POA
this is a servant this is an interface of the same type as the object reference
How to connect your implementation
classes with the generated code
_this() or
ORB
Yet another picture
extract POA name from Object Key
POA
find POA
Object Reference (with Object Key)
request from a client
or
Adaptor Activator
call Adaptor Activator if POA not found
create POA
extract Object Id
from Object Key Active Object Map
POA Policies
• there can be more POAs and each of them
can have different features =
policies
• the policies are given to the POA in its
creation time, they are
not changeable
later
• the policies are
not inherited
from parent
POA to its children POA
• the policies are
locally-constrained
objects
policy:
CORBA Object Life Span
• TRANSIENT
– the objects created in the POA cannot outlive this POA
– they are more modest regarding resources
• PERSISTENT
– the objects can outlive the process in which they were first created
– their POA name is stored in the object references
policy:
Object Id Uniqueness
• UNIQUE_ID
– each servant support exactly one Object Id
• MULTIPLE_ID
– a servant may support one or more Object Ids – good, for example, for many database objects
which may all be served by a single servant
(assuming that the state of the objects is kept in the database)
policy:
Id Assignment
• USER_ID
– Object IDs are assigned by the application, not by the POA
– typical for persistent objects (the same ID is used for keeping track where the object state is stored)
• SYSTEM_ID
– Object IDs are assigned by the POA
policy:
Request Processing
• USE_ACTIVE_OBJECT_MAP_ONLY
– an Object Id must be found in the active object map
• USE_DEFAULT_SERVANT
– if an Object Id is not found in the active object map the request is dispatched to the default servant
• USE_SERVANT_MANAGER
– if an Object Id is not found in the active object map the servant manager gets control
enum RequestProcessingPolicyValue {
policy:
ObjectId to Servant Associations
• RETAIN
– the POA will keep active servants in its active object map
– various combinations of this policy and Request Processing policy
• NON_RETAIN
– servants are not retained by the POA
– it is up to the application to keep track about active (existing) servants
policy:
Implicit Activation
• IMPLICIT_ACTIVATION
– the POA will support implicit activation of servants – also requires SYSTEM_ID and RETAIN policies – implicit activation is done (in Java) using a shortcut
method “_this”
• NO_IMPLICIT_ACTIVATION
– the POA will not support implicit activation of servant
– typically used to avoid accidental object creation
policy:
Thread
• ORB_CTRL_MODEL
– servants can be called in parallel from separate threads (created and controlled by the ORB)
– servants must be written as thread-aware
• SINGLE_THREAD_MODEL
– a model which guarantees that all requests for all objects in this POA will be dispatched
sequentially
– but the application still can have more single-threaded POAs running in parallel (in separate threads)
How to create “policies”
• each policy has its own factory:
• an example how to use the policy factory:
• typically, all necessary policy objects are passed
in a
PolicyList
to the POA creation function
• …and then invoke
destroy
on the policy objects
interface POA {
LifespanPolicy create_lifespan_policy ( in LifespanPolicyValue value); };
Policy policy =
ORB
Yet another picture
(now let’s show where different policies apply)
extract POA name from Object Key
POA
find POA
Object Reference (with Object Key)
request from a client
or
Adaptor Activator
call Adaptor Activator if POA not found
create POA
extract Object Id
from Object Key Active Object Map
POA Creation
• each POA is created as a child of another
POA
• all server applications have a “
RootPOA
”
• POAs are created in a tree, in a hierarchy
• each POA has its own namespace for its
Object Ids
code:
POA Creation
interface POA {
POA create_POA (
in string adapter_name, in POAManager manager, in CORBA::PolicyList policies) raises (AdapterAlreadyExists, InvalidPolicy); };
// get a reference to the Root POA
POA rootPOA = POAHelper.narrow (orb.resolve_initial_references ("RootPOA"));
// get a reference to the POA manager
POAManager manager = rootPOA.the_POAManager();
// create an empty PolicyList for child POA
Policy[] policies = new Policy [0];
// create the child POA
Activation: don’t be confuse...
• “Object activation” is not the same as
“Server activation”
– Server activation is about “how to start a separate process on the server side”
• also called: “Implementation repository” issue (see another talk)
Object creation and activation
• POA provides several options for creating
objects and activating them
– an application can create objects without
creating any servants
– a servant can be explicitly or implicitly
registered to incarnate an object - and POA can remember it in its Active Object Map
– an application can supply servant managers
Creation and activation methods
Object create_reference (in CORBA::RepositoryId intf) raises (WrongPolicy);
Object create_reference_with_id (in ObjectId oid, in CORBA::RepositoryId intf) raises (WrongPOlicy);
Object create_reference (in CORBA::RepositoryId intf) raises (WrongPolicy);
Object create_reference_with_id (in ObjectId oid, in CORBA::RepositoryId intf) raises (WrongPOlicy);
Creating CORBA Objects without creating servants
ServantManager get_servant_manager () raises (WrongPolicy);
void set_servant_manager (in ServantManager imgr) raises (WrongPOlicy);
ServantManager get_servant_manager () raises (WrongPolicy);
void set_servant_manager (in ServantManager imgr) raises (WrongPOlicy);
Registration of Servant managers
Servant get_servant ()
raises (NoServant, WrongPolicy); void set_servant (in Servant serv)
raises (WrongPOlicy); Servant get_servant ()
raises (NoServant, WrongPolicy); void set_servant (in Servant serv)
raises (WrongPOlicy);
Registration of Default Servant
ObjectId activate_object (in Servant serv) raises (ServantAlreadyActive, WrongPolicy);
void activate_object_with_id (in ObjectId oid, in Servant serv) raises (ServantAlreadyActive,
ObjectAlreadyActive, WrongPolicy); ObjectId activate_object (in Servant serv)
raises (ServantAlreadyActive, WrongPolicy);
void activate_object_with_id (in ObjectId oid, in Servant serv) raises (ServantAlreadyActive,
ObjectAlreadyActive, WrongPolicy);
Conversions among key entities
Object Reference
Object Id
Servant
ObjectId reference_to_id (in Object ref)
raises (WrongAdapter, WrongPolicy); Object id_to_reference (in ObjectId oid)
raises (ObjectNotActive, WrongPolicy); ObjectId reference_to_id (in Object ref)
raises (WrongAdapter, WrongPolicy); Object id_to_reference (in ObjectId oid)
raises (ObjectNotActive, WrongPolicy);
ObjectId servant_to_id (in Servant serv)
raises (ServantNotActive, WrongPolicy); Servant id_to_servant (in ObjectId oid)
raises (ObjectNotActive, WrongPolicy); ObjectId servant_to_id (in Servant serv)
raises (ServantNotActive, WrongPolicy); Servant id_to_servant (in ObjectId oid)
raises (ObjectNotActive, WrongPolicy);
Servant reference_to_servant (in Object ref)
raises (ObjectNotActive, WrongAdapter, WrongPolicy); Object servant_to_reference (in Servant serv)
raises (ServantNotActive, WrongPolicy); Servant reference_to_servant (in Object ref)
raises (ObjectNotActive, WrongAdapter, WrongPolicy); Object servant_to_reference (in Servant serv)
Servant managers
• Used when an explicit servant registration is
difficult or impossible
– e.g. dealing with too many objects – or finding objects dynamically
• Servant Activator
– Servant incarnate (in ObjectId oid, in POA adapter) – void etherealize (in ObjectId oid, in POA adapter, …)
– the resulting servant retains in the Active Object Map
• Servant Locator
– Servant preinvoke (in ObjectId oid, in POA adapter, in CORBA::Identifier operation, out Cookie the_cookie) – void postinvoke (in ObjectId oid, in POA adapter, in CORBA::Identifier operation, out Cookie the_cookie,…)
Common for both Servant managers
• The
incarnate()and
preinvoke()may raise any system
exception
– e.g. OBJECT_NOT_EXIST if the object corresponding to the Object Id cannot be incarnated
• SeqFactory.get_sequence() normally would raise at once exception
WrongAccession but if the real access to the database is postponed
some other exception must be used
• Both operations may also raise a
ForwardRequest– then the ORB is responsible for delivering the current and subsequent requests to the object denoted in
Default Servant
• a single Servant for many CORBA objects
– typically of the same type
– ideally suited to objects in large databases
• the invoking POA and ObjectId is
accessible using
Current
interface
org.omg.CORBA obj =
orb.resolve_initial_references (”POACurrent")); Current current = CurrentHelper.narrow (obj);
org.omg.CORBA obj =
orb.resolve_initial_references (”POACurrent")); Current current = CurrentHelper.narrow (obj);
How to get Current
interface Current {
POA get_POA();
ObjectID get_object_id(); };
interface Current {
POA get_POA();
ObjectID get_object_id(); };
Object deactivation
• deactivation is breaking object-to-servant
association
• after deactivation the object is not visible
any more
– but the corresponding servant can still be available and may be activated later again
• an administrative tool for controlling the
contents of the Active Object Map
void deactivate_object (in ObjectId oid)
raises (ObjectNotActive, WrongPolicy); void deactivate_object (in ObjectId oid)
Notes on hands-on
• POA/stage1
– plain differences between BOA and POA
• POA/stage2-persistent
– create persistent object reference
• POA/stage3-servantActivator
– create a factory for sequence references, – the servants are created later only when a