Figure 12-1 illustrates the architecture of a generic SyncML Server. Fundamentally, a Server only needs to implement the SyncML protocols and implement a few applications and data types for compliance and interoperability. It is not necessary for a Server to be structured or be modular in any way. The form of the illustrated generic Server simply follows the function of any given SyncML Server. The function of a SyncML Server can be partitioned into three main parts.
Figure 12-1. The structure of a generic SyncML Server. The components of the Server work together to implement its key functions, Protocol Management, Sync Management, and Data Management.
The Protocol Management part handles functions related to the SyncML protocol itself. These functions include processing and generating messages as per the SyncML Representation Protocol [SRP02], and implementing the handshake sequence as per the SyncML Synchronization Protocol [SSP02]. This part could also handle transport-level authentication and security functions. In addition, in some cases this part may further handle data-level authentication and access control. The Sync Management part primarily handles functions related to maintaining synchronization state and detecting and resolving conflicts. The Data Management part handles functions related to accessing and updating the actual datastores that are being synchronized with the Client. In some cases, this part also handles data-level authentication and access control. One advantage of structuring the Server in this way is that this structure insulates the Sync Management logic from changes in the protocols, and the Data Management logic from changes in the Sync Management logic.
 This is commonly the case for Service Provider Servers.
 This is commonly the case for Enterprise Servers.
The Protocol Management part implements several functions. It performs transport-level authentication; transforms between the wire transport format and the format specified by the SyncML Representation Protocol ; realizes the SyncML Synchronization Protocol; maintains synchronization session information; and transforms between the SyncML format and the different internal formats that may be required by the various Sync Engines. Below we discuss the several components that realize the Protocol Management function.
 For the same logical SyncML package, the actual message transmitted varies depending on the transport used or the particular encryption used.
Service Access Point
The Service Access Point is the primary entry point to the SyncML Server. In many cases, the SyncML Server is a Web server accessed using the HTTP protocol. In such cases the Service Access Point is commonly a Java™ servlet. The access point however, could be a cgi-bin script, or a Visual Basic® script. Messages to the left of the Service Access Point are encoded per their wire transport formats. Messages to the right of the Service Access Point are encoded in the canonical SyncML representation format. The Service Access Point may perform some transport layer authentication and encryption/decryption. In cases where other transports are used (e.g., OBEX [OBEX99]), the Service Access Point could be some custom code accessible via a communication port.
 The Service Access Point itself may not do this, but its underlying infrastructure could. For example, a servlet typically does not perform authentication and/or encryption per se, but the underlying HTTP Server does.
The Sync Adapter is the nerve center of the Protocol Management function. First, it may perform SyncML authentication and access control by consulting the user table that stores usernames, passwords, keys, and certificates. This is especially common in Service Provider Servers, where the Server itself primarily manages the actual datastores. It uses the SyncML Toolkit to transform or generate SyncML Messages to or from "sync objects." The term sync object is used loosely to refer to the internal format that Sync Engines may use. The sync object typically contains synchronization commands and associated data. It is ideal if all Sync Engines associated with the Server can use a common sync object representation. It is possible, however, to have different types of sync objects for different Sync Engines.
The Sync Adapter may also implement the various types of synchronizations in the Synchronization Protocol. It is responsible for conducting the synchronization dialogue with Clients. In addition, the Sync Adapter performs session management for a SyncML session. Using the session table, it keeps track of the progress of a SyncML session and maintains synchronization anchors for Client datastores. It implements failure handling and retries incomplete synchronization sessions.
The Sync Adapter uses the device capabilities table to better control communication with individual Client devices. The capabilities table stores information about individual Client capabilities and also Server capabilities. Client capability information is obtained in the capabilities exchange phase of synchronization. The Sync Adapter, for example, may use Client memory information to limit the size of individual SyncML Messages and decide to send a SyncML Package using multiple Messages.
The SyncML Toolkit is a set of library routines that assist the Sync Adapter in parsing incoming SyncML messages and generating outgoing SyncML messages. A Reference Implementation of the Toolkit exists, but clearly it is not obligatory for a Server to use the Reference Toolkit. In fact, the Toolkit function could be included in the Sync Adapter itself. Many Servers may find it convenient to use the SyncML Toolkit for the task of parsing and generating SyncML messages. The Service Access Point can use the communication toolkit (part of the SyncML Reference Implementation) to easily process and generate messages specific to a transport protocol. Chapter 10 describes the existing SyncML Toolkit.
The Sync Management function primarily consists of detecting and resolving conflicts arising from concurrent updates to data. Further, Sync Management entails various content adaptation functions, such as filtering and field mapping. For example, filtering enables a Server to send only certain fields of a data record to a particular Client. The key component that performs these functions is the Sync Engine.
There can be numerous Sync Engines in a SyncML Server. The Sync Adapter invokes the appropriate Sync Engine, depending on the MIME (Multipurpose Internet Mail Extensions) [RFC2045] type of the application or the data involved in synchronization. The Sync Engine component likely implements a Sync Engine API, which the Sync Adapter can use to communicate with multiple Sync Engines in a consistent manner. Note that this Sync Engine API is not part of the SyncML specification. It is simply an internal API that is convenient for a Server to define and use, as it simplifies the implementation of the Sync Adapter. Some Sync Engines may not implement the "common" Sync Engine API. For such Sync Engines, the Sync Adapter will need to communicate using the specific access API provided by the Sync Engine.
The sync object encapsulates the command, the data being synchronized, and certain qualifiers or metadata associated with the data. For example, for synchronizing calendars, the sync object could contain vCalendar [VCAL] data. Along with the data, the object may contain other qualifiers, such as data identifiers on the Client and the back-end datastore, application identifiers, and a datastore identifier on the Server.
The Sync Engine implements all the logic required for sync analysis. Some Sync Engines can be quite generic. For example, there can be one Sync Engine for the personal calendar application that operates on vCalendar data and encodes certain simple rules about conflict detection and resolution. There can be, however, another Sync Engine for the shared family calendar application (see Chapter 3) that operates on the same kind of data, but encodes slightly more complex rules about conflict detection and resolution.
In general, Sync Engines are configurable, as shown in Figure 12-2(a). A configurable Sync Engine is driven by policies set by administrators, which are used to resolve conflicts. Policies can be specific to applications or data types. Policies could range from simple ones, such as "Server wins" or "Client wins," to more complex ones, such as "user A's updates win over user B's" or "Server wins during the day and Client wins during the night," or "conflicting updates are merged." The Sync Engine in this case is essentially a rule engine that is able to execute a set of well-formed rules.
Figure 12-2. Different types of Sync Engines
Sync Engines can be extensible, as shown in Figure 12-2(b). An extensible Sync Engine allows application programmers to extend the behavior of the Sync Engine by registering callback functions with the Sync Engine. The Sync Engine invokes the callback functions at appropriate times during synchronization for the purposes of conflict resolution. This type of Sync Engine is used in cases where richer application semantics are involved and conflict resolution cannot be encoded in a set of rules. Clearly, a Sync Engine can both be configurable and extensible. For example a provider may choose to implement a Sync Engine for calendars containing some basic rules and policies that can be further specialized for shared family calendars, resource reservation calendars, and business calendars, using application callbacks.
It is common for Sync Engines to perform additional functions to adapt the content for particular Clients. A Sync Engine may use the capability table to determine that a Client only expects a subset of fields present in the back-end data record and to filter the content likewise. Further, a Sync Engine may map between field names used by a Client to and from the field names used by a back-end datastore.
The synchronized data ultimately resides in a back-end datastore such as a Relational Database or a file. The datastore itself may actually be an application, such as Lotus Notes® or Microsoft Exchange®, that in turn manages its own physical datastores. A commercial SyncML Server likely contains numerous Datastore Adapters that facilitate the Sync Engine's access to diverse datastores.
A Datastore Adapter converts a generic sync object into a specific datastore object and vice-versa. For example, data for an application such as vCalendar may eventually be stored in a Relational Database. The corresponding Datastore Adapter will convert vCalendar data into the rows of a database table and vice-versa. The application data can also be stored in files. A file Datastore Adapter will convert vCalendar data to and from structures or records and then write or read files. Calendar data is especially interesting, as the datastore can be an application itself. For example, for synchronizing business calendars, the datastore may be Lotus Notes. The Lotus Notes Datastore Adapter will convert vCalendar data to and from the Lotus Notes format and use the Lotus Notes API instead of the JDBC [Ree00] (Java Database Connectivity) API for databases or the file-access APIs offered by the host operating system.
It is desirable from the Sync Engine perspective to communicate with all back-end datastores using a single Datastore API. This ability insulates the Sync Engine from the particulars of the back-end datastore. Note that the Datastore API is not part of the SyncML specification. It is an internal API that Servers may define and use for reasons of convenience. It is reasonable to expect that most Datastore Adapters can support this internal API, simplifying the Sync Engine appreciably. There can, however, be back-end datastores that are not amenable to a "common" API for which the Sync Engine may have to use a specific access API offered by the corresponding Datastore Adapter.
Another key function of Datastore Adapters is assisting in ID mapping. The Sync Engine and the Datastore Adapter cooperate to realize this function. The Datastore Adapter provides back-end identifiers corresponding to insertions made on Client devices that only bear local Client identifiers. The mapping table is used to maintain associations between local Client identifiers and back-end datastore identifiers. Certain Datastore Adapters, especially in the case of Enterprise Servers, also perform authentication and access control functions.
 Chapter 5 discusses ID mapping in detail.
The Data Management function and Datastore Adapters can be quite complex over and above simple format conversion. In multiple-path synchronization (see Figure 12-5), the Datastore Adapter essentially performs another "synchronization" with the back-end datastore rather than simply reading and writing a back-end datastore.
Figure 12-5. Multiple-path synchronization, where not all data updates pass through the synchronization Server.
An Illustrative Dataflow
Let us consider a simple synchronization to understand how actual synchronization may be realized by this generic architecture. Figure 12-3 shows dataflow and the sequence of actions taken by the different components of the SyncML Server while processing an incoming SyncML Package #3 and generating an outgoing SyncML Package #4 from a Two-way synchronization session.
Figure 12-3. The figure illustrates dataflow and the sequence of actions in a SyncML Server processing Package #3 and Package #4 of a Two-way synchronization session.
An encrypted transport message first arrives at the Service Access Point. The Service Access Point authenticates the message, decrypts it, and passes the resulting SyncML Message to the Sync Adapter. This Message happens to be Package #3 of an ongoing synchronization session containing Client updates. The Sync Adapter updates the session table state to reflect the receipt of Package #3. The Sync Adapter then verifies that the user has access rights to the datastores indicated in the Message. In this case, we assume that the Server itself manages access rights to the datastores. The Sync Adapter uses the SyncML Toolkit library routines to convert the SyncML Message into one or more sync objects and invokes a Sync Engine.
 If this Package were the first for sync initiation, the Sync Adapter would consult the session table for Sync anchors to detect any failures and initiate slow sync if necessary.
The Sync Engine first detects conflicting updates and resolves them. In the process of resolution, the Sync Engine may need to fetch the actual data items using the Datastore Adapter. The Engine also detects new insertions that the Client has made. It further detects that there have been updates on the Server datastore that the Client has not seen. The engine uses the Datastore Adapter to obtain back-end identifiers corresponding to Client insertions and updates the mapping table. The engine also obtains the new updates from the Datastore Adapter. The Engine then returns the results of the conflict resolution and new Server updates as one or more sync objects to the Sync Adapter.
The Sync Adapter uses the returned sync objects to construct a corresponding SyncML Message (Package #4), using the SyncML Toolkit, and returns it to the Service Access Point. The Sync Adapter also updates the session table state to reflect that Package #3 has been processed completely. The Service Access Point uses the SyncML communication toolkit to actually construct the transport message, possibly encrypting the message, and transmit it to the Client.