Galaxy Communicator Documentation:

Provider Names and Provider Selection

License / Documentation home / Help and feedback

The Galaxy Communicator infrastructure has evolved considerably in the way it handles references to servers. The Hub, for instance, makes the distinction between service types, which is a set of operations the Hub can perform, and service providers, which are the individual Communicator-compliant servers which implement these operations.

In version 4.0, we have enhanced and rendered consistent the way programmers can refer to these service providers. Until this release, it was possible to describe providers in various ways (e.g., by their service type), but not to identify them uniquely. This could be a problem in situations where, for instance, the programmer desires to use only asynchronous invocations to support synchronous interactions, but the Hub maintains connections to multiple providers of the affected type. If the programmer was either unwilling or unable to lock the server to the session, or if the session itself could make use of multiple providers for the affected type (for load balancing, for instance), the programmer had no other options. Now, provider names fill this gap.


The syntax of provider names

The syntax of provider names is as follows:
"["<id>"]"(<service_type>)
That is, the provider name begins with a left square bracket ("["), followed by an ID, followed by a right square bracket ("]"), followed optionally by the name of a service type (declared by either the SERVICE_TYPE: or SERVER: directives in the Hub script).

We call the bracket-delimited portion the provider ID. The <id> can be either an integer or a string. Here are some examples:
[4]
[myparser]Parser
[17]Dialogue
The integers are assigned by the Hub when the Hub first learns of the existence of each provider: either one it should contact, or one that contacts it. The non-integer IDs are assigned by the Hub programmer, as follows:
SERVICE_PROVIDER: Parser
PROVIDER_ID: [myparser]
These provider names are used in a number of different contexts, which we describe here and in the Hub program reference document.

Extended provider names

In a number of contexts, provider names can be optionally extended with a location suffix. This location suffix is the same format as the value of the LOCATION: directive in the Hub scripts. The suffix is attached with an at sign ("@"):
[7]Parser@foo.bar.com:1567

Selecting a provider

Provider names can impose restrictions on how the Hub selects providers.

The Hub selects a provider to use according to the following rules. These rules apply either to scriptless interaction or to the RHS of Hub program rules.

The basic requirements

First, the provider must minimally satisfy three requirements:

The provider must be available

In order to be available, a provider must be connected, idle (not busy with another operation for another token), and not locked to another session.

The provider must support the specified operation

The RHS of the rule must be listed in the OPERATIONS: list of one of the service types associated with the provider.

The provider must satisfy the specified service type or service provider conditions, if present

The service provider must satisfy whatever conditions are specified by the relevant CONDITIONS: directives.

Service type and provider prefixes

In addition to these requirements, it's possible to narrow the range of provider selection by attaching a prefix to the operation name, separated from the operator by a period ("."). This prefix can be either a service type or a provider name.

If the operation name prefix is the name of a service type, the Hub restricts its search to providers of that type. This restriction can be valuable if multiple service types support the same operation. For example, the following rule directs the Hub to consider only those providers of service type jupiter:

RULE: :request_frame & :key_value & :domain Jupiter --> jupiter.turn_management
Alternatively, if an incoming message named jupiter.turn_management matches no program name (i.e., it's scriptless), the Hub will consider relaying it only to providers of service type jupiter.

The operation name prefix can also be a provider name. In this case, the Hub will consider only one provider, namely the one with the specified name. For example, the following rule directs the Hub to consider only the provider with id 1:

RULE: :request_frame & :key_value & :domain Jupiter --> [1].turn_management
In the scriptless case (i.e., if the Hub receives a message named [1].turn_management which matches no program), the same restriction would apply.

Finally, you can use the PROVIDER_NAME: directive to add a provider name restriction. The advantage of this directive is that it can be any value; so if you've stored the provider name in a key in the token, you can refer to that key:
RULE: :request_frame & :key_value & :domain Jupiter --> turn_management
PROVIDER_NAME: :stored_provider

What if you don't know the name or ID of the provider you're interested in?

If you're interested in referring to a provider by name in a program file, then be sure to give it a PROVIDER_ID: directive when you declare it. If it's a server which contacts the Hub, then your life is a little more complicated. If the provider sends a new message to the Hub at any point (ideally, when it connects), you can call the Builtin function hub_token_owner to retrieve the provider ID of the originating provider. If it doesn't, you're currently out of luck.

Other conditions

If the provider is "write-locked" to the current session (that is, if the session is required to send all its output to that provider when it can), that provider will be the only one considered. The Hub also provides additional functionality which can be used to affect provider selection in Hub programs.

Once the candidates are chosen

If multiple providers satisfy all the requirements, the Hub makes a random choice among them (there is no broadcast option yet). If no candidate fulfills all the requirements, but there is a chance that one will (i.e., it's eligible except for not being idle at the moment), the Hub will queue the message. However, the Hub currently considers some situations irrecoverable, and will not queue the message. This is not and has never been implemented consistently; it will be fixed in a later release, we hope.


Bypassing Hub programs

When the Hub receives a new message, it tries to find a program which matches the message name. This match is an identical string match, and it ignores the significance of the dot notation. This means that even if the provider intends to route the message to a particular provider, and tries to impose this routing by use of the dot notation, the Hub program can override this intention. For instance, the following programs would override this apparent intention in the dot notation examples:
PROGRAM: jupiter.turn_management
...

PROGRAM: [1].turn_management
...

The Communicator infrastructure does provide a way to bypass this potential override (i.e., force a scriptless interaction). The functions GalSS_EnvWriteFrameToProvider and GalSS_EnvDispatchFrameToProvider accomplish this.

int GalSS_EnvWriteFrameToProvider(GalSS_Environment *env, Gal_Frame frame, const char *provider_id, int do_block)
Like GalSS_EnvWriteFrame, but directs the message to the provider name or service type name specified by provider_id and bypasses Hub program matching.

Gal_Frame GalSS_EnvDispatchFrameToProvider(GalSS_Environment *env, Gal_Frame frame, const char *provider_id, GalIO_MsgType *t)
Like GalSS_EnvDispatchFrame, but directs the message to the provider name or service type name specified by provider_id and bypasses Hub program matching.

If you need to know the name of the provider you want to direct the message to, you can retrieve it in one of two ways: either by using the $id entity reference function or the function GalSS_EnvGetOriginatingProvider.

char *GalSS_EnvGetOriginatingProvider(GalSS_Environment *env)
This function returns the provider name of the provider associated with the environment env which originated the token (i.e., sent the new message which caused the Hub to create the token). This provider name will be available in the context of a dispatch function invocation, and will be stored in any environment (or a copy of any such environment) which is created for this purpose, because this information is provided by the Hub along with each dispatch function invocation. If the environment env doesn't have this information recorded (e.g., if it wasn't created for a dispatch function invocation), this function returns NULL.


License / Documentation home / Help and feedback
Last updated August 23, 2002