2.2.3.9 Canonical URIs

For data services conformant with the URI path construction rules defined in this specification, the canonical form of an absolute URI identifying a single EntityType instance MUST be formed by adding a single path segment to the Path Prefix. The path segment MUST be made up of the EntitySet name associated with the entity followed by the key predicate identifying the entity within the set.

For example, the URIs http://host/service.svc/Customers('ALFKI')/Orders(1) and http://host/service.svc/Orders(1) identify the same entity in the example data model shown in Appendix A: Sample Entity Data Model and CSDL Document (section 6). Following the rules outlining the canonical form for URIs identifying single entities, the canonical URI in the example is http://host/service.svc/Orders(1).

If an EntityType instance is contained by another EntityType instance (see Containment (section 2.2.1.6)), the canonical URI for the contained EntityType instance SHOULD be relative to the canonical URI of the containing EntityType instance.

If the server follows the URI conventions that are specified by the OData protocol, the canonical URL for contained entities MUST start with the canonical URL of the container entity, followed by a '/', and then the name of the containment NavigationProperty. If the container can contain at most one contained entity, the canonical URL is complete.

For example, if a BookAbstract EntityType contains at most one Book EntityType via a 'Book' containment NavigationProperty, the canonical URL of the Book would be as follows: http://host/service.svc/BookAbstracts(1)/Book.

More commonly, the container can contain many contained entities. For example, an 'Order' entity can contain many 'OrderLines' via the 'Lines' containment NavigationProperty. In situations like this, the URI conventions in the OData protocol state that the canonical URI of a contained entity has to include a keyPredicate (see Resource Path: Construction Rules (section 2.2.3.4)) that identifies the particular contained entity among the other contained entities. An example would be the following: http://host/service.svc/Orders(1)/Lines(6).

Further, if a containment NavigationProperty is backed by an AssociationType that includes a Referential Integrity Constraint that indicates that the contained EntityType shares key values with its container EntityType, the keyPredicate that is used in the canonical URI for the contained EntityType instance ought to omit the key values that are shared between the containing and the contained EntityType instances.