On this page:
An object adapter does not automatically know when you create a servant locator. Instead, you must explicitly register a servant locator with the object adapter:
{zcode:slice} module Ice { local interface ObjectAdapter { // ... void addServantLocator(ServantLocator locator, string category); ServantLocator removeServantLocator(string category); ServantLocator findServantLocator(string category); // ... }; }; {zcode} |
As you can see, the object adapter allows you to add, remove, and find servant locators. Note that, when you register a servant locator, you must provide an argument for the category
parameter. The value of the category
parameter controls which object identities the servant locator is responsible for: only object identities with a matching category
member trigger a corresponding call to locate
. An incoming request for which no explicit entry exists in the active servant map (ASM) and with a category for which no servant locator is registered returns an ObjectNotExistException
to the client.
addServantLocator
has the following semantics:
addServantLocator
for the same category more than once raise an AlreadyRegisteredException
.locate
can find out which category the incoming request is for by examining the object identity member of the Current
object that is passed to locate
.locate
on the default servant locator.removeServantLocator
removes and returns the servant locator for a specific category (including the empty category) with the following semantics:
NotRegisteredException
.removeServantLocator
returns immediately without waiting for the completion of any pending requests on that servant locator; such requests still complete normally by calling finished
on the servant locator.deactivate
on that servant locator, as deactivate
is only called when a registered servant locator's object adapter is destroyed.findServantLocator
allows you to retrieve the servant locator for a specific category (including the empty category). If no match is found, the operation returns null.
The preceding rules may seem complicated, so here is a summary of the actions taken by the Ice run time to locate a servant for an incoming request.
Every incoming request implicitly identifies a specific object adapter for the request (because the request arrives at a specific transport endpoint and, therefore, identifies a particular object adapter). The incoming request carries an object identity that must be mapped to a servant. To locate a servant, the Ice run time goes through the following steps, in the order shown:
locate
on the servant locator and, if locate
returns a servant, dispatch the request to that servant, followed by a call to finished
; otherwise, if the call to locate
returns null, raise ObjectNotExistException
or FacetNotExistException
in the client.ObjectNotExistException
or FacetNotExistException
in the client. (ObjectNotExistException
is raised if the ASM does not contain a servant with the given identity at all, FacetNotExistException
is raised if the ASM contains a servant with a matching identity, but a non-matching facet.)It is important to keep these call dispatch semantics in mind because they enable a number of powerful implementation techniques. Each technique allows you to streamline your server implementation and to precisely control the trade-off between performance, memory consumption, and scalability. To illustrate the possibilities, we will outline a number of the most common implementation techniques.