Monday 18 May 2009

Synchronous Communications between Domains

All bridges between domains allow communications in both directions. Even though the domains being bridging are labelled as either client or server. Those roles may be reversed for a given communication. Explicit communications between domains are known as wormholes in Shlaer-Mellor OOA/RD. Wormholes were introduced in OOA96 and later defined in [Wormhole96] as an alternative to domain-crossing events and bridging processes. However, OOA09 integrates these concepts together to gain benefits from both approaches. All synchronous communications between domains involve:

  • bridging processes (request wormholes) in client domains,
  • synchronous services in server domains,
  • request mappings in bridges,
  • synchronous return wormholes in server domains,
  • synchronous return mappings in bridges,
  • and return coordinate types.

A bridging process is an abstract process associated with a terminator in a client domain which may be invoked in any composed operation (action or synchronous service). It may have any number of user-defined input and output parameters. A thread of control passes from one domain to another when a bridging process is invoked. A synchronous return must be invoked by a server domain to continue the original thread of control. Whether processing can still occur within the client domain while waiting for a synchronous return depends on how many concurrent threads have been allocated to the client domain.

A synchronous service (as defined in [SyncServ96]) is a composed operation implemented using an Action Language statement block or a process model. It is associated with a terminator in a server domain. It may have any number of user-defined input and output parameters. A special Return Coordinate parameter is also defined automatically. This parameter is required to invoke a synchronous return wormhole. Return coordinates can be passed on within the server domain as event data items or ordinary parameters and stored as attributes. However, they should not be stored for long since the client domain is waiting for a result. They can also be passed to other domains as external values. However, they can't be used to invoke synchronous returns in other domains.

A request mapping in a client-server bridge is implemented using an Action Language statement block. It maps a request wormhole (domain-crossing event or bridging process) to a control reception point (external event or synchronous service). A synchronous communication always requires a bridging process and a synchronous service. If a domain-crossing event is mapped to a synchronous service then any synchronous returns will be ignored. If a bridging process is mapped to an external event then no synchronous return is possible since new return coordinates are not passed to external events. However, it is still possible to carry an existing return coordinate via an event. The input parameters associated with a request mapping match the input parameters associated with the bridging process. Request mappings have no output parameters. The code in a request mapping must invoke the synchronous service converting bridging process input parameters to synchronous service input parameters.

There may be any number of request mappings for a given bridging process. However, only one synchronous return can be used to satisfy a given invocation. OOA09 allows multiple request mappings, all of which may invoke a synchronous return. Only the first response will be used to satisfy the request. Any additional responses will be ignored. Whether it is good design practice to allow multiple responses here is open to debate. If all return coordinates associated with the synchronous services invoked in response to a bridging request go out of scope then the bridging process invocation can terminate. If all output parameters associated with the bridging process are conditional or have default values then this is a recoverable error that should be flagged but is otherwise acceptable. If there are any mandatory output parameters without default values then this is a fatal error with serious consequences since the original thread of control can't continue. All such fatal errors can be eliminated from deployed systems by ensuring that all bridging process output parameters are either conditional or have a default value. A software architecture may place time limits or other restrictions on bridging processes as long as a default synchronous return is possible, e.g. a software architecture may break a deadlock by invoking default synchronous returns on deadlocked synchronous communications.

A synchronous return wormhole is an abstract process associated with a synchronous service (and as a consequence a terminator) in a server domain which may be invoked in any composed operation (action or synchronous service). The input parameters are automatically determined from the output parameters of the associated synchronous service. Synchronous return wormholes have no output parameters. A self parameter with a return coordinate type is also automatically defined. However, explicit synchronous return wormholes are not actually required in OOA09 since synchronous return mappings and return coordinate types are associated directly with synchronous services rather than synchronous return wormholes. The only benefit of an explicit synchronous return wormhole is that it can be labelled and shown separately on process models.

A synchronous return wormhole is normally invoked on a return coordinate value using an invoke return statement, e.g.

return_coordinate.return(message:"Hello World");
However, within a synchronous service statement block, a synchronous return wormhole can also be invoked using an ordinary non-empty return statement, e.g.
return message:"Hello World";
An empty return statement can't be used for this purpose even if there are no output parameters.

A synchronous return mapping in a client-server bridge is implemented using an Action Language statement block. It maps a synchronous service to a bridging process. It is invoked whenever an explicit or implicit synchronous return occurs. The input parameters associated with a synchronous return mapping match the output parameters of the synchronous service while the output parameters match the output parameters of the bridging process. The code in a synchronous return mapping must convert the synchronous service output values to bridging process output values. If there are no synchronous return mappings for a synchronous service then any synchronous returns will simply be ignored.

A predefined return coordinate type is defined for each synchronous service allowing return coordinates to be safely passed around within a domain since the parameters associated with a return coordinate can be statically determined within Action Language code. There is no generic return coordinate type in OOA09 as a consequence. However, that does not mean that return coordinates can't be passed to a service domain as external values since any return coordinates must be passed back to their server domains (requiring type verification) before they can be used.

No comments: