Skip to content

Creating an Adapter Service

Jim Amsden edited this page Jul 12, 2016 · 5 revisions

Introduction

A generic oslc-server can use the oslc-service configured to support some number of OSLC domain resources with default support for resource creation factories, resource preview, selection and creation delegated dialogs, and OSLC query. However there are many instances where we would like to create an adapter that provides existing data sources as OSLC resources. This page provides an overview for how to create such an adapter, describing the steps for designing the adapter, and providing a specific example scenario and adapter for accessing IoT resources through OSLC REST services.

Implementing OSLC capabilities on existing data sources follows a general pattern that involves executing a number of typical design and implementation steps. The following sections describe those steps for an example OSLC adapter - the iot-service. The iot-service is an example of and Express middleware component that provides OSLC access to resources in the IBM Watson IoT Platform, and the tools used to develop applications on that platform.

1. Define the Problem

The first step is to define the problem the solution is intended to solve. This can be done by describing use cases and/or specific scenarios that capture the integration capabilities that the OSLC IoT adapter would be intended to solve. For OSLC integration, these use cases are well understood and follow typical patterns for:

  • Authentication
  • Service discovery
  • Resource creation
  • Resource preview
  • Resource selection and creation delegated dialogs
  • Resource query

For our iot-service, our minimal use case is to be able to link from any Rational CLM application (RDNG, Rhapsody/DM, RTC, and/or RQM) to certain elements in the IoT dev or runtime platform. These links are intended to enable broader support of full lifecycle activities including cognitive analytics in order to inform development strategies and priorities. It also provides a means of connecting lifecycle data with physical IoT devices that help realize solution requirements.

For example, the use case could be constrained to be one-way links from RDNG requirements to IoT resources that implement the requirements.

2. Decide on an Architecture

There are three typical approaches to providing OSLC capabilities and REST services on existing data sources:

  1. Native Support - the OSLC capabilities are directly built into the IoT platform and/or dev tools
  2. Plugin - As a variation of native support, the OSLC capabilities could be built using some extensibility mechanism provided by the IoT platform
  3. Adapter - a new iot-service can be created using the Adapter Pattern, and used in an iot-server application that is implemented using the native capabilities of the platform.

In the rest of this page we'll assume the adapter approach. This has the advantage that it does not require any changes in the IoT platform or dev tools, and minimizes coupling between applications that use the iot-service and the implementation of the underlying platform resources. iot-service Architecture

In the case of the iot-server, the oslc-service and ldp-services may only provide some reusable capabilities such as OSLC and LDP header management, entity representations in different content types, generic resource preview and delegated dialogs, etc. It is likely the iot-server will not actually store any resources itself, but will get them all from the IoT platform through the iot-service adapter.

3. Map OSLC domain to data source domain

In order to provide OSLC capabilities on IoT platform resources, we have to determine what resources should be exposed as OSLC resources, and how they will be represented using RDF. OSLC defines a number of domains including Requirements Management (RM), Architecture Management (AM), Change and Configuration Management (CCM), Quality Management (QM), etc. Each of these domains is described using an OWL ontology that defines the domain vocabulary terms, including RDFS classes, data and object properties. The OSLC domains also define a set of constraints using OSLC Resource Shapes that constrain the otherwise open vocabularies for use in life-cycle management applications. These constraints can be used to determine what properties must be provided on resource creation, what properties can be updated, and can be used to automatically construct resource preview and delegated dialogs.

It would be easy enough to define a new OSLC domain for IoT devices and other dev and runtime platform resources by creating the vocabulary terms OWL ontology and resource shape constraints. But care should be taken in defining new OSLC vocabularies because once a vocabulary has been created, implemented and integrated with other domains, it becomes hard to change. Also, existing tools that might want to integrate with the new domain would have to be updated to understand the now domain vocabulary, and use the new properties to create links.

OSLC recognizes the difficulty of updating existing tools in order to use new domains, and purposefully defined the existing OSLC domains to be simple, minimal, and provide basis for integration while leaving flexibility for implementations to provide their own extensions in a standard way. One way to limit the changes to existing OSLC applications in order to link to OSLC resources in new data sources is to map the data sources to existing OSLC domain vocabularies or extensions to those vocabularies. This allows existing applications supporting standard domains to be able to link to the now domain resources using known element types with known properties.

For example, the RM specification defines the Requirement class and properties such as oslc_rm:implementedBy or oslc_rm:satisfiedBy. These properties could be used to link requirements to Architecture Management Resources (ARM). IoT devices could be represented as subtypes of Architecture Management Resource. Then RDNG could link to IoT resources without change.

