Device Description Repository Simple API 1c

Editors' Draft 15 February 2008

This version:
http://www.w3.org/2005/MWI/DDWG/drafts/api/080215
Latest version:
http://www.w3.org/2005/MWI/DDWG/drafts/api/latest
Previous version:
http://www.w3.org/2005/MWI/DDWG/drafts/api/070831
Editors:
Jo Rabin, dotMobi (mTLD Top Level Domain)
José Manuel Cantera Fonseca, Telefónica I+D
Rotan Hanrahan, MobileAware
Ignacio Marín, Fundación CTIC

Abstract

Web content delivered to a mobile context usually benefits from being tailored to take into account a range of factors such as device form factor, input capabilities, browser markup language support and image format support. Data about such information is stored in proprietary databases called "Device Description Repositories" (DDR).

This document describes a simple API for access to DDRs, in order to ease and promote the development of such adaptive Delivery Context aware Web content.

Status of this Document

This document is an editors' copy that has no official standing.

This section describes the status of this document at the time of its publication. Other documents may supersede this document. A list of current W3C publications and the latest revision of this technical report can be found in the W3C technical reports index at http://www.w3.org/TR/.

This is an Editorial Draft of a possible future W3C Recommendation.

Publication as an Editorial Draft does not imply endorsement by the Device Description Working Group or the W3C Membership. This is a draft document and may be updated, replaced or obsoleted by other documents at any time. It is inappropriate to cite this document as other than work in progress.

This document is published as part of the W3C Mobile Web Initiative (MWI) by the Device Description Working Group. It is a deliverable as defined in the Charter of that group.

Please send comments to public-ddwg@w3.org. This list is archived at http://lists.w3.org/Archives/Public/public-ddwg/.

This document was produced by a group operating under the 5 February 2004 W3C Patent Policy. W3C maintains a public list of any patent disclosures made in connection with the deliverables of the group; that page also includes instructions for disclosing a patent. An individual who has actual knowledge of a patent which the individual believes contains Essential Claim(s) must disclose the information in accordance with section 6 of the W3C Patent Policy.

Revision Description

Table of Contents

1 Introduction
    1.1 Background to the need for Device Description Repositories
    1.2 Development of the Simple API Specification
    1.3 Scope
2 Reading the Specification
    2.1 Normative and Informative Parts
    2.2 Normative Language for Conformance Requirements
3 Interfaces
    3.1 AspectName
        3.1.1 Binding
        3.1.2 Methods
    3.2 Evidence
        3.2.1 Binding
        3.2.2 Methods
    3.3 PropertyName
        3.3.1 Binding
        3.3.2 Methods
    3.4 SimplePropertyValue
        3.4.1 Binding
        3.4.2 Methods
    3.5 SimplePropertyValues
        3.5.1 Binding
        3.5.2 Methods
    3.6 SimpleService
        3.6.1 Binding
        3.6.2 Methods
    3.7 Exceptions
    3.8 Instantiation
4 Vocabularies
5 Conformance
    5.1 General Conformance Requirements
    5.2 Conformance Requirements (Languages where there is a Normative Binding)
    5.3 Conformance Requirements (Languages where there is no Normative Binding)

Appendices

A IDL Definitions for Simple API
B Java Bindings
    B.1 org.w3c.ddr.simple.AspectName
    B.2 org.w3c.ddr.simple.Evidence
    B.3 org.w3c.ddr.simple.PropertyName
    B.4 org.w3c.ddr.simple.SimplePropertyValue
    B.5 org.w3c.ddr.simple.SimplePropertyValues
    B.6 org.w3c.ddr.simple.SimpleService
    B.7 org.w3c.ddr.simple.SimpleServiceFactory
    B.8 Exceptions
C WSDL Language Binding
D Binding rules for mapping APIs to any programming language
E Normative References
F Informative Use Case: To Be defined (Non-Normative)
G Informative References (Non-Normative)
H Acknowledgements (Non-Normative)


1 Introduction

This section is informative.

1.1 Background to the need for Device Description Repositories

The need for Device Descriptions (information about the properties of various aspects of the Delivery Context [@@q.v.]) is not confined to the mobile Delivery Context. It has been common, for some time, to use the technique of "browser sniffing" to determine possibly small but important differences between various desktop Web browsers and adapt content to accommodate those differences.

The number of different properties that need to be recorded for the desktop Delivery Context, is limited when compared with the number of different properties of the mobile Delivery Context that affect the usability of the resulting content. Examples of such properties include screen dimensions, input methods, memory and CPU constraints, as well as differences in implementation and support between Web browsers which typically vary by many factors including markup languages supported and image formats supported.

Historically, it has been difficult or impossible to upgrade Web browser software on mobile devices or to add support for features not present in the Web browser originally shipped with the device. This leads to a very wide variation not only of hardware related features but also of features determined by software and firmware. As a result of this, although the need for content adaptation is a general requirement of the Web as a whole, the need for a more systematic approach is seen as being most urgent in the mobile Delivery Context.

As a result, Device Description Repositories (DDRs) have become the sine qua non of development of content targeted at the mobile Delivery Context. A number of proprietary implementations exist, each with its own API and method of describing the properties of the Delivery Context.

The Device Descriptions Working Group (DDWG) [@@q.v.], a Working Group of the W3C Mobile Web Initiative [@@q.v.], was chartered to create a single API though which property values can be retrieved, and a "core" vocabulary that identifies a small number of such properties.

1.2 Development of the Simple API Specification

By charter, the DDWG's work was limited to providing an API into a DDR, and to consider only those applications of DDRs that relate to the delivery of Web content to mobile devices.

It was recognised at the time of creation of the charter that there are many other similar use cases, including delivery of non Web content (such as MMS) to mobile devices, as well as delivery of Web content to some types of non mobile devices which may share some of restrictions and wide variations of mobile devices.

It was also recognized that by their very nature, DDRs are limited to describing the values of properties of devices that can be known "a priori". For example, while it may be known that the screen size of a particular device is a certain number of pixels, and while it may also be known that the screen orientation can change from landscape to portrait, it cannot be known a priori what the orientation is at any particular moment.

In the course of the work of the DDWG it became clear that having an API that revealed only the a properties of a particular device that can be known a priori, and a potentially different api to reveal those that can not, would entail usability difficulties for creators of software that uses API. For instance, in the example above relating to screen orientation use of a DDR API would reveal the screen orientation for some set of devices, but for other devices leave the need for further, possibly unrelated, API calls to determine the actual screen orientation. It was felt that such a situation would not serve the community of software developers well.

Unfortunately, categorization of properties into classes of "can not be known a priori" (sometimes called dynamic properties) and "can be known a priori" (sometimes called static properties) turns out to be fraught with difficulties, leaving most properties in the category of "can not be known a priori on some set of devices".

Additionally, as work progressed, the DDWG gained an increasing understanding that properties refer in some cases to the Delivery Context as a whole, and in other cases to specific constituent components of the Delivery Context. For example, screen width and height are often considered to be properties of the device hardware, but more usefully to the developer, they might be considered to represent the size of the canvas when operating system and browser chrome, together with scroll bars are taken into account. In other cases, for example, the properties Vendor, Model and Version, each constituent component of the delivery context has a separate and discrete identity, so it is unhelpful to regard these properties as being a superposition of the contributions of the various individual components.

Moreover, it is possible that more than one component of the same type may be present in the delivery context. The type of the component was described by the DDWG as an "aspect" of the Delivery Context, and as work on the API progressed it became clear that to provide a thoroughgoing API that allows both the identification of components present in a Delivery Context, and also allows the querying of aspects or specific components of the Delivery Context is a very significant task that was well beyond the scope and charter of the DDWG. Such a thoroughgoing API would not be limited to mobile Delivery Contexts and would not be limited to determining a priori information.

The DDWG, recognizing the urgent need for an API to ease and promote the development of adaptive context aware content - specifically mobile Web content - decided to create a "simple" API that fulfils the majority of needs of the "Run Time" use case. It decided also to documenting its findings to contribute to a possible future activity in a Working Group chartered to consider uses cases that go beyond the limitations of mobile repository derived information.

1.3 Scope

Various use cases for DDRs are detailed in [Requirements]. In summary, the uses fall into two main classes: design time and run time. The design time use case relates to the activities of the planning, UI prototyping, market research and so on for mobile Web applications. These are collectively also referred to as cataloging functions. By contrast, the run time use case represents the determining of the actual values of properties that are relevant to a particular application for the delivery of Web content.

The W3C DDR Simple API supports only the run-time use case. It provides read-only functionality to allow an adapting application to provide evidence in the form of HTTP headers that identifies the Delivery Context (DC) and allows it query the DDR for property values for aspects of the DC identified. Maybe, Maybe not: In addition, it provides access to basic catalog information that allows it to find out about which properties are supported.

The run-time use case consists, in general, of two logically (though not necessarily in practice) distinct activities: Device Recognition and Property Value Retrieval. The simple API does not expose these two activities as distinct to the user of the API.

The types of components that compose a specific Delivery Context (its aspects) are in general many and various. [@@ don't think this is the best way to go any more aspects should be part of a vocabulary] The simple API recognises two aspects of the delivery context that are "essential" to implementing adaptive mobile content, namely "device" and "Web browser". Other aspects of the Delivery Context may be supported by specific implementations.Actually, do we also recognise "the DC as a whole" and "unspecified" as aspects?

There is an indefinite number of possible properties descriptive of the Delivery Context. The simple API does not define any properties nor mandate the use of any particular set of properties. The DDWG strongly recommends that its Core Vocabulary is supported by all DDRs. Necessary characteristics of sets of properties (known as "vocabularies") supported by the DDR Simple API are document in 4 Vocabularies.

This specification provides a normative definition of the interface based on OMG IDL [IDL]. In addition, it provides a normative WSDL [WSDL] and Java [@@bibref] bindings.

2 Reading the Specification

This section is normative.

3 Interfaces

3.6 SimpleService

This is the principal object of the API and provides the ability to query the value of a property or set of properties given Evidence representing a particular Delivery Context.

3.6.2 Methods

SimplePropertyValue getPropertyValue(Evidence evidence, PropertyName propertyName) throws NameException,SystemException

Returns a SimplePropertyValue for the supplied property. A SimplePropertyValue will be returned but may be @@empty. For Properties that apply to more than one Aspect it is an implementation matter as to which value is returned. But surely the value should say which aspect it pertains to, hence again, shouldn't the PropertyName have an aspect to it?

SimplePropertyValues getPropertyValues(Evidence evidence) throws SystemException;

Returns a SimplePropertyValues containing values for every property for which the DDR has values. None of the entries of SimplePropertyValues may be @@empty.

Exceptions are thrown if ...

SimplePropertyValues getPropertyValues(Evidence evidence, PropertyName[] properties) throws NameException,SystemException;

Returns a SimplePropertyValues for the supplied array of properties. The SimplePropertyValues contains entries for each PropertyName supplied, but PropertyValues may be @@empty. For Properties that apply to more than one Aspect it is an implementation matter as to which value is returned. But surely the value should say which aspect it pertains to, hence again, shouldn't the PropertyName have an aspect to it?

Exceptions are thrown if ...

SimplePropertyValue getPropertyValue(Evidence evidence, AspectName aspect,PropertyName propertyName) throws NameException,SystemException;

This would not be needed if aspect were regarded as part of PropertyName.

Returns a SimplePropertyValue for the supplied PropertyName and Aspect. The SimplePropertyValue returned may be @@empty.

Exceptions are thrown if ... should not throw an exception on unknown name, surely, as the other methods don't.

SimplePropertyValues getPropertyValues(Evidence evidence,AspectName aspect) throws SystemException;

This would not be needed if aspect were regarded as part of PropertyName.

Returns a SimplePropertyValues for the supplied Aspect. The SimplePropertyValues contains entries only for those properties with a value.

Exceptions are thrown if ...

SimplePropertyValues getPropertyValues(Evidence evidence, AspectName aspect,PropertyName[] properties) throws NameException, SystemException

This would not be needed if aspect were regarded as part of PropertyName.

Returns a SimplePropertyValues for the supplied array of PropertyNames. The SimplePropertyValues contains an entry for each PropertyName supplied, but PropertyValues may be @@empty.

Exceptions are thrown if ...

PropertyName newPropertyName(String vocabularyIRI, String localPropertyName) throws NameException;

A factory method for creating new PropertyNames with the specified namespace.

PropertyName newPropertyName(String localPropertyName) throws NameException;

A factory method for creating new PropertyNames with the default vocabulary.

AspectName newAspectName(String aspectIRI) throws NameException;

Not needed if PropertyNames contain aspects. Plus this specifies aspects as IRIs which has not been decided yet.

A factory for creating Aspects.

AspectName[] listAspects() throws SystemException;

This would not be needed if Aspects were recorded as part of PropertyNames.

Returns an array of AspectNames.

PropertyName[] listProperties(String vocabularyIRI) throws SystemException;

This is open to question a) should it be here at all, b) if it is here then there is probably no need for the vocab IRI as all the properties would get listed with their associated vocabularies anyway.

Returns an array of PropertyNames listing @@all the properties the DDR knows about.

String[] listVocabularies()throws SystemException;

This is probably not required as the vocabularies supported can be inferred from the result of listProperties.

void initialize(String defaultVocabularyIRI, Properties props) throws SystemException;

Called with the IRI of a vocabulary to set as the default (which must not be null), and some Java Properties [@@ref] for configuration tasks specific to the implementation. This method is available after instantiation of the SimpleService. If the default vocabulary specified is not supported an [@@exception] is thrown. If there are problems with the configuration properties or there are other initialization issues a SystemException is thrown. Implementation may throw a SystemException if the method is called at any time other than immediately prior to instantiation.

4 Vocabularies

This section is informative.

The DDWG has published a suggested "core" vocabulary for essential properties for Web content adaptation [Core Vocab]. It is anticipated that implementations will extend the core vocabulary by using properties defined in different name spaces.

[@@limitations etc as to how a vocab can be constructed - e.g. property names and data types that can be accommodated by the Simple API, plus aspects etc.] [@@Also need to check that the Core Vocab note makes it clear that extensions require that a new namespace is defined.]

5 Conformance

This section is normative.

A IDL Definitions for Simple API

This appendix contains the complete normative OMG IDL [IDL] definitions for DDR-API

// File: ddrsimpleapi.idl

#ifndef _DDRSIMPLEAPI_IDL_
#define _DDRSIMPLEAPI_IDL_

#pragma prefix "w3c.org"

module ddrsimpleapi
{
	//Forward declarations
	interface AspectName;
	interface PropertyName;
	interface SimplePropertyValue;

	//Array typedefs
	//N.B. the same could be done with anonymous types, but that behaviour is deprecated in IDL
	typedef sequence<AspectName> AspectNameArray;
	typedef sequence<PropertyName> PropertyNameArray;
	typedef sequence<SimplePropertyValue> SimplePropertyValueArray;
	typedef sequence<string> StringArray;
	
	//Represents a Map
	//TODO: Decide which one to choose
	//Alternative
	//interface Map {
	//	string getValue(in string key);
	//};
	struct Pair {
		string key;
		string value;
	};
	typedef sequence<Pair> Map;
	
	//
	//Represents a DDR Exception
	//
	//TODO: There is no exception inheritance in IDL, need to decide whether to use only one exception or several different ones
	//TODO: Methods or attributes?
	exception SimpleException {
		//TODO: how to express constructors?
		long getCode();
		string getMessage();
	};

	exception NameException {
		//TODO: how to express constructors?
		long getCode();
		string getMessage();
	};

	exception SystemException {
		//TODO: how to express constructors?
		long getCode();
		string getMessage();
	};

	exception ValueException {
		//TODO: how to express constructors?
		long getCode();
		string getMessage();
	};

	//Used for NameException
	const long PROPERTY_NOT_RECOGNIZED = 100;
	const long VOCABULARY_NOT_RECOGNIZED = 200;
	const long ASPECT_NOT_RECOGNIZED = 800;
	//Used for SystemException
	const long INITIALIZATION = 400;
	const long CANNOTPROCEED = 500;
	//Used for ValueException
	const long INCOMPATIBLE_TYPES = 600;
	const long NOT_KNOWN = 900;
	const long MULTIPLE_VALUES = 10000;

	
	interface AspectName {
		string getName();
	};

	//
	// Represents a property 
	//
	interface PropertyName {
		//
		// The name of the property
		// 
		string getName();

		//
		// The namespace of the property
		//
		string getNamespace();
	};
	
	//
	//Represents the value of a property
	//
	//TODO: Check the exceptions raised
	interface SimplePropertyValue {
		//
		//Returns the value as double in the default units of the property
		//
		//If the value cannot be represented as a double an exception will be
		//thrown
		//
		double getDouble()
			raises (ValueException);

		//
		//Returns the value as a long in the default units of the property
		//
		//An exception will be thrown if the value cannot be represented as a long
		//
		long getLong()
			raises (ValueException);

