2.2.3.5 Resource Path: Semantics
This section describes the semantics for a base set of data service URIs. From these base cases, the semantics of longer URIs are defined by composing the rules below.
The URI segments listed in this section use Augmented Backus-Naur Form (ABNF), as specified in [RFC5234] syntax, and the rules used in the segments are defined in the Augmented BNF for URI Construction listing in URI Syntax (section 2.2.3.1) and in [RFC3986]. Directly beneath each ABNF rule that describes a URI, there is a description of the semantic meaning for the URI and an example URI derived from the sample Entity Data Model (EDM) that is defined in Appendix A: Sample Entity Data Model and CSDL Document (section 6).
The following rules are in addition to the grammar rules defined in the resource path semantics listing:
In each of the grammar rules below, the serviceOperation-collEt rule can be substituted for the first occurrence of an entitySet rule in the resource path. This type of a substitution redefines the replaced segment, from identifying an EntitySet to identifying a group of entities.
Any rule within the resource path portion of a data service URI, which identifies an EntitySet or collection of entities, MAY<4> be immediately followed by a parenthesis, as described by the "paren" rule in the ABNF grammar in URI Format: Resource Addressing Rules (section 2.2.3).
The following are the grammar rules of the resource path semantics listing:
URI1 = scheme serviceRoot "/" entitySet
MUST identify all instances of the base EntityType or any of the EntityType's subtypes within the specified EntitySet specified in the last URI segment.
If the EDM associated with the data service does not include an EntitySet with the name specified, this URI (and any URI created by appending additional path segments) MUST be treated as identifying a non-existent resource, as described in Message Processing Events and Sequencing Rules (section 3.2.5).
Example:
URI: http://host/service.svc/Customers Identifies: All customer entities in the Customers Entity Set
URI2 = scheme serviceRoot "/" entitySet "(" keyPredicate ")"
MUST identify a single EntityType instance, which is within the EntitySet specified in the URI, where key EntityKey is equal to the value of the keyPredicate specified.
If no entity identified by the keyPredicate exists in the EntitySet specified, this URI (and any URI created by appending additional path segments) MUST represent a resource that does not exist in the data model.
Example:
URI: http://host/service.svc/Customers('ALFKI') Identifies: The entity in the Customers entity set with the Entity Key 'ALFKI'.
Note The keyPredicate in this example represents an EntityKey made up of a single property (keyPredicate-single) and the type of that property is Edm.String. The literal value of the property is represented using single quotes as per the data literal syntax for primitive types, as specified in Abstract Type System (section 2.2.2).
URI3 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/" entityComplexProperty
MUST identify an instance of a ComplexType on the specified EntityType instance. URI 2 (shown in the preceding example) describes how an entitySet followed by a keyPredicate identifies an EntityType instance.
Example:
URI: http://host/service.svc/Customers('ALFKI')/Address Identifies: The value of the Address property of the customer entity identified by key value 'ALFKI' in the Customers Entity Set.
URI4 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/" entityComplexProperty "/" entityProperty
MUST identify a property of a ComplexType defined on the EntityType of the entity whose EntityKey value is specified by the keyPredicate and is within the specified EntitySet.
As noted in the Augmented BNF for URI Construction listing in URI Syntax (section 2.2.3.1), a path segment containing only the rule entity property can append a '"/$value" segment. A $value MUST be interpreted as a dereference operator and indicates only the value of the property that is being addressed (for example, it does not indicate additional metadata or the surrounding envelope).
Example:
URI: http://host/service.svc/Customers('ALFKI')/Address/Name Identifies: The value of the Name property of the Address ComplexType property of the customer entity identified by key value 'ALFKI' in the Customers Entity Set.
Example:
URI: http://host/service.svc/Customers('ALFKI')/Address/Name/$value Identifies: Same as the example preceding, but identifies the value of the property free of any metadata or surrounding markup.
URI5 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/" entityProperty
MUST identify a property whose type is an EDMSimpleType on the EntityType instance (identified with EntityKey equal to the specified key predicate) within the specified EntitySet.
As noted in the Augmented BNF for URI Construction listing in URI Syntax (section 2.2.3.1), a path segment containing only the rule entity property can append a "/$value" segment. A $value MUST be interpreted as a dereference operator and indicates only the value of the property that is being addressed (for example, it indicates that no additional metadata or surrounding envelope is to be used).
Example:
URI: http://host/service.svc/Customers('ALFKI')/CompanyName Identifies: The name of the customer entity in the Customers EntitySet identified by key 'ALFKI'.
Example:
URI: http://host/service.svc/Customers('ALFKI')/CompanyName/$value Identifies: Same as preceding, but identifies the value of the property free of any metadata or surrounding markup.
URI6 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/" entityNavProperty
MUST identify a set of entities or an EntityType instance that is reached via the specified NavigationProperty on the entity identified by the EntitySet name and key predicate specified.
For example, given an association between Customer and Order entities, an Order entity type might define a NavigationProperty named "OrderedBy" that represents the Customer instance associated with that particular Order instance. Similarly, the Customer entity type might define a navigation property named "Orders" that represents the Order instances associated to that particular Customer instance.
Example:
URI: http://host/service.svc/Customers('ALFKI')/Orders Identifies: The set of Order Entity Type instances (or instances of a sub type of Order) associated with the customer identified by the key 'ALFKI' through the Orders Navigation Property.
URI7 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/$links/" entityNavProperty
MUST identify the collection of all links from the specified EntityType instance (identified by the EntitySet name and key predicate specified) to all other entities that can be reached via the navigation property. The path segment following the $links segment specifies the specific association being addressed, which can identify a single or collection of links. Therefore, this URI identifies a link or collection of links (depending on the association multiplicity defined by the navigation property) and not the value of an entity or collection of entities.
Example:
URI: http://host/service.svc/Customers('ALFKI')/$links/Orders Identifies: The collection of all Links between the entity in the Customers Entity Set identified by key 'ALFKI' and the Orders entities associated with that customer via the Orders navigation property.
Example:
URI: http://host/service.svc/Orders(1)/$links/Customer Identifies: The Link between the order entity with key value 1 in the Orders Entity Set and customer entity associated with that order via the Customer navigation property.
URI8 = scheme serviceRoot "/$metadata"
MUST identify the Entity Data Model Extensions (EDMX) document, as specified in [MC-EDMX], which includes the EDM represented using a conceptual schema definition language (CSDL), as specified in [MC-CSDL], for the data service.
Example:
URI: http://host/service.svc/$metadata Identifies: The EDMX (metadata) document for the data service
URI9 = scheme serviceRoot "/$batch"
MUST identify the endpoint of a data service that accepts Batch Requests (section 2.2.7.6).
Example:
URI: http://host/service.svc/$batch Identifies: The batch request endpoint for a data service
URI10 = scheme serviceRoot "/" serviceOperation-et
MUST identify a FunctionImport that returns a single EntityType instance.
If no FunctionImport exists in the EDM associated with the data service which has the same name as specified by the serviceOperation-et rule, this URI MUST represent a resource that does not exist in the data model.
As per the ABNF grammar in URI Format: Resource Addressing Rules (section 2.2.3), no further resource path segments can be composed onto a URI of this form.
URI11 = scheme serviceRoot "/" serviceOperation-collCt
MUST identify a FunctionImport that returns a collection of ComplexType instances.
If no FunctionImport exists in the EDM associated with the data service that has the same name as specified by the serviceOperation-collCt rule, this URI MUST represent a resource that does not exist in the data model.
As per the ABNF grammar in URI Format: Resource Addressing Rules (section 2.2.3), no further resource path segments can be composed onto a URI of this form.
URI12 = scheme serviceRoot "/" serviceOperation-ct
MUST identify a FunctionImport that returns a ComplexType instance.
If no FunctionImport exists in the EDM associated with the data service that has the same name as specified by the serviceOperation-ct rule, this URI MUST represent a resource that does not exist in the data model.
As per the ABNF grammar in URI Format: Resource Addressing Rules (section 2.2.3), no further resource path segments can be composed onto a URI of this form.
URI13 = scheme serviceRoot "/" serviceOperation-collPrim
MUST identify a FunctionImport that returns a collection of primitive type values. The set of primitive types supported is specified in URI Format: Resource Addressing Rules (section 2.2.3).
If no FunctionImport exists in the EDM associated with the data service that has the same name as specified by the serviceOperation-prim rule, this URI MUST represent a resource that does not exist in the data model.
As per the ABNF grammar in URI Format: Resource Addressing Rules (section 2.2.3), no further resource path segments can be composed on to a URI of this form.
URI14 = scheme serviceRoot "/" serviceOperation-prim
MUST identify a FunctionImport that returns a single primitive type value. The set of primitive types supported is defined in section 2.2.2.
If no FunctionImport exists in the EDM associated with the data service that has the same name as specified by the serviceOperation-prim rule, this URI MUST represent a resource that does not exist in the data model.
A path segment containing only the rule serviceOperation-prim can append a "/$value" segment. A $value MUST be interpreted as a dereference operator and indicates only the value of the property that is being addressed (for example, it indicates no additional metadata or surrounding envelope is to be used).
URI15 = scheme serviceRoot "/" entitySet count
MUST identify the count of all instances of the base EntityType or any of the EntityType's subtypes within the specified EntitySet specified in the last URI segment.
If the EDM associated with the data service does not include an EntitySet with the name specified, this URI MUST be treated as identifying a non-existent resource, as described in Message Processing Events and Sequencing Rules (section 3.2.5).
The $count segment is supported only in the OData 2.0 and OData 3.0 protocols.
URI16 = scheme serviceRoot "/" entitySet "(" keyPredicate ") count
MAY identify the count of a single EntityType instance (the count value SHOULD always equal one), which is within the EntitySet specified in the URI, where key EntityKey is equal to the value of the keyPredicate specified.
If the EDM associated with the data service does not include an EntitySet instance with the keyPredicate specified, this URI MUST be treated as identifying a nonexistent resource, as described in Message Processing Events and Sequencing Rules (section 3.2.5).
URI17 = scheme serviceRoot "/" entitySet "(" keyPredicate ")" value
MUST identify the Media Resource [RFC5023] associated with the identified EntityType instance. The EntityType that defines the entity identified MUST be annotated with the HasStream attribute, as defined in Conceptual Schema Definition Language Document for Data Services (section 2.2.3.7.2). As shown in the ABNF grammar in section 2.2.3.1, the "value" segment shown in this URI MAY be appended to any path which identifies a single entity.
Example:
URI: http://host/service.svc/Documents(1)/$value Identifies: The Media Resource associated with the Document Entity Type instance identified
URI18 = scheme serviceRoot "/" entitySet "(" keyPredicate ")"/" entityCollectionProperty
MUST identify a property whose type is a Collection on the EntityType instance (which is identified with EntityKey equal to the specified key predicate) within the specified EntitySet. As per the ABNF grammar in URI Format: Resource Addressing Rule (section 2.2.3), no further resource path segments can be composed onto a URI of this form.
The entityCollectionProperty segment is supported only in the OData 3.0 protocol.
Example:
URI: http://host/service.svc/Customers(1)/AlternateAddresses Identifies: A Collection Property on the entity.
The named resource stream segment is supported only in the OData 3.0 protocol.
URI19 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/" entityNamedStream
MUST identify a named resource stream that is associated with the identified EntityType instance. The EntityType that defines the entity that is identified MUST declare or inherit from a base type a property of type Edm.Stream with the same name.
Example:
URI: http://host/service.svc/Photos(1)/Thumbnail/ Identifies: The 'Thumbnail' Named Resource Stream associated with the specified Photo
The namespaceQualifiedEntityType segment is supported only in the OData 3.0 protocol.
URI20 = scheme serviceRoot "/" entitySet"/" namespaceQualifiedEntityType
MUST identify all instances of the EntityType, subtype of the base EntityType, or any of its subtypes within the specified EntitySet specified in the prior URI segment.
If the EDM that is associated with the data service does not include an EntityType with the namespace-qualified EntityType specified, this URI (and any URI created by appending additional path segments) MUST be treated as identifying a nonexistent resource, as described in Message Processing Events and Sequencing Rules (section 3.2.5).
Example:
URI: http://host/service.svc/Customers/SampleModel.VipCustomer Identifies: All customer entities in the Customers Entity Set that are of type SampleModel.VipCustomer
URI21 = scheme serviceRoot "/" entitySet"/" namespaceQualifiedEnitityType "(" keyPredicate ")"
URI22 = scheme serviceRoot "/" entitySet"(" keyPredicate ")" "/" namespaceQualifiedEnitityType
Both of the previous URIs are equivalent and MUST identify a single namespace-qualified EntityType instance or one of its subtypes. In each case, the entity instance MUST be within the EntitySet that is specified in the URI, where key EntityKey is equal to the value of the specified keyPredicate.
If no entity identified by the keyPredicate exists in the specified EntitySet, this URI (and any URI created by appending additional path segments) MUST represent a resource that does not exist in the data model.
Examples:
URI: http://host/service.svc/Customers/SampleModel.VipCustomer('ALFKI2') Identifies: The entity in the Customers entity set, of type SampleModel.VipCustomer, with the Entity Key 'ALFKI2'. URI: http://host/service.svc/Customers('ALFKI2')/SampleModel.VipCustomer Identifies: The entity in the Customers entity set, of type SampleModel.VipCustomer, with the Entity Key 'ALFKI2'.
The following path segments MAY be used following a URI in which namespaceQualifiedEntityType is used to specify a derived property:
entityComplexProperty
entityProperty
entityNavProperty
entityCollectionProperty
entityNamedStream
Example:
URI: http://host/service.svc/Customers('ALFKI2')/SampleModel.VipCustomer/CreditPurchases/Balance Identifies: The value of the Balance property of the CreditPurchases ComplexType property of the VipCustomer entity identified by key value 'ALFKI2' in the Customers Entity Set.
Examples:
URI: http://host/service.svc/Customers/SampleModel.VipCustomer('ALFKI2')/CreditPurchases/Balance/$value Identifies: Same as the example preceding, but identifies the value of the property free of any metadata or surrounding markup. URI: http://host/service.svc/Customers/SampleModel.VipCustomer('ALFKI2')/InHouseStaff Identifies: The set of Employee Entity Type instances (or instances of a sub type of Employee) associated with the VipCustomer identified by the key 'ALFKI2' through the InHouseStaff Navigation Property. URI: http://host/service.svc/Customers/SampleModel.VipCustomer('ALFKI2')/$links/InHouseStaff Identifies: The collection of all Links between the VipCustomer entity in the Customers Entity Set identified by key 'ALFKI2' and the Employee entities associated with that VipCustomer via the InHouseStaff navigation property. URI: http://host/service.svc/Customers/SampleModel.VipCustomer('ALFKI2')/$value Identifies: The Media Resource associated with the VipCustomer Entity Type instance in the Customers Entity Set URI: http://host/service.svc/Customers/SampleModel.VipCustomer('ALFKI2')/CountriesOfOperation Identifies: A Collection Property on the VipCustomer entity. URI: http://host/service.svc/Customers/SampleModel.VipCustomer('ALFKI2')/Logo Identifies: The 'Logo' Named Resource Stream associated with the specified property of the VipCustomer entity identified by key value 'ALFKI2' in the Customers Entity Set.
The functionCall segment is supported only in the OData 3.0 protocol.
URI23 = scheme serviceRoot "/" functionCall
The functionCall segment MUST identify a FunctionImport that represents a function (Functions (section 2.2.1.4)). If the EDM that is associated with the data service does not include a FunctionImport with IsSideEffecting set to "false" and the name specified, this URI MUST be treated as identifying a nonexistent resource, as described in Message Processing Events and Sequencing Rules (section 3.2.5).
Further resource path segments or query options MAY be specified only if the FunctionImport does not have IsComposable set to "false".
Examples:
URI: http://host/service.svc/TopTenCustomersInCity(city='Seattle') Identifies: Results of evaluating the TopTenCustomersInCity function with a parameter value of 'Seattle' specified inline. URI: http://host/service.svc/TopTenCustomersInCity(city=@c)?@c='Seattle' Identifies: Results of evaluating the TopTenCustomersInCity function with a parameter value of 'Seattle' specified via a parameter alias. URI: http://host/service.svc/TopTenCustomersInCity()?city='Seattle' Identifies: Results of evaluating the TopTenCustomersInCity function with a parameter value of 'Seattle' specified by parameter name in the query.
The functionCall-partiallyBound segment is supported only in the OData 3.0 protocol.
URI24 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/" functionCall-partiallyBound
The functionCall-partiallyBound segment MUST identify a FunctionImport that represents a function (Functions (section 2.2.1.4)). If the EDM that is associated with the data service does not include a FunctionImport (that has no side effects) with the name specified, this URI MUST be treated as identifying a nonexistent resource, as described in Message Processing Events and Sequencing Rules (section 3.2.5).
The FunctionImport MUST have IsBindable set to "true", and MUST have at least one parameter. The first (binding) parameter MUST be of the same type as is represented by the resource path to which the functionCall-partiallyBound segment is appended.
Further resource path segments or query options MAY be specified only if the FunctionImport is composable.
Example:
URI: http://host/service.svc/Customers('ALFKI')/TopTenOrders Identifies: Results of evaluating the TopTenOrders function with the first (or binding) parameter value of 'http://host/service.svc/Customers('ALFKI')'
This functionCall-partiallyBound segment MAY also be applied to entitySet segments directly.
URI25 = scheme serviceRoot "/" entitySet "/" functionCall-partiallyBound
The functionCall-partiallyBound segment MUST identify a FunctionImport that represents a function (Functions), that has a least one (the binding) parameter of type Collection(entityType) where entitySet contains entityType instances.
Other rules are the same as for URI24.
Example:
URI: http://host/service.svc/Customers/TopTenCustomers Identifies: Results of evaluating the TopTenCustomers function with the first (or binding) parameter value of 'http://host/service.svc/Customers'.
Notice that functionCall-partiallyBound, actionCall, and namespaceQualifiedEntityType segments are the only resource path segments that can be directly appended to a resource path that represents a collection of entities without first selecting a single entity using a keyPredicate. A functionCall—partiallyBound segment is also the only segment that can be appended to a resource path that represents a collection of primitive types or ComplexTypes.
This functionCall-partiallyBound segment MAY also be applied to arbitrary navPaths.
URI26 = scheme serviceRoot "/" entitySet navPath "/" functionCall-partiallyBound
Examples:
URI: http://host/service.svc/SalesPeople(6)/Customers/TopTenCustomers() Identifies: Results of evaluating the TopTenCustomers function with the first (or binding) parameter value of 'http://host/service.svc/SalesPeople(6)/Customers', i.e. the Customers of SalesPerson(6). URI: http://host/service.svc/SalesPeople(6)/Customers/Best()/TopTenOrders() Identifies: Results of evaluating the TopTenOrders function with the first (or binding) parameter value being the result of evaluating the Best function which returns a single customer, and which has been evaluated with its first (or binding) parameter value set to 'http://host/service.svc/SalesPeople(6)/Customers', i.e. the Customers of SalesPerson(6)
Notice that multiple functionCall-partiallyBound segments can be used in a single resource path, as in the previous second example.
The actionCall segment is supported only in the OData 3.0 protocol.
URI27 = scheme serviceRoot "/" entitySet "(" keyPredicate ")/" actionCall
The actionCall segment MUST identify a FunctionImport that represents an action (Actions (section 2.2.1.3)). If the EDM associated with the data service does not include a FunctionImport with the name specified, this URI MUST be treated as identifying a non-existent resource, as described in Message Processing Events and Sequencing Rules (section 3.2.5).
The FunctionImport MUST have IsBindable set to "true", and MUST have at least one parameter. The first (binding) parameter MUST be of the same type as is represented by the resource path to which the actionCall segment is appended.
Further resource path segments or query options MAY be specified only if the FunctionImport is composable.
To invoke an action a POST request MUST be used. All parameters other than the first (binding) parameter MUST be specified in the body of the POST request used to invoke this action (see section 2.2.3.6.5).
URI28 = scheme serviceRoot "/" actionCall
The actionCall segment MAY be called directly off the service root if it has binding set to "false" or if the binding parameter is specified in the POST body (see Action Parameters (section 2.2.3.6.5)).
Listing: Resource Path Semantics