Skip to main content

ORD Overlay

Alpha

This specification is in alpha and subject to change.

The ORD Overlay is an optional ORD model extension that allows patching both ORD resource metadata and referenced resource definition files (e.g. OpenAPI, AsyncAPI, OData CSDL, MCP/A2A Agent Cards) without modifying the original source files.

{
"ordOverlay": "0.1",
"target": { "ordId": "sap.foo:apiResource:astronomy:v1", "definitionType": "openapi-v3" },
"patches": [
{
"action": "merge",
"selector": { "operation": "getConstellationByAbbreviation" },
"data": {
"summary": "Get constellation by IAU abbreviation",
"description": "Returns full details of a constellation by its IAU abbreviation (e.g. 'Ori' for Orion). Useful for star-chart lookups and astronomy education tools."
}
}
]
}

Distribution

Decision guidance for choosing a distribution mode is collected in the Appendix: ORD Configuration vs. Attached Resource Definition.

Via the ORD Configuration Endpoint

Overlays can be listed directly in the ORD Configuration Endpoint under openResourceDiscoveryV1.overlays. This is the preferred approach for cross-cutting overlays that are not tied to a single resource, or when patching ORD resource metadata itself.

{
"openResourceDiscoveryV1": {
"overlays": [
{ "url": "/ord/overlays/my-api.overlay.json", "accessStrategies": [{ "type": "open" }] }
]
}
}

Attached to an ORD Resource

Overlays can also be attached directly to an API or Event resource as a resourceDefinitions entry with type ord:overlay:v1. This keeps the overlay co-located with the resource it patches.

{
"resourceDefinitions": [
{ "type": "openapi-v3", "url": "/ord/metadata/my-api.oas3.json", "accessStrategies": [{ "type": "open" }] },
{ "type": "ord:overlay:v1", "url": "/ord/overlays/my-api.overlay.json", "accessStrategies": [{ "type": "open" }] }
]
}

Target Resolution

The optional target object narrows which document the overlay applies to. When omitted, all patches in the file are context-free and each patch's selector alone identifies the element.

Key fields on target:

FieldPurpose
ordIdIdentifies the ORD resource being patched (API, Event, Data Product, …). Selects the ORD resource metadata itself.
urlDirect URL to the specific metadata definition file (e.g. an OpenAPI JSON file).
definitionTypeDeclares the format of the file (e.g. openapi-v3, a2a-agent-card). Disambiguates when a resource has multiple definitions attached.

Example of ambiguity: an OData API resource may expose both edmx and openapi-v3 definitions. Provide definitionType and/or url to make the concrete patch target explicit.

For overlays that only patch ORD metadata via selector.ordId, target may be omitted. Multiple resources can be patched in a single file using multiple patches with different selector ordId values.

Selectors

Each patch identifies the element to patch using exactly one selector. Concept-level selectors are preferred over jsonPath because they are resilient to structural format changes (e.g. OpenAPI 3.0 → 3.1, OData CSDL XML → JSON).

SelectorLevelSupported formats
ordIdResourceORD resource metadata
operationOperationOpenAPI (openapi-v2/v3/v3.1+), MCP (MCP Server Card), A2A Agent Card (a2a-agent-card), OData (edmx, csdl-json)
entityTypeEntity typeOData (edmx, csdl-json), CSN Interop (sap-csn-interop-effective-v1)
propertyTypePropertyOData (edmx, csdl-json), CSN Interop (sap-csn-interop-effective-v1)
jsonPathAny locationAny JSON/YAML metadata file (generic fallback)

The operation selector maps to different identifiers depending on the format:

  • OpenAPIoperationId of an HTTP operation in paths.{path}.{method}
  • MCP (any Specification ID) → tools[].name
  • A2A Agent Cardskills[].id
  • OData (edmx, csdl-json) → Action or Function name, namespace-qualified (e.g. OData.Demo.Approval)

When definitionType is set on target, the format is known and the selector resolves unambiguously. When definitionType is absent, the implementation SHOULD infer the format from the target document's content (e.g. the openapi field, $schema, or $kind markers). Using the operation selector with a named format constant that has no operation support (e.g. asyncapi-v2) raises an error.

Patch Actions

Each patch specifies an action and a selector, plus an optional data value. The full semantics of each action (update, merge, append, remove) are defined on the action field.

Key point for merge: arrays are appended, not replaced. To fully replace an array, use two ordered patches — first remove the array, then merge the new value.

Validation

Overlays assume the target document is already valid for its native format. The merge tool does not fully re-validate target formats. After applying an overlay, validate the merged output with the corresponding format-specific tooling.

ORD Aggregator Expectations

An ORD Aggregator MUST apply overlays that patch ORD resource metadata when building its ORD Discovery API and related indexes. This is necessary so that ORD-level overlay changes are reflected in discovery responses, filtering, searching, and similar aggregator behavior.

An ORD Aggregator SHOULD enforce that overlay sources are permitted to patch the target metadata. Without such enforcement, consumers could be exposed to unauthorized metadata changes through overlay processing.

Overlay Document Metadata

Note on perspective: unlike its use in ORD Documents (which scopes transport), perspective on an overlay declares where the patch should be applied — at system-type, system-version, or system-instance level. See the field description for details.

Schema Definitions

ORD Overlay

Type: Object($schema, ordOverlay, ordId, description, perspective, describedSystemType, describedSystemVersion, describedSystemInstance, visibility, target, patches)

PropertyTypeDescription
$schema
OPTIONAL
string
Optional URL to the ORD Overlay schema (defined as a JSON Schema).
If provided, this enables code intelligence and validation in supported editors (like VSCode) and tools.
JSON Schema Format: uri-reference
Array Item Allowed Values (extensible):
  • Any string of format uri-reference
  • "https://open-resource-discovery.org/spec-extension/models/OrdOverlay.schema.json#"
ordOverlay
MANDATORY
string
Version of the ORD Overlay specification.
Allowed Values:
  • "0.1"

Example Values:
  • "0.1"
ordId
OPTIONAL
string
Optional ORD ID of this overlay document.
MUST be provided if the ORD Overlay is published via ORD Configuration endpoint.
Regex Pattern: ^([a-z0-9]+(?:[.][a-z0-9]+)*):(overlay):([a-zA-Z0-9._\-]+):(v0|v[1-9][0-9]*)$
Maximum Length: 255
Example Values:
  • "sap.foo:overlay:astronomy-api-openapi:v1"
description
OPTIONAL
string
Optional description of the overlay document itself.

Notated in CommonMark (Markdown).
Minimum Length: 1
Example Values:
  • "This overlay adds descriptive metadata for AI use-cases\nwithout modifying the original resource definition.\n"
perspective
OPTIONAL
string
Overlay Perspective

Overlay-specific perspective that scopes where this overlay should be applied.

Use this together with describedSystemType, describedSystemVersion, and describedSystemInstance
to describe whether the overlay applies broadly to a system type, to one released system version,
or only to a specific system instance.
Allowed Values:
  • "system-type": Applies the overlay at system-type level.

    Use this when the overlay should patch the same targeted resource across versions and instances
    of the same system type, typically for the same ORD resource major version.
    describedSystemType SHOULD be provided as the identifying context.

  • "system-version": Applies the overlay to one concrete system version.

    Use this when metadata differs between released versions and the patch should only affect
    a specific version of the target resource.
    describedSystemVersion SHOULD be provided, and describedSystemType SHOULD also be provided as parent context.

  • "system-instance": Applies the overlay to one concrete system instance / tenant.

    Use this when the patch reflects tenant-specific configuration, extensions, or runtime differences
    in the target metadata.
    describedSystemInstance SHOULD be provided.


Example Values:
  • "system-type"
  • "system-version"
  • "system-instance"
describedSystemType
OPTIONAL
Information on the system type this overlay describes.
This object is identical to the ORD Document describedSystemType object.

Its purpose is to link the overlay to the same system landscape model as ORD resources, if needed.
This is the primary context object for perspective: system-type, and also the parent context
for more specific system-version and system-instance overlays.

Usually this is not necessary for static overlays if the patched resource is already selected via ORD ID.
describedSystemVersion
OPTIONAL
Information on the system version this overlay describes.
This object is identical to the ORD Document describedSystemVersion object.

Its purpose is to link the overlay to the same system landscape model as ORD resources, if needed.
Use this when the overlay should only patch metadata for one specific released system version.

Usually this is not necessary for static overlays if the patched resource is already selected via ORD ID.
describedSystemInstance
OPTIONAL
Information on the system instance this overlay describes.
This object is identical to the ORD Document describedSystemInstance object.

Its purpose is to link the overlay to the same system landscape model as ORD resources, if needed.
Use this when the overlay should only patch metadata for one concrete tenant / runtime instance.

Usually this is not necessary for static overlays if the patched resource is already selected via ORD ID.
visibility
OPTIONAL
string
Overlay Visibility

Controls which consumers can discover and access this overlay document.

It does NOT control runtime access to the resources being patched — that is managed separately through authentication and authorization mechanisms.

Use this to prevent exposing internal overlay enrichments to inappropriate consumer audiences.
Allowed Values:
  • "public": The overlay can be discovered and accessed by anyone, including customers, partners, and unauthenticated external parties.

  • "internal": The overlay can only be discovered and accessed by vendor internal consumers (e.g. applications or services of the same vendor).
    MUST NOT be made available to external parties or vendor customers.

  • "private": The overlay should not be discoverable outside the application / service's own deployment scope (e.g., outside of the provider application or the same system namespace / system type).

target
OPTIONAL
Optional target context for this overlay.
The target can reference an ORD resource or a referenced resource definition file.

When target is present, at least one identifier (ordId, url, or correlationIds)
MUST be provided so that consumers and tooling can determine what is being patched.

ordId selects the ORD resource metadata itself.
If patches are intended for a specific attached metadata definition file, ordId alone can be ambiguous
when the resource exposes multiple definitions.
In that case, use url and/or definitionType to clarify the intended file.

Example: an OData API resource may provide both edmx and openapi-v3 definitions.
Use definitionType and/or an explicit url to identify which one is patched.

Exception: if all patches exclusively use selector.ordId, the patch selectors themselves
are sufficient to identify the target resources and target may be omitted entirely.
Multiple resources can still be patched by defining multiple patches with different selector ordId values.
patches
MANDATORY
Ordered sequence of patches to apply to the targeted resource(s).
Patches are applied strictly in the order they are listed.
If two patches target the same document element, both are applied in sequence —
the later patch supersedes the earlier one.
Array Constraint: MUST have at least 1 items

Overlay Target

Optional context about the target being patched. The target can refer to an ORD resource or to a referenced resource definition file.

When this object is present, at least one of ordId, url, or correlationIds MUST be provided so that consumers can identify what is being patched. Exception: if all patches exclusively use selector.ordId selectors, target may be omitted entirely.

ordId targets the ORD resource metadata itself. For patching a specific resource definition file of that resource, use url and/or definitionType to disambiguate.

Example: one OData API resource can have both edmx and openapi-v3 definitions attached. In such cases, provide definitionType and/or url to make the concrete patch target explicit.

Multiple identifiers, if provided, are treated as all pointing to the same resource.

Type: Object(ordId, url, correlationIds, definitionType)

PropertyTypeDescription
ordId
OPTIONAL
string
ORD ID of the target being patched (e.g. an API Resource, Event Resource, Data Product).
MUST be a valid ORD ID.
Regex Pattern: ^([a-z0-9]+(?:[.][a-z0-9]+)*):([a-zA-Z0-9.\-]+):([a-zA-Z0-9.\-]+):(v0|v[1-9][0-9]*)$
Maximum Length: 255
Example Values:
  • "sap.s4:apiResource:OP_API_BUSINESS_PARTNER_SRV:v1"
url
OPTIONAL
string
URL or URI pointing directly to the file being patched.
This is typically a resource definition file (e.g. OpenAPI, AsyncAPI, OData CSDL),
but can also point to any JSON/YAML-based target document.
JSON Schema Format: uri-reference
Example Values:
  • "https://example.com/api/openapi.json"
  • "./openapi.yaml"
correlationIds
OPTIONAL
Array<string>
Correlation IDs referencing the target resource in external registries or systems of record.
Reuses the ORD correlation ID format: namespace:type:localId.
All listed IDs are treated as pointing to the same resource.
Array Constraint: MUST have at least 1 items
Array Item Regex Pattern: ^([a-z0-9]+(?:[.][a-z0-9]+)*):([a-zA-Z0-9.\-\/]+):([a-zA-Z0-9.\-\/]+)$
Example Values:
  • ["sap.s4:communicationScenario:SAP_COM_0008"]
definitionType
OPTIONAL
string
Overlay Definition Type

Optional, but RECOMMENDED type of the target definition being patched.
If provided, this SHOULD match the type of the referenced metadata definition
(as used in API/Event/Capability resource definitions).
This is especially useful when ordId resolves to a resource with multiple attached definitions.

This can be used to disambiguate how selectors are interpreted for the target.

MUST be either:
- any valid Specification ID, or
- one of the pre-defined values reused from:
- API Resource Definition type
- Event Resource Definition type
- Capability Definition type

The literal value custom is deprecated for definitionType and MUST NOT be used.
In such cases, use a concrete Specification ID instead.
Array Item Allowed Values (extensible):
  • Any string: Any valid Specification ID.
  • "openapi-v2"
  • "openapi-v3"
  • "openapi-v3.1+"
  • "raml-v1"
  • "edmx"
  • "csdl-json"
  • "graphql-sdl"
  • "wsdl-v1"
  • "wsdl-v2"
  • "a2a-agent-card"
  • "sap-rfc-metadata-v1"
  • "sap-sql-api-definition-v1"
  • "sap-csn-interop-effective-v1"
  • "asyncapi-v2"
  • "sap.mdo:mdi-capability-definition:v1"
  • "ord:overlay:v1"

Example Values:
  • "openapi-v3"
  • "asyncapi-v2"
  • "sap.mdo:mdi-capability-definition:v1"

Overlay Patch

A single patch action to apply to the element identified by the selector.

Type: Object(description, action, selector, data, tags, meta)

PropertyTypeDescription
description
OPTIONAL
string
Optional human-readable note explaining the purpose or rationale of this individual patch.
This field is purely informational and has no effect on patch application.

Typical use-cases:
- Reviewer / audit notes explaining why a particular element is being modified.
- Commit-message style annotations generated by AI tooling (e.g. "Enriched summary for GetUser operation").
- References to tickets or decisions that motivated the change.

Maps 1:1 to the actions[].description field in the
OpenAPI Overlay spec, enabling lossless
round-trip conversion between OpenAPI overlays and ORD overlays.
Example Values:
  • "Added missing description for the pagination parameters."
  • "Marked as deprecated following platform v3 migration."
  • "JIRA-1234: Corrected return type description."
action
MANDATORY
string
The patch operation to perform on the selected element:

- update: Replace the selected element entirely with data.
- append:
- When data is a string: append it to the selected string value.
Only valid when the selected element is a text/string field.
- When data is an object: recursively append each string property in data
to the corresponding string field in the selected object.
Nested objects are traversed; arrays in data are appended to matching arrays.
Throws an error if a string in data targets a non-string field in the target.
- Useful to extend existing descriptions, summaries, or other text fields
without replacing them entirely.
- remove:
- data: {} (empty object): remove the selected element from the document entirely.
- data with null-valued properties: remove only those fields (recursively).
Nested null values remove nested fields as well
(JSON Merge Patch-style delete semantics).

Example for partial removal:
data: { "foo": { "bar": null } } removes only foo.bar inside the selected element.
To remove the entire selected element, use data: {}.
- merge:
- objects are deep-merged recursively.
- scalar values are overwritten by the value from data.
- arrays are appended (new array items are added after existing items).
- existing object properties not mentioned in data are preserved.

To fully replace an array, use two ordered patches:
1. remove the array at the selected location.
2. merge the new array content.
Allowed Values:
  • "update"
  • "append"
  • "remove"
  • "merge"
selector
MANDATORY
Identifies the element in the target to patch.
Exactly one selector type is used per patch. The selector object uses one explicit key:

- ordId: resource level - targets an ORD resource (API, Event, Data Product, ...)
- operation: operation level - targets an operation (OpenAPI: operationId, MCP: tool name, OData: Action/Function name)
- entityType: entity type level - targets an OData EntityType or CSN entity definition by name
- propertyType: property type level - targets a property/element on an OData EntityType/ComplexType or a CSN entity element
- jsonPath: generic fallback - targets any location in a JSON/YAML-based target document by path

Prefer concept-level selectors (operation, entityType, propertyType) over jsonPath
where possible, as they are resilient to structural changes in the target format.
data
MANDATORY
The value to be used together with patch actions:
- with action: append:
- string value appended to selected text field
- with action: merge:
- objects are deep-merged recursively
- scalar values overwrite existing values
- arrays are appended to existing arrays
- with action: update, it replaces the selected element entirely
- with action: remove:
- {} (empty object): the selected element is removed entirely
- object with null-valued properties: only those fields are deleted (recursively,
including nested fields; JSON Merge Patch-style delete semantics)

To fully replace an existing array, use two ordered patches:
1. remove the array
2. merge the new array value

For OData targets (edmx, csdl-json), the value MUST be expressed in CSDL JSON
annotation format. Annotation keys use the @TermName convention:
e.g. { "@Core.Description": "...", "@Core.Revisions": [...] }.
When the target is EDMX XML, the merge implementation converts this to <Annotation> elements.
See: https://docs.oasis-open.org/odata/odata-csdl-json/v4.01/odata-csdl-json-v4.01.html

For CSN Interop targets (sap-csn-interop-effective-v1), the value is plain CSN JSON
merged directly into the matched entity definition or element object.
Use the CSN doc field for human-readable descriptions, and @AnnotationName keys
for vocabulary annotations (e.g. @EndUserText.label, @Semantics.text).
See: https://sap.github.io/csn-interop-specification/

This is a free-form value whose structure depends on the target being patched.

null as a standalone patch value is not supported outside remove masks.
To delete an element, use action: remove with data: {}.
tags
OPTIONAL
Array<string>
String labels associated with the patched element.
Useful for classification, domain tagging, and filtering in registries or tooling.

These are purely informational and have no effect on patch application or on the
target document.
Array Constraint: MUST have at least 1 items
Example Values:
  • ["HR","Employee","Core"]
  • ["deprecated","migration-v3"]
meta
OPTIONAL
Optional arbitrary metadata associated with the patched element for use by overlay
consumers, tooling, and registries.
The contents of this block are never applied to the target document — they are
strictly out-of-band and ignored by the patch merge process.

Use this to carry information that enrichment sources associate with a specific element
but that has no standard representation in the target metadata format.

This is an open/extensible object — any properties are allowed.

Overlay Patch Meta

Optional arbitrary metadata associated with the patched element for use by overlay consumers, tooling, and registries. The contents of this block are never applied to the target document — they are strictly out-of-band and ignored by the patch merge process.

Use this to carry information that enrichment sources associate with a specific element but that has no standard representation in the target metadata format.

This is an open/extensible object — any properties are allowed.

Overlay Selector

Identifies the element in the target to patch. Exactly one selector type is used per patch. The selector object uses one explicit key:

  • ordId: resource level - targets an ORD resource (API, Event, Data Product, ...)
  • operation: operation level - targets an operation (OpenAPI: operationId, MCP: tool name, OData: Action/Function name)
  • entityType: entity type level - targets an OData EntityType or CSN entity definition by name
  • propertyType: property type level - targets a property/element on an OData EntityType/ComplexType or a CSN entity element
  • jsonPath: generic fallback - targets any location in a JSON/YAML-based target document by path

Prefer concept-level selectors (operation, entityType, propertyType) over jsonPath where possible, as they are resilient to structural changes in the target format.

One of the following: Overlay Selector By JsonPath | Overlay Selector By ORD ID | Overlay Selector By Operation | Overlay Selector By Entity Type | Overlay Selector By Property Type | Overlay Selector By Entity Set | Overlay Selector By Namespace | Overlay Selector By Parameter | Overlay Selector By Return Type

Example Values:
{
"ordId": "sap.foo:apiResource:astronomy:v1"
}
{
"operation": "getConstellationByAbbreviation"
}
{
"operation": "OData.Demo.Approval"
}
{
"operation": "dispute-case-resolution"
}
{
"entityType": "OData.Demo.Customer"
}
{
"entityType": "AirlineService.Airline"
}
{
"propertyType": "BirthDate",
"entityType": "OData.Demo.Customer"
}
{
"propertyType": "AirlineID",
"entityType": "AirlineService.Airline"
}
{
"jsonPath": "$.info.description"
}
{
"jsonPath": "$.paths['/constellations'].get"
}

Overlay Selector By JsonPath

Type: Object(jsonPath)

PropertyTypeDescription
jsonPath
MANDATORY
string
JSONPath expression targeting any location in a JSON/YAML-based target document.
MUST start with $.
This is the generic structural fallback selector, supported for all JSON/YAML-based formats:
- openapi-v2, openapi-v3, openapi-v3.1+: targets any node in the OpenAPI document.
- a2a-agent-card: targets any node in the A2A Agent Card JSON document.
- csdl-json: targets any node in the OData CSDL JSON document.
- MCP (any Specification ID): targets any node in the MCP-compatible JSON/YAML tool metadata.

Use concept-level selectors (operation, entityType, etc.) when available, as they are
resilient to structural differences between format versions. Reserve jsonPath for cases
where no concept-level selector covers the target location.
Regex Pattern: ^\$
Minimum Length: 1
Example Values:
  • "$.info.description"
  • "$.paths['/constellations'].get"

Overlay Selector By ORD ID

Type: Object(ordId)

PropertyTypeDescription
ordId
MANDATORY
string
ORD ID targeting an ORD resource (API, Event, Data Product, ...) in an ORD document.
MUST be a valid ORD ID.
Supported metadata formats:
- ORD document (no specific definitionType): locates the ORD resource object whose
ordId field matches this value. The resource type (apiResource, eventResource,
dataProduct, etc.) is derived from the ORD ID namespace and is not required in the selector.

Use this selector when patching ORD resource metadata itself (e.g. title, description,
visibility, tags). For patching the technical API definition file that the resource
references, apply the overlay to that definition file directly using its own selectors.
Regex Pattern: ^([a-z0-9]+(?:[.][a-z0-9]+)*):([a-zA-Z0-9.\-]+):([a-zA-Z0-9.\-]+):(v0|v[1-9][0-9]*)$
Example Values:
  • "sap.s4:apiResource:OP_API_BUSINESS_PARTNER_SRV:v1"

Overlay Selector By Operation

Type: Object(operation)

PropertyTypeDescription
operation
MANDATORY
string
Concept-level operation identifier.
Supported mappings by format:
- OpenAPI (openapi-v2, openapi-v3, openapi-v3.1+): maps to the operationId field on
an HTTP operation inside paths.{path}.{method}.
- MCP (any Specification ID other than a2a-agent-card): maps to tools[].name.
See: https://modelcontextprotocol.io/specification/2025-11-25/schema#tool-name
- A2A Agent Card (a2a-agent-card): maps to skills[].id.
See: https://google.github.io/A2A/specification/#agentskill-object
- OData (edmx, csdl-json): maps to the Action or Function name at Schema level.
MUST use the namespace-qualified name (e.g. OData.Demo.Approval) to be unambiguous.
For OData v2 edmx targets: also searches FunctionImport elements in EntityContainer
when no Schema-level Action/Function matches the name.
For bound operations overloaded on multiple entity types, use jsonPath as a fallback
to target the specific overload.

When definitionType is set on target, the format is known and the selector resolves unambiguously.
When definitionType is absent, the implementation SHOULD infer the format from the target
document's content (e.g. the openapi field, $schema, or $kind markers).
Minimum Length: 1
Example Values:
  • "getConstellationByAbbreviation"
  • "dispute-case-resolution"
  • "OData.Demo.Approval"
  • "OData.Demo.Rejection"
  • "getCompensationHistory"

Overlay Selector By Entity Type

Type: Object(entityType)

PropertyTypeDescription
entityType
MANDATORY
string
Concept-level entity or enum type identifier.
Supported metadata formats:
- edmx (OData v2/v4 CSDL XML): targets EntityType, ComplexType, or EnumType elements
declared in the Schema. MUST use the namespace-qualified name (e.g. OData.Demo.Customer).
For EntitySet-level patching (Capabilities annotations), use the entitySet selector instead.
- csdl-json (OData v4 CSDL JSON): same name resolution as edmx. Resolves elements
with $Kind equal to EntityType, ComplexType, or EnumType.
- sap-csn-interop-effective-v1 (CSN Interop): targets a definitions entry by its
fully qualified key (e.g. AirlineService.Airline). In CSN Interop the key is always
fully qualified, so the fully qualified form MUST be used.

When targeting an EnumType to patch its members individually,
use this selector as the entityType context within a propertyType selector.
Minimum Length: 1
Example Values:
  • "OData.Demo.Customer"
  • "OData.Demo.LeaveRequest"
  • "OData.Demo.OrderStatus"
  • "AirlineService.Airline"

Overlay Selector By Property Type

Type: Object(propertyType, entityType)

PropertyTypeDescription
propertyType
MANDATORY
string
Concept-level property, navigation property, or enum member identifier.
Supported metadata formats:
- edmx (OData v2/v4 CSDL XML): targets a Property or NavigationProperty on an EntityType
or ComplexType; or a Member on an EnumType. Use the unqualified name (e.g. BirthDate).
- csdl-json (OData v4 CSDL JSON): same resolution as edmx. Targets non-$-prefixed keys
on the matched EntityType, ComplexType, or EnumType object.
- sap-csn-interop-effective-v1 (CSN Interop): targets an entry in the elements map of
the matched entity definition. Use the element name as defined (e.g. AirlineID, Name).

entityType MUST always accompany this field to unambiguously identify the owning type.
Property names are unqualified and frequently reused across entity types (e.g. Name,
Description, CreatedAt), so propertyType alone is not a reliable unique selector.

To patch an enum member, set entityType to the qualified EnumType name and
propertyType to the unqualified member name.
Minimum Length: 1
Example Values:
  • "BirthDate"
  • "CountryName"
  • "Fax"
  • "AirlineID"
  • "Name"
  • "Active"
entityType
MANDATORY
string
Required entity type, complex type, or enum type context for the selected property or member.
Because property and member names are unqualified and commonly repeated across types
(e.g. Name, Description, CreatedAt), entityType is mandatory to ensure
the selector is unambiguous and stable across schema evolution.
- For OData EntityType/ComplexType: the namespace-qualified name (e.g. OData.Demo.Customer).
- For OData EnumType: the namespace-qualified EnumType name (e.g. OData.Demo.OrderStatus).
- For CSN Interop: the fully qualified definitions key of the containing entity
(e.g. AirlineService.Airline).
Minimum Length: 1
Example Values:
  • "OData.Demo.Customer"
  • "OData.Demo.LeaveRequest"
  • "OData.Demo.OrderStatus"
  • "AirlineService.Airline"

Overlay Selector By Entity Set

Type: Object(entitySet)

PropertyTypeDescription
entitySet
MANDATORY
string
Concept-level entity set identifier.
Supported metadata formats:
- edmx (OData v2/v4 CSDL XML): targets an EntitySet element inside EntityContainer.
May use the unqualified name (e.g. Customers) or namespace-prefixed name.
- csdl-json (OData v4 CSDL JSON): targets a key with $Collection: true inside the
EntityContainer object in the namespace.

Use entitySet when you need to patch EntityContainer-bound metadata such as
Capabilities annotations (InsertRestrictions, UpdateRestrictions, etc.).
For patching the EntityType structure (Properties, NavigationProperties), use entityType.
Minimum Length: 1
Example Values:
  • "Customers"
  • "SalesOrders"
  • "EmployeeSet"

Overlay Selector By Namespace

Type: Object(namespace)

PropertyTypeDescription
namespace
MANDATORY
string
Concept-level OData schema/namespace selector.
Supported metadata formats:
- edmx (OData v2/v4 CSDL XML): targets the <Schema Namespace="..."> element.
Use the namespace value exactly as declared (e.g. com.example.OrderService).
- csdl-json (OData v4 CSDL JSON): targets the namespace-level object (the non-$-prefixed
key in the CSDL JSON document that matches the namespace value).

Use this selector for service/schema-level annotations such as @Core.Description and
@Core.LongDescription on the OData service as a whole.
Minimum Length: 1
Example Values:
  • "com.example.OrderService"
  • "SFSF.EC.Compensation"
  • "API_BUSINESS_PARTNER"

Overlay Selector By Parameter

Type: Object(parameter, operation)

PropertyTypeDescription
parameter
MANDATORY
string
Concept-level parameter name.
Supported metadata formats:
- edmx (OData v2/v4 CSDL XML): targets a <Parameter Name="..."> child element on
an Action, Function, or FunctionImport. Use the unqualified parameter name.
- csdl-json (OData v4 CSDL JSON): targets an entry in the $Parameter array of an
Action/Function overload whose $Name matches.
- OpenAPI (openapi-v2, openapi-v3, openapi-v3.1+): targets an entry in the
parameters array of the operation identified by operation (operationId), matching
by the parameter name field.

operation MUST always accompany this field to unambiguously identify the owning operation.
Minimum Length: 1
Example Values:
  • "employeeId"
  • "Count"
  • "filter"
operation
MANDATORY
string
Required operation context for the selected parameter.
- For OData: the namespace-qualified Action, Function, or FunctionImport name.
- For OpenAPI: the operationId of the HTTP operation.
Minimum Length: 1
Example Values:
  • "com.example.Svc.TerminateEmployee"
  • "getConstellationByAbbreviation"

Overlay Selector By Return Type

Type: Object(returnType, operation)

PropertyTypeDescription
returnType
MANDATORY
boolean
Flag indicating that the return type of the specified operation is the target.
MUST be true. Use operation to identify the owning operation.
Supported metadata formats:
- edmx (OData v2/v4 CSDL XML): targets the <ReturnType> child element of the
matched Action or Function element.
- csdl-json (OData v4 CSDL JSON): targets the $ReturnType object inside the matched
Action/Function overload array entry.
Constant Value: true
operation
MANDATORY
string
Namespace-qualified Action or Function name whose ReturnType is targeted.
- For edmx: the namespace-qualified name of the Action or Function (e.g. com.example.Svc.TerminateEmployee).
- For csdl-json: the namespace-qualified name looked up in the Namespace object.
Minimum Length: 1
Example Values:
  • "com.example.Svc.TerminateEmployee"
  • "com.example.Svc.GetDirectReports"

Overlay Patch Value

The value to be used together with patch actions:

  • with action: append:
    • string value appended to selected text field
  • with action: merge:
    • objects are deep-merged recursively
    • scalar values overwrite existing values
    • arrays are appended to existing arrays
  • with action: update, it replaces the selected element entirely
  • with action: remove:
    • {} (empty object): the selected element is removed entirely
    • object with null-valued properties: only those fields are deleted (recursively, including nested fields; JSON Merge Patch-style delete semantics)

To fully replace an existing array, use two ordered patches:

  1. remove the array
  2. merge the new array value

For OData targets (edmx, csdl-json), the value MUST be expressed in CSDL JSON annotation format. Annotation keys use the @TermName convention: e.g. { "@Core.Description": "...", "@Core.Revisions": [...] }. When the target is EDMX XML, the merge implementation converts this to <Annotation> elements. See: https://docs.oasis-open.org/odata/odata-csdl-json/v4.01/odata-csdl-json-v4.01.html

For CSN Interop targets (sap-csn-interop-effective-v1), the value is plain CSN JSON merged directly into the matched entity definition or element object. Use the CSN doc field for human-readable descriptions, and @AnnotationName keys for vocabulary annotations (e.g. @EndUserText.label, @Semantics.text). See: https://sap.github.io/csn-interop-specification/

This is a free-form value whose structure depends on the target being patched.

null as a standalone patch value is not supported outside remove masks. To delete an element, use action: remove with data: {}.

Type: object,array,string,number,boolean,null

Overlay System Instance

A system instance is a concrete, running instance of a system type. This object is identical to the ORD Document describedSystemInstance object.

Its purpose is to link the overlay to the same system landscape model as ORD resources, if needed. Usually this is not necessary for static overlays if the patched resource is already selected via ORD ID.

Type: Object(baseUrl, localId, correlationIds)

PropertyTypeDescription
baseUrl
OPTIONAL
string
Optional base URL of the system instance.
By providing the base URL, relative URLs in the overlay are resolved relative to it.
JSON Schema Format: uri-reference
Regex Pattern: ^http[s]?:\/\/[^:\/\s]+\.[^:\/\s\.]+(:\d+)?(\/[a-zA-Z0-9-\._~]+)*$
Example Values:
  • "https://example-sap-system.com"
  • "https://sub.foo.bar.com/api/v1"
localId
OPTIONAL
string
Optional local ID for the system instance (usually tenant ID), as known by the described system.
Maximum Length: 255
Example Values:
  • "LocalTenantId123"
correlationIds
OPTIONAL
Array<string>
Correlation IDs for linking this system instance to external systems of record.
Array Constraint: MUST have at least 1 items
Array Item Regex Pattern: ^([a-z0-9]+(?:[.][a-z0-9]+)*):([a-zA-Z0-9.\-\/]+):([a-zA-Z0-9.\-\/]+)$
Example Values:
  • ["sap.cld:tenant:741234567"]

Overlay System Type

A system type is the abstract type of an application or service, from operational perspective. This object is identical to the ORD Document describedSystemType object.

Its purpose is to link the overlay to the same system landscape model as ORD resources, if needed. Usually this is not necessary for static overlays if the patched resource is already selected via ORD ID.

Type: Object(systemNamespace, correlationIds)

PropertyTypeDescription
systemNamespace
OPTIONAL
string
The system namespace is a unique identifier for the system type.
Regex Pattern: ^[a-z0-9]+(?:[.][a-z0-9]+){1}$
Maximum Length: 32
Example Values:
  • "sap.s4"
  • "sap.c4c"
  • "sap.cld"
correlationIds
OPTIONAL
Array<string>
Correlation IDs for linking this system type to external systems of record.
Array Constraint: MUST have at least 1 items
Array Item Regex Pattern: ^([a-z0-9]+(?:[.][a-z0-9]+)*):([a-zA-Z0-9.\-\/]+):([a-zA-Z0-9.\-\/]+)$
Example Values:
  • ["sap.cld:systemRole:S4_PC"]

Overlay System Version

A system version describes a version/release of the system. This object is identical to the ORD Document describedSystemVersion object.

Its purpose is to link the overlay to the same system landscape model as ORD resources, if needed. Usually this is not necessary for static overlays if the patched resource is already selected via ORD ID.

Type: Object(version, title, correlationIds)

PropertyTypeDescription
version
OPTIONAL
string
The version of the system instance (run-time) or the version of the described system-version perspective.

It MUST follow the Semantic Versioning 2.0.0 standard.
Regex Pattern: ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
Example Values:
  • "1.2.3"
  • "2024.8.0"
title
OPTIONAL
string
Human-readable title of the system version.
Minimum Length: 1
Maximum Length: 255
Example Values:
  • "SAP S/4HANA Cloud 2408"
correlationIds
OPTIONAL
Array<string>
Correlation IDs for linking this system version to external systems of record.
Array Constraint: MUST have at least 1 items
Array Item Regex Pattern: ^([a-z0-9]+(?:[.][a-z0-9]+)*):([a-zA-Z0-9.\-\/]+):([a-zA-Z0-9.\-\/]+)$
Example Values:
  • ["sap.cld:release:2408"]

Appendix

Deep Dive: Overlays vs. Resource Definition Visibility

When additional metadata should only be visible to a narrower audience, two main approaches exist:

  • publish a separate overlay that patches the target metadata for that audience
  • publish multiple resource definitions of the same resource with different API Resource Definition.visibility settings

These approaches solve different problems:

  • resource-definition visibility controls who can access a concrete published definition file
  • overlays add another metadata layer without modifying the original source

Prefer overlays when

  • the enrichment is owned by a different team than the team publishing the base resource definition
  • the enrichment has a different lifecycle, approval workflow, or release cadence
  • the enrichment should be optional and separable from the original source
  • multiple parallel enrichments may exist for different consumers or use cases
  • the original source format should remain untouched, for example because it is generated elsewhere or mirrored from another system

Prefer multiple resource definitions with different visibility when

  • the same producer team owns both the public and internal metadata
  • the enriched information is part of the authoritative source and should not drift from it
  • full consumer compatibility is required without assuming overlay support
  • the difference is primarily "what full definition should this audience receive?" rather than "what extra layer should be applied afterward?"
  • the provider already has a reliable publishing pipeline for separate public/internal definition artifacts

Main tradeoff

  • overlays improve separation of concerns, but they add a second source of truth and may create ordering, sync, and provenance questions
  • duplicated resource definitions reduce consumer complexity and stay self-contained, but they increase publisher-side duplication and consistency obligations
  • both approaches can be combined: a narrower-visibility definition may still be enriched further via overlay

Rule of thumb:

  • use resource-definition visibility for authoritative producer-owned variants
  • use overlays for additive, externally managed, or use-case-specific enrichment layers

Deep Dive: ORD Configuration vs. Attached Resource Definition

Overlays can be distributed either through the ORD Configuration endpoint or by attaching them as ord:overlay:v1 resource definitions to a resource. Those options are not interchangeable in practice, because they imply different ownership and publication models.

The strongest discriminator is ownership: if the overlay is created by a different ORD Provider than the one describing the target resource, there is in practice no way to attach that overlay as a resource definition of the foreign resource. In that case, ORD Configuration is the viable distribution mechanism.

Prefer ORD Configuration when

  • the overlay is created by someone other than the original resource provider
  • the overlay patches ORD resource metadata itself rather than only one attached definition file
  • the overlay is cross-cutting and applies to multiple resources
  • the overlay should be published independently from the lifecycle of one concrete API or Event resource
  • the overlay provider needs its own publication channel and cannot modify the target resource entry

Prefer attaching as a resource definition when

  • the same ORD Provider owns both the target resource and the overlay
  • the overlay belongs to the resource as part of the producer-owned metadata package
  • consumers should discover the overlay directly next to the resource definition it patches
  • the overlay lifecycle is tightly coupled to one specific API or Event resource
  • the producer wants the co-location to be explicit in the resource metadata itself

Main tradeoff

  • ORD Configuration is more flexible for independent publishers, cross-resource overlays, and separate release cycles
  • attached resource definitions are easier to understand when the overlay is just another producer-owned artifact of the same resource
  • ORD Configuration makes provenance and authorization more important, because overlays may come from outside the original resource provider
  • attached overlays reduce indirection, but only work when the publisher controls the target resource entry

Rule of thumb:

  • use attached resource definitions for producer-owned, resource-local overlays
  • use ORD Configuration for externally managed, cross-resource, or ORD-level overlays

Open TODOs

Aggregator behavior and compatibility:

  • Decide how to indicate use-case-specific overlays when multiple overlays exist for the same target.

OData selectors:

  • Define the implementation roadmap for entityType and propertyType selector support in the reference merge library.
  • Decide whether OData overlays should be restricted to annotation-only patches (i.e. data keys MUST follow the @TermName convention). In practice, all meaningful OData enrichments are vocabulary annotations, and allowing arbitrary structural changes could produce invalid CSDL output. Restricting to annotations would also make the patch intent more explicit and aid validation. Note: OData patching/merging almost certainly operates at the annotation level — but it is not entirely clear whether remove or structural changes to non-annotation elements should also be supported (e.g. deprecating or removing an operation from a CSDL description).
  • Decide whether the entityType selector should target only the EntityType/ComplexType definition, or also the EntitySet in the EntityContainer (or both). Currently only the EntityType definition is targeted. EntitySet-level annotations (e.g. Capabilities) sit on the EntitySet, not the EntityType, and are not reachable via the current selector — jsonPath is the current fallback for those cases.
  • Consider aligning OData selectors with the standard OData CSDL Annotation Target syntax. OData defines a well-specified path grammar for identifying any CSDL element as an annotation target (e.g. MyService.MyEntityType/MyProperty, MyService.MyEntityContainer/MyEntitySet). Using this as the native OData selector format would piggyback on an existing standard and avoid inventing a parallel addressing scheme. The trade-off is that consumers and implementors need deeper OData knowledge to construct and interpret selectors correctly, compared to the current named-key approach. Reference: OData CSDL XML 4.01.
  • Not sure if we need fully qualified selectors, maybe we can support both and only require fully qualified selectors in cases where it's ambiguous.

Selectors in General:

Use @EntityRelationship annotations if available as selector for EntityType or PropertyType?