4. Choose the Containers

OSLC resources are usually organized into containers. These containers are represented by LDP Containers (LDPC) of LDP Resources (LDPR), typically LDP RDF Source (LDP-RS) resources. For the Rational CLM tools, the top-level container for resources is the Jazz Project Area. CLM 6.0.3 introduces Fine Grained Components that provide more granular resource containers which can be the using for access control and configuration management. Implementations may provide other containers such as collections of folders.

Different resource containers in a server/tool could potentially support different OSLC services. The OSLC concept of Service Provider corresponds to an LDPC of resources that can be created, selected, previewed, linked to, etc. Each resource in the container has one or more Service entries in the OSLC discovery resources that indicates what can be done on what domain resources - delegated UI for create, selection, preview, query, etc.

The IoT service for example may wish to expose a hierarchy of containers used to organize IoT resources.

5. Define the OSLC services

Now that the resource containers, vocabulary terms and constraints have been defined, possibly as extensions to existing OSLC domains, the services provided by the OSLC server can be defined. These services are defined using the OSLC ServiceProviderCatalog, ServiceProvider and Service LDPC resources. OSLC Service Provider concepts and relationships

For example, the iot-service will need to provide the ServiceProviderCatalog and ServiceProvider resources on GET requests for OSLC discovery resources (the Services are inlined in the ServiceProvider resource based on the OSLC Core constraints). These could be at least partially statically constructed and returned as JSON-LD documents or they may be dynamically constructed based on what is available from the IoT platform through its specific API.

6. Manage Authentication to Connect the Servers

Clients will need to be able to connect to the iot-server, and in the future, the iot-server may need to be a client that connects to other OSLC servers. There is a fair amount of variability in how to authenticate client to server and server to server connections. The simplest approach is to use JavaEE FORM based authentication over https for client to server connections, and OAuth for server to server connections.

For example, the iot-server will need to support OAuth to create connections with any of the CLM servers. Depending on the versions of the CLM servers the iot-server needs to interact with, it may have to implement OAuth 1.0a and/or Open ID Connect. There may be Express middleware components that can be used to support the required connection. For example, see How To Use Twitter OAuth with node-oauth in your Node.js / Express Application

7. Provide Resource Previews

A default OSLC resource preview can be done generically through the oslc-service. Default previews would have fixed icons and labels that would be provided by doing a GET on the resource to provide the required information.

Providing default resource previews through oslc-service will require access to the adapter's specific domain vocabulary and shape constraints as these provide metadata necessary to support reflective creation of the small and large resource dialogs. The adapter service may however need to be involved if the icon representing the resource depends on the state of the resource as only the adapter could know that information.

8. Delegated Dialogs

Similar to resource preview, oslc-service can utilize domain vocabulary and shape information to generate default selection and creation delegated dialogs on adapter resources. If this is not sufficient, or the adapter service wishes to provide more specific or customized dialogs for different resources, then it will have to have the delegated dialog URI requests routed to itself and construct the dialogs itself.

9. CRUD Operations

The adapter service will need to be responsible for handling all CRUD (http POST, GET, PUT, DELETE) operations on the resources it provides. This includes getting individual resources or sets of resources through GET on the resource containers.

POST operations are used to create resources in an LDPC. The entity request body should be the Turtle or JSON-LD representation of the resource to be created, often provided by the content of a creation dialog. The service implementation is responsible for mapping the content of the entity request body to the corresponding representation in the adapted data source, and to use the data source provider's specific API to create the actual data resource.

GET operations can be applied to resource containers (LDPC) or resources adapted from the data source. The adapter service is responsible for translating the request URI into a data source specific id (or primary key), and using the data source API to access the resource. It then converts the resource from the data source format to the corresponding OSLC domain resource, and constructs the entity response body based on the HTTP Accept header. Turtle and JSON-LD content types are required, RDF/XML, XML and HTML are optional but desirable.

PUT operations can be used to update data source elements. The adapter service is responsible for reading the Turtle or JSON-LD entity request body and constructing the corresponding data source element based on the designed OSLC domain to data source mapping. The service then uses data source specific APIs to update the resource.

10. Query

The adapter service may choose to support OSLC query by including a value for the oslc:queryBase property in the Service data. This is the base URI that queries are executed against. It is very often the same as the LDPC URI used for the creation factory oslc:creation property. Utility modules can be used to parse the OSLC queries, but the service adapter must be responsible for converting the OSLC query into one that can be executed by the adapted data source, and to convert the result into the specification for the query result.