		//
		//Returns the value of the property as a string
		//
		//An exception will be thrown if the value does not exist
		//
		string getString()
			raises (ValueException);
		
		//
		//Returns the actual value as a boolean
		//
		//If the value cannot be represented as a boolean an exception will be thrown
		//
		boolean getBoolean()
			raises (ValueException);
		
		//
		//Returns the value as an integer in the default units of the property
		//
		//If the value cannot be represented as an integer an exception will be thrown
		long getInteger()
			raises (ValueException);
		
		//
		//Returns the value as an enumeration
		//
		//If the value cannot be represented as an enumeration an exception will be thrown
		//
		stringArray getEnumeration()
			raises (ValueException);
		
		//
		//Returns the value in the specified unit as a float
		//
		//If the value cannot be represented as a float an exception will be thrown
		//
		float getFloat()
			raises (ValueException);
		
		PropertyName getPropertyName();
		
		boolean exists();
	};
	
	interface SimplePropertyValues {
		SimplePropertyValueArray getAll();

		SimplePropertyValue getValue(in PropertyName prop)
			raises (NameException);
	};
	
	interface SimpleService {
		SimplePropertyValue getPropertyValue(in Map evidence, in PropertyName propertyName)
			raises (NameException, SystemException);

		SimplePropertyValues getPropertyValues(in Map evidence)
			raises (SystemException);

		SimplePropertyValues getPropertyValues(in Map evidence, in PropertyNameArray properties)
			raises (NameException, SystemException);

		SimplePropertyValue getPropertyValue(in Map evidence, in AspectName aspect, in PropertyName propertyName)
			raises (NameException, SystemException);
			
		SimplePropertyValues getPropertyValues(in Map evidence, in AspectName aspect) 
			raises (SystemException);
			
		SimplePropertyValues getPropertyValues(in Map evidence, in AspectName aspect, in PropertyNameArray properties) 
			raises (NameException,SystemException);
			
		PropertyName newPropertyName(in string vocabularyIRI, in string localPropertyName) 
			raises (NameException);
			
		//
		//Creates a property name that is within the default vocabulary
		//
		PropertyName newPropertyName(in string localPropertyName) 
			raises (NameException);
			
		AspectName newAspectName(in string aspectIRI) 
			raises (NameException);
			
		AspectNameArray listAspects() 
			raises (SystemException);

		PropertyNameArray listProperties(in string vocabularyIRI)
			raises (NameException, SystemException);

		StringArray listVocabularies()
			raises (SystemException);

		// Vocabulary cannot be 'null'
		void initialize(in string defaultVocabularyIRI, in Map props)
			raises (SystemException);
	};
	
	interface SimpleServiceFactory {
		SimpleService newSimpleService(in string clazz, in string defaultVocabulary, in Map configuration)
			raises (NameException, SystemException);

		SimpleService newSimpleService(in string defaultVocabulary, in Map configuration)
			raises (NameException, SystemException);
	};
};

#endif _DDRSIMPLEAPI_IDL_

B Java Bindings

Java bindings are normative?

The new version can be downloaded from SVN at https://svn.morfeo-project.org/svn/ddr-ri/trunk/Simple/API/java/DevInfo-Simple-API The code can be browsed in https://forge.morfeo-project.org/plugins/scmsvn/viewcvs.php/trunk/Simple/API/java/DevInfo-Simple-API/?root=ddr-ri

B.4 org.w3c.ddr.simple.SimplePropertyValue

package org.w3c.ddr.simple;

import org.w3c.ddr.simple.exception.ValueException;

/**
 * Represents the value of a property
 * 
 * @author jmcf
 * 
 */
public interface SimplePropertyValue {

	/**
	 * 
	 * Returns the value as double in the default units of the property
	 * 
	 * If the value cannot be represented as a double an exception will be
	 * thrown
	 * 
	 * 
	 */
	public double getDouble() throws ValueException;

	/**
	 * 
	 * Returns the value as a long in the default units of the property
	 * 
	 * An exception will be thrown if the value cannot be represented as a long
	 * 
	 * @return
	 * @throws ValueException
	 */
	public long getLong() throws ValueException;

	/**
	 * 
	 * Returns the value of the property as a String
	 * 
	 * This method will return
	 * 
	 * @return
	 */
	public String getString() throws ValueException;

	/**
	 * Returns the actual value as a boolean
	 * 
	 * If the value cannot be represented as a boolean an exception will be
	 * thrown
	 * 
	 * @return
	 * @throws SimpleException
	 */
	public boolean getBoolean() throws ValueException;

	/**
	 * 
	 * Returns the value as an integer in the default units of the property
	 * 
	 * An exception will be thrown if the value cannot be represented as an
	 * Integer
	 * 
	 * @return
	 * @throws SimpleException
	 */
	public int getInteger() throws ValueException;

	/**
	 * 
	 * Returns the value as an enumeration
	 * 
	 * If the value cannot be represented as an enumeration an exception will be
	 * thrown
	 * 
	 * 
	 * @return
	 * @throws SimpleException
	 */
	public String[] getEnumeration() throws ValueException;

	/**
	 * 
	 * Returns the value in the specified unit as a float
	 * 
	 * If the value cannot be represented as a float an exception will be thrown
	 * 
	 * 
	 * 
	 */
	public float getFloat() throws ValueException;

	/**
	 * @return
	 */
	public PropertyName getPropertyName();

	/**
	 * @return
	 */
	public boolean exists();
}

B.6 org.w3c.ddr.simple.SimpleService

package org.w3c.ddr.simple;


import java.util.Properties;

import org.w3c.ddr.simple.exception.NameException;
import org.w3c.ddr.simple.exception.SystemException;

public interface SimpleService {
	
	public SimplePropertyValue getPropertyValue(Evidence evidence,
			PropertyName propertyName) throws NameException,SystemException;

	public SimplePropertyValues getPropertyValues(Evidence evidence) throws SystemException;

	public SimplePropertyValues getPropertyValues(Evidence evidence,
			PropertyName[] properties) throws NameException,SystemException;
	
	public SimplePropertyValue getPropertyValue(Evidence evidence,
			AspectName aspect,PropertyName propertyName) throws NameException,SystemException;

	public SimplePropertyValues getPropertyValues(Evidence evidence,AspectName aspect) throws SystemException;

	public SimplePropertyValues getPropertyValues(Evidence evidence,
			AspectName aspect,PropertyName[] properties) throws NameException,SystemException;	

	public PropertyName newPropertyName(String vocabularyIRI,
			String localPropertyName) throws NameException;
	
	/**
	 *  Creates a property name that is within the default vocabulary
	 * 
	 * @param localPropertyName
	 * @return
	 * @throws NameException
	 */
	public PropertyName newPropertyName(String localPropertyName) throws NameException;
	
	/**
	 *  Creates an aspect name. An aspect is identified by an IRI
	 *  
	 *  For example in the UWA ontology the WebBrowser is:
	 *  
	 *  http://www.w3.org/2007/uwa/ontologies/DeliveryContext.owl#WebBrowser
	 * 
	 * @param aspectIRI
	 * @return
	 * @throws NameException
	 */
	public AspectName newAspectName(String aspectIRI) throws NameException; 
	
	public AspectName[] listAspects() throws SystemException;
	
	public PropertyName[] listProperties(String vocabularyIRI) throws SystemException;
	
	public String[] listVocabularies() throws SystemException;

	// Vocabulary cannot be 'null'
	public void initialize(String defaultVocabularyIRI, Properties props)
			throws SystemException;
}

C WSDL Language Binding

This section is normative. It describes a WSDL [WSDL] language binding for DDR-API.

D Binding rules for mapping APIs to any programming language

This section is normative

E Normative References

WSDL
"WSDL (tbd)" (See #)
IETF RFC 2119
"Key words for use in RFCs to Indicate Requirement Levels", S. Bradner, March 1997 (See http://www.ietf.org/rfc/rfc2119.txt)
IDL
"OMG IDL Syntax and Semantics", Object Management Group. (See http://www.omg.org/technology/documents/formal/corba_2.htm)
Core Vocab
Device Description Repository Core Vocabulary, W3C @@Working Draft, Andrea Trasatti, Jo Rabin, Rotan Hanrahan (eds.), @@Date (See http://www.w3.org/TR/ddr-core-vocabulary/)

F Informative Use Case: To Be defined (Non-Normative)

This section is informative. It provides an illustration of how the DDR-API could operate.

G Informative References (Non-Normative)

@@tbd

H Acknowledgements (Non-Normative)

The editors wish to acknowledge the contributions of members of the DDWG.

The editors wish to acknowledge the specific written contributions of: