Application Capability

Draft Community Group Report,

More details about this document
This version
https://dokieli.github.io/application-capability/
Latest published version
https://dokieli.github.io/application-capability/
History
Commit history
Editors
Sarven Capadisli (v0.3.1415)
Virginia Balseiro (v0.3.1415)
Published
Modified
Feedback
GitHub dokieli/application-capability (pull requests, new issue, open issues)
Language
English
Document Type
Specification
Version
0.3.1415
Policy
Rule
Offer
Unique Identifier
https://dokieli.github.io/application-capability/#document-policy-offer
Target
https://dokieli.github.io/application-capability/
Permission
Assigner
W3C Foo Bar Baz Group
Action

Abstract

Application Capability (AC) defines a structured description of an application's affordances: the actions it can perform, how to invoke them, and what it requires from the environment to function. Consumers, including servers, web user agents, and applications, can discover and process these descriptions to make informed decisions about accessing, presenting, and interacting with resources.

Status of This Document

This report was published by the Foo Bar Baz Group. It is not a W3C Standard nor is it on the W3C Standards Track. Please note that under the W3C Community Contributor License Agreement (CLA) there is a limited opt-out and other conditions apply. Learn more about W3C Community and Business Groups.

Explainer

This section is non-normative.

Note: Temporary Section

This section summarises the proposal for early review, following W3C TAG's Writing Effective Explainers. Discussion takes place in the issue tracker. It is intended for early designs and will be removed as the specification matures.

User-Facing Problem

People choose which applications to use on their resources. When a resource is stored independently of applications, neither the person nor software acting on their behalf can reliably find out which applications can open, edit, annotate, transform, or search it. They also cannot learn what those applications require from the environment, or how to hand the resource over to them. This knowledge is either hard-coded per application or mediated by platform-specific stores and registries.

AI agents assisting users face the same problem. To act on a resource with an application, an agent needs a structured account of what the application can do and how to trigger it, without driving the human interface and without requiring the application to be loaded first.

The problem is also not specific to web applications. Desktop applications and Progressive Web Apps handle resources and register invocation handlers. Their capabilities are described in platform-specific manifests that other parties cannot discover or process uniformly.

Goals

  • An Application publishes one authoritative, machine-readable description of its capabilities and requirements at a dereferenceable IRI.
  • Any Consumer, such as a server, web user agent, application, catalogue, or agent, discovers the description and matches capabilities to a resource and a task.
  • A Consumer constructs an invocation IRI from a declared URI Template, so that a user can act on a resource with an application of their choice.
  • A server reviews an application's declared requirements, such as Content Security Policy directives, and makes informed authorisation decisions.
  • Human-facing and machine-facing use share one declaration. An agent selects a capability from the same description a catalogue or user agent presents to a person, so the two surfaces cannot drift apart.
  • The description is independent of how the application is built or deployed. Web applications, Progressive Web Apps, and desktop applications can publish or embed descriptions.
  • All of the above works without central registries or prior coordination between the parties.

Non-Goals

  • Script-level tool calling between an agent and a loaded application.
  • Defining or replacing web user agent permission models, Content Security Policy, or access control enforcement.
  • Describing user-activated operations or UI events within a running application.
  • Operating a registry of applications. Catalogues can be built from published descriptions.
  • Authentication. For example, the login invocation property is a hint about who to authenticate as, and the application remains responsible for authenticating the user.

Proposed Approach

An application publishes an Application Capability Description, a JSON-LD document discoverable from the application IRI (see Discovery). The description declares Capabilities, the actions the application can perform together with their matching criteria. Each capability links to Invocations. An invocation is typically a URI Template whose variables are bound to properties with defined semantics (see Invocation Properties). The description also declares Requirements, such as Content Security Policy directives annotated with their purpose. It can further declare Policies about the application's own conduct. Notifications let the application's needs be reviewed by the server hosting a resource. A description can also be embedded in host formats so that existing application metadata can carry it. Examples include a Web Application Manifest and a Web Extension manifest (see Embedded Descriptions).

Example: A minimal capability description. The application displays a resource supplied via the open variable. A Consumer invoking it with open = https://data.example/article navigates to https://app.example/#open=https%3A%2F%2Fdata.example%2Farticle.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/",
  "capability": {
    "id": "#capability-open",
    "type": "Capability",
    "action": "odrl:display",
    "invocation": {
      "id": "#invoke-open",
      "type": "UriTemplateInvocation",
      "template": "#open={open}",
      "mapping": [{ "variable": "open", "property": "ac:open" }]
    }
  }
}

Alternatives Considered

  • Web Application Manifest is scoped to installed applications mediated by the browser or operating system, not to applications acting on third-party resources.
  • registerProtocolHandler requires prior browser registration and named schemes rather than arbitrary https: IRIs.
  • Hydra Core Vocabulary describes HTTP API operations. This specification reuses its template and mapping terms by aliasing and subclassing, and adds capabilities, requirements, policies, and notifications.
  • WebMCP registers script-defined tools imperatively and requires the application to be loaded in the browser.

The Introduction lists the related efforts in full.

Stakeholder Feedback

dokieli, a clientside editor for decentralised article publishing, annotations, and social interactions, implements features across this specification. It has a capability description in JSON-LD (curl -H'Accept: application/ld+json' https://dokie.li/) and in HTML+RDFa. An independent Application Capability validator checks a page's capability description against a SHACL shape for the vocabulary. Other implementers have expressed interest. Feedback from communities working on agent and application interoperability is particularly welcome. Application, Security, Privacy, Accessibility, and Internationalisation are addressed in Considerations. These include a Threat Model and the completed Security and Privacy Review and Societal Impact Review.

Introduction

This section is non-normative.

Web applications increasingly operate in decentralised environments where resources are stored and served independently of the applications that consume them. A server hosting a resource has no prior knowledge of which applications a user wishes to use to interact with in different ways. Applications and tools such as resource managers, catalogues, and authorisation agents face the same problem: no reliable mechanism exists to discover what an application supports, what resource types it handles, or what web user agent permissions it requires.

This specification addresses that gap by defining a structured description of an application's capabilities and requirements. An Application Capability Description allows an application to declare, at a discoverable location, the following kinds of information:

  • The media types, classes of resources, or shape of resources it can handle.
  • The actions it can perform on those resources, expressed in terms of established action vocabularies.
  • The invocation patterns used to trigger the application, such as a URI Template for opening a resource.
  • The web user agent level permissions and Content Security Policy directives it requires, so that server operators can make informed decisions about authorisation.
  • Descriptive information such as name, description, homepage, and repository, together with an inbox for receiving notifications about the outcome of a requirements review.

This specification is informed by, but distinct from, the following related efforts:

  • Web Application Manifest defines a JSON-based manifest for installed web apps, primarily for Progressive Web Applications (PWA) use cases. The file_handlers member, defined in Manifest Incubations, declares media-type handling scoped to installed applications mediated by the browser or operating system.
  • Content Security Policy Level 3 defines the CSP header mechanism that servers use to restrict resource loading.
  • Permissions and Permissions Policy define browser permission models.
  • Data Privacy Vocabulary (DPV) provides vocabulary for expressing data processing purposes and policies.
  • Description of a Project (DOAP) provides vocabulary for describing software projects.
  • Hydra Core Vocabulary describes HTTP API operations and IRI templates in RDF.
  • Web of Things (WoT) Architecture defines a self-description model for network-connected entities, describing interaction affordances of the entity itself. This specification describes applications that act on third-party resources and negotiate host-origin Content Security Policy.
  • WebMCP proposes an API for a web page to register script-defined tools that agents can call while the page is loaded in the browser. This specification declares capabilities at a dereferenceable IRI, so Consumers, including agents, can discover them without loading the application and invoke them by navigation.
  • registerProtocolHandler (HTML) allows a web application to register as a handler for a custom URL scheme, enabling scheme-based invocation. It requires prior user-mediated browser registration and is scoped to named schemes rather than arbitrary https: IRIs, making it unsuitable as a general mechanism for invoking applications against HTTP resources.
  • Service Workers can intercept fetch requests before they reach the network, allowing query-string parameters to remain client-side and avoiding server disclosure. This requires the service worker to be registered in advance, introducing a bootstrapping dependency that general-purpose invocation cannot rely on.

Where terms from these vocabularies are appropriate, this specification reuses or references them.

Use cases:

  • Resource owner wants to set application-specific content security policies for servers so that users can bring their own applications to hosted resources without the browser blocking them, and without the server issuing overly permissive blanket policies.
  • End-user wants to use a specific application based on its affordances so that they can choose among applications whose declared actions match their intent, without hardcoded file associations.
  • Application developer wants their application's entry in catalogues to update automatically, by publishing one authoritative capability description that catalogues re-fetch, instead of submitting updates to each catalogue manually.

This specification is intended for:

  • Server and storage operators that want to make security and privacy-relevant decisions about which applications can access resources they serve, and to understand the permissions those applications declare they need.
  • Application developers that want to produce or consume structured capability descriptions from their applications so that they can be discovered and invoked by other consumers.

Terminology

This section is non-normative.

The Application Capability specification defines the following terms. These terms are referenced throughout this specification.

Application
A web application that operates on resources identified by IRIs. An application can be deployed at a fixed origin, embedded in markup-based host languages, or as a Web Extension. An application could act as a Sender, a Consumer, or both.
Sender
An implementation that publishes and, where applicable, delivers an Application Capability Description to a Receiver. Typically an Application making its identity, capabilities, and requirements known.
Receiver
An implementation that accepts and processes capability descriptions or notifications referencing them. Typically an HTTP server that hosts resources, hosts an inbox, reviews declared requirements, and serves Content Security Policy headers accordingly to a Sender or a Consumer.
Consumer
An implementation that reads and processes an Application Capability Description, obtained directly from the Application's IRI or from a Receiver, in order to discover capabilities, prepare invocations, or inform authorisation decisions.
Capability
A declared affordance of an Application: an action that can be triggered by an invocation.
Invocation
The act of triggering an Application to perform processes, for example by navigating to a URI constructed from a URI Template. For invocations based on URI Templates, an invocation covers only the URL-loading step. Subsequent user-activated operations or UI events within the application are out of scope, even though the capabilities do express these affordances.

Namespaces

The following prefixes and namespaces are used in this specification.

Prefixes and Namespaces
Prefix Namespace Description
ac https://www.w3.org/ns/ac# Application Capability (this specification)
as https://www.w3.org/ns/activitystreams# [Activity Vocabulary]
dcterms http://purl.org/dc/terms/ [DC-TERMS]
doap http://usefulinc.com/ns/doap# Description of a Project
dpv https://w3id.org/dpv# [Data Privacy Vocabulary]
hydra http://www.w3.org/ns/hydra/core# [Hydra Core Vocabulary]
ldp http://www.w3.org/ns/ldp# [Linked Data Platform]
oa http://www.w3.org/ns/oa# [Web Annotation Vocabulary]
odrl http://www.w3.org/ns/odrl/2/ [ODRL Vocabulary & Expression 2.2]
rdf http://www.w3.org/1999/02/22-rdf-syntax-ns# [rdf-schema]
rdfs http://www.w3.org/2000/01/rdf-schema# [rdf-schema]

Syntax

This specification uses JSON-LD [JSON-LD11] as the preferred data format, and https://www.w3.org/ns/ac.jsonld as a URI for the JSON-LD context and as a value of the profile parameter used for content negotiation.

Note: Temporary Inclusion

The JSON-LD context and the vocabulary outlined in this section are temporarily included here. Once the JSON-LD context document and the vocabulary are published, they will be the normative references.

JSON-LD context (https://www.w3.org/ns/ac.jsonld)
{
  "@context": {
    "@version": 1.1,
    "@protected": true,
    "ac":      "https://www.w3.org/ns/ac#",
    "as":      "https://www.w3.org/ns/activitystreams#",
    "dpv":     "https://w3id.org/dpv#",
    "hydra":   "http://www.w3.org/ns/hydra/core#",
    "ldp":     "http://www.w3.org/ns/ldp#",
    "oa":      "http://www.w3.org/ns/oa#",
    "odrl":    "http://www.w3.org/ns/odrl/2/",
    "id":   "@id",
    "type": "@type",
    "Accept": "as:Accept",
    "accept": "ac:accept",
    "action": {"@id": "ac:action", "@type": "@id"},
    "actor": {"@id": "as:actor", "@type": "@id"},
    "browserPermission": "ac:browserPermission",
    "Capability": "ac:Capability",
    "capability": {"@id": "ac:capability", "@type": "@id"},
    "cspDirective": "ac:cspDirective",
    "destination": {"@id": "ac:destination", "@type": "@id"},
    "hasPurpose": {"@id": "dpv:hasPurpose", "@type": "@id"},
    "inbox": {"@id": "ldp:inbox", "@type": "@id"},
    "Invocation": "ac:Invocation",
    "invocation": {"@id": "ac:invocation", "@type": "@id"},
    "issuedPolicy": {"@id": "odrl:issuedPolicy", "@type": "@id"},
    "login": {"@id": "ac:login", "@type": "@id"},
    "mapping": "hydra:mapping",
    "object": {"@id": "as:object", "@type": "@id"},
    "open": {"@id": "ac:open", "@type": "@id"},
    "output": "ac:output",
    "property": {"@id": "hydra:property", "@type": "@id"},
    "proxy": {"@id": "ac:proxy", "@type": "@id"},
    "Reject": "as:Reject",
    "Request": "ac:Request",
    "Requirement": "ac:Requirement",
    "requirement": {"@id": "ac:requirement", "@type": "@id"},
    "resourceType": {"@id": "ac:resourceType", "@type": "@id"},
    "search": "ac:search",
    "selector": {"@id": "oa:hasSelector", "@type": "@id"},
    "state": {"@id": "oa:hasState", "@type": "@id"},
    "shape": {"@id": "ac:shape", "@type": "@id"},
    "summary": "as:summary",
    "template": "hydra:template",
    "UriTemplateInvocation": "ac:UriTemplateInvocation",
    "variable": "hydra:variable"
  }
}

When this context is combined with other JSON-LD contexts, for example ActivityStreams in Request Notifications, it is listed last so that its term definitions apply.

This context does not define a term for typing the application itself. A capability description subject can carry any type from its host vocabulary (for example as:Application, an OAuth client, a doap:Project, or a Web of Things Thing) or none at all. See Capability Description.

The ac vocabulary defines the following classes and properties. Terms mapped to other vocabularies, such as as, hydra, and ldp, retain the semantics of their defining specifications.

Classes
Term IRI Description
Accept, Reject as:Accept, as:Reject Outcome notification types (Activity Vocabulary).
(none) ac:Application A web application that operates on resources identified by IRIs. Not aliased in the context: a capability description subject can use this class, a host vocabulary's type, or none at all.
Capability ac:Capability A declared affordance of an application: an action that can be triggered by an invocation. See Capability.
Invocation ac:Invocation An abstract class describing one mechanism by which a capability is triggered. See Invocation.
Request ac:Request A notification asking a Receiver to review information concerning an application and act on it. See Request Notification.
Requirement ac:Requirement A declaration of something the application needs from its environment. See Requirement.
UriTemplateInvocation ac:UriTemplateInvocation An Invocation by navigation to an IRI constructed from a URI Template, a subclass of hydra:IriTemplate. See URI Template Invocation.
Properties
Term IRI Description
accept ac:accept Media types a capability accepts as input.
action ac:action The action a capability affords, preferably from a controlled and shared vocabulary.
actor, object, summary as:actor, as:object, as:summary Properties used in Request Notifications (Activity Vocabulary).
browserPermission ac:browserPermission A browser permission name the application could request at runtime.
capability ac:capability Links an application to one or more Capability declarations.
cspDirective ac:cspDirective A CSP directive the host server ought to include with responses of resources the application creates, modifies, or opens.
destination ac:destination The IRI to deliver or save the result of an action to.
hasPurpose dpv:hasPurpose Links to a DPV purpose class expressing why the application needs the declared permissions.
login, open, output, proxy, search ac:login, ac:open, ac:output, ac:proxy, ac:search Invocation properties parameterising the IRI used to invoke an application. See Invocation Properties.
selector, state oa:hasSelector, oa:hasState Invocation properties identifying a segment and a version of the resource. See Invocation Properties.
inbox ldp:inbox The IRI of a Linked Data Notifications inbox associated with the application.
invocation ac:invocation Links a capability to one or more Invocations describing how to trigger it.
issuedPolicy odrl:issuedPolicy Links an application, as a Party, to a Policy it issues about its own conduct.
mapping hydra:mapping Mapping nodes pairing a template variable with its defining property.
output ac:output Media types of the result produced by a capability's action.
property hydra:property The property defining the semantics of a template variable.
requirement ac:requirement Links an application to one or more Requirement declarations.
resourceType ac:resourceType IRIs identifying the classes of resource a capability applies to.
shape ac:shape IRIs identifying shapes for a resource that a capability applies to.
template hydra:template A URI Template [RFC6570] expressing the invocation-specific part of the IRI.
variable hydra:variable The string name of a variable as used in a template.

Conformance

This section describes the conformance model of the Application Capability specification.

Normative and Informative Content

All assertions, diagrams, examples, and notes are non-normative, as are all sections explicitly marked non-normative. Everything else is normative.

The key words “MUST”, “MUST NOT”, “SHOULD”, and “MAY” are to be interpreted as described in BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all capitals, as shown here.

The key words "strongly encouraged", "strongly discouraged", "encouraged", "discouraged", "can", "cannot", "could", "could not", "might", and "might not" are used for non-normative content.

Specification Category

The Application Capability specification identifies the following Specification Category to distinguish the types of conformance: content/data (the capability description format), notation/syntax (the URI Template invocation syntax), and protocol (the discovery and notification interactions between Senders, Receivers, and Consumers).

Classes of Products

The Application Capability specification identifies the following Classes of Products for conforming implementations.

A single implementation can fulfil more than one role simultaneously.

Capability Description
The structured document describing a web application's capabilities and requirements.
Receiver
An implementation (typically a responding agent such as a server) that accepts HTTP requests to provide a representation of a Capability Description. Receivers also accept notifications to their inbox about capability descriptions so that the needs of an application can be reviewed and processed, such as applying CSP headers or addressing authorisation needs.
Consumer
An implementation that reads and processes a Capability Description in order to discover application's capabilities and requirements, construct invocation instructions, or surface other application affordances.
Sender
An implementation that delivers a Capability Description to a Receiver's inbox.

Interoperability

In this specification, interoperability occurs between the Classes of Products defined by this specification: Consumer–CapabilityDescription, Consumer–Receiver, and Sender–Receiver.

Consumer–Capability Description interoperability
Interoperability of implementations for Consumer and Capability Description is tested by evaluating the description's conformance to the data model and processing of descriptions.
Consumer–Receiver interoperability
Interoperability of implementations for Consumer and Receiver is tested by evaluating an implementation's ability to request and respond to HTTP messages.
Sender–Receiver interoperability
Interoperability of implementations for Sender and Receiver is tested by evaluating an implementation's ability to request and respond to HTTP messages.

Subdivisions

This document can be subdivided into the following modules:

Discovery

The starting point for discovery is a web resource containing a capability description. How the subject URI of an application is obtained is not constrained by this specification.

A capability description is the set of statements this specification defines about an application, sharing the application's IRI as their subject. A Consumer that obtains that IRI treats it as the subject of the capability description and dereferences it, directly or via redirect, requesting a format that carries the description, such as application/ld+json. In the case of a fragment URI, the Consumer fetches the document at the base IRI and locates the subject within it by matching the full URI. A Consumer can obtain a capability description from a Receiver that has accepted and stored it from a Sender.

Example: Discovery of a capability description resource.
GET https://app.example/
Accept: application/ld+json

HTTP/1.1 200 OK
Content-Type: application/ld+json

Data Model

Capability Description

The following application-level properties are defined by this specification for describing an application.

capability
Links the application to one or more Capability declarations.
requirement
Links the application to one or more Requirement declarations.
inbox
The IRI of an inbox to which notifications concerning the application can be delivered, such as the outcome of a requirements review. Applications that wish to receive such notifications can publish this property [LDN].
issuedPolicy
Links the application, as an odrl:Party, to a policy, inline or referenced by IRI, it asserts about its own conduct, e.g., rules over data it processes or defaults it applies to resources it creates [ODRL-MODEL]. Issuing a policy grants no privileges.

These properties can be attached to any resource identifying an application. The Application type is not required for conformance. Consumers process these properties by subject, consistent with Discovery, which targets the application as the subject of these statements. See Embedded Descriptions for usage alongside other vocabularies and within non-RDF formats.

Example: Application capability description in JSON-LD. One capability per action, and capabilities can include their invocations. The type and descriptive properties come from host vocabularies (here ac:Application and as:name). Neither is required.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#i",
  "type": "ac:Application",
  "as:name": "Example App",
  "inbox": "https://app.example/inbox/",
  "capability": [
    "https://app.example/#capability-view",
    "https://app.example/#capability-edit",
    "https://app.example/#capability-transform-html"
  ],
  "requirement": [
    "https://app.example/#requirement-scripts",
    "https://app.example/#requirement-styles",
    "https://app.example/#requirement-connect",
    "https://app.example/#requirement-notifications"
  ],
  "issuedPolicy": "https://app.example/#policy-conduct"
}

Capability

A Capability is a resource of type Capability that declares one action an application can perform, the media types (if any) the action applies to, and how to invoke it.

Because capabilities are identified by IRIs, they can be shared across applications. An application's capability description can reference a capability IRI published elsewhere (for example, a well-known capability defined by a community or standard) rather than defining its own. Multiple applications linking to the same capability IRI signal that they support the same action under the same terms.

accept
Zero or more media types [IANA-MEDIA-TYPES] that this capability accepts as input.
resourceType
Zero or more IRIs identifying the classes of resource (e.g., rdf:type) this capability applies to.
shape
Zero or more IRIs identifying shapes (e.g., SHACL) for a resource that this capability applies to. The interpretation of a shape is bound to the capability's action: for a display or edit action the shape describes the accepted input, and for a transform action the accepted source. Shape-based matching is stricter than accept or resourceType matching, and Consumers can fall back to the coarser criteria when shape validation is unavailable.
action
The action the application can perform per capability. Each capability declares an action. Recommended practice is to use values from a controlled and shared vocabulary (such as ODRL actions). An application that affords multiple actions declares multiple capabilities, which can share an invocation by reference.
invocation
Links the capability to one or more invocations describing how to trigger it.
destination
The IRI to deliver or save the result to. Used when the action produces an output.
output
Zero or more media types of the result produced by the action. An application that can produce multiple output formats declares a separate Capability for each format. Consumers match the desired output format against the declared output to select the appropriate Capability, then pass that format as the output invocation variable.

Matching semantics: a capability is matched on a criterion (accept, output, resourceType, shape) only if it declares that criterion. An absent criterion is not a wildcard. A capability that declares none of them is selected by its action. Consumers are encouraged to ignore capabilities whose declared action, accept, or resourceType they do not recognise rather than treat them as errors.

Note: Scope of Action

action describes what the application affords once invoked. It is unrelated to the HTTP GET used for navigation and to the methods the application later uses to manipulate the resource, which are outside the scope of this specification.

Example: A capability that advertises what the application can do without declaring how to invoke it. Consumers can surface it in a UI (e.g. a catalogue entry) but cannot construct an invocation IRI from it.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#capability-open",
  "type": "Capability",
  "action": "odrl:display"
}
Example: An open capability with an invocation. No accept, output, or destination: the application opens any resource the Consumer provides.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#capability-open",
  "type": "Capability",
  "action": "odrl:display",
  "invocation": "https://app.example/#invoke-open"
}
Example: Two capabilities sharing one invocation by IRI reference. The Consumer selects by action (display versus modify), then follows the shared invocation IRI.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#capability-view",
  "type": "Capability",
  "accept": ["text/html", "text/markdown"],
  "action": "odrl:display",
  "invocation": "https://app.example/#invoke-open"
}
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#capability-edit",
  "type": "Capability",
  "accept": ["text/html", "text/markdown"],
  "action": "odrl:modify",
  "invocation": "https://app.example/#invoke-open"
}
Example: A transform capability with all properties. The Consumer matches on accept and output format to select this capability, then invokes it with the resource to transform. The application delivers the result to the declared destination.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#capability-transform",
  "type": "Capability",
  "accept": "text/markdown",
  "action": "odrl:transform",
  "output": "text/html",
  "destination": "https://storage.example/output/",
  "invocation": "https://app.example/#invoke-transform"
}

Invocation

An Invocation is a resource describing one mechanism by which a capability is triggered. Invocation is an abstract class. Every Invocation is typed with one of its subclasses. This specification defines UriTemplateInvocation. Other invocation kinds can be described by defining additional subclasses of Invocation. This specification does not constrain their form.

A capability can declare multiple invocations. A Consumer selects an invocation according to its own deployment context and not by document order. Consumers are encouraged to ignore invocations of a type they do not recognise rather than treat them as errors.

An application ultimately decides whether to carry out a given invocation and in which order invocations are processed. An error with one invocation could prevent related invocations from being fulfilled.

URI Template Invocation

A UriTemplateInvocation describes invocation by navigation: the Consumer expands the template, resolves the result against the application's deployment IRI, and navigates the user agent to it via HTTP GET. How the invocation parameters are carried within the IRI, and the resulting trade-offs, are described in the notes below.

template
A URI Template [RFC6570] expressing the invocation-specific part of the IRI. The Consumer resolves the expanded result against the application's deployment IRI, following the reference resolution rules of RFC 3986, to obtain the full invocation IRI, so that the same template works regardless of where the application is deployed. An expansion that is already an absolute IRI is used as is. Each variable in the template has a mapping entry giving its property. How each variable's value appears in the expanded IRI follows one of two forms, the query form or the functional form, described under Encoding below. Values produced by simple expansion are percent-encoded, satisfying the requirement that resource IRIs travel percent-encoded [RFC3987].
mapping
Zero or more mapping nodes, each pairing a variable (the string name used in the template) with a property (the property that defines its semantics). Each variable in the template has a mapping node. The variable name is a local placeholder, and its meaning rests on the property, whether one defined in Invocation Properties or an application-defined one. See Invocation Extension.

Each invocation parameter is encoded in one of two forms, the query form or the functional form, chosen by the property mapped to its variable and defined below. The form is independent of where the parameter is placed: either form can sit in the fragment or the query component, and only parameters in the query component are sent to the application's host.

Query form
Name-bearing: each variable pairs its name with its value explicitly, for example #open={open}, so that the receiving application can identify each value in the expanded IRI. In the result, & is the sole pair separator and = the sole name/value separator. Receiving applications MUST NOT treat ; as a separator. Because simple expansion percent-encodes sub-delimiters within values, every unencoded & and = in the result is structural. Receiving applications parse these parameters, whether carried in the fragment or the query component, with query-string semantics. A variable can carry multiple values. The canonical wire form repeats the name for each value (open=uri1&open=uri2). RFC 6570 simple expansion of a list ({open*}) produces comma-separated values without name repetition and is not name-bearing. Templates that need a variable to carry multiple values are encouraged to use an expansion operator whose output is name-bearing. The open, output, search, login, and proxy properties use this form.
Functional form
The fragment is a name(data) expression in the functional syntax of the XPointer Framework [XPTR-FRAMEWORK], where name identifies a scheme and the parenthesised data is defined by that scheme, nesting key=name(…) where a field is itself such an expression. In a template the (, ), =, and , are structural literals. Each field is a variable expanded within them, and simple expansion percent-encodes the characters that make the fragment ambiguous (space, =, ,, #). The selector and state properties use this form.

Receivers are encouraged to treat all invocation parameter values as untrusted input and validate or sanitise them before acting on them. A login value identifies who to authenticate as and never substitutes for authentication. open and other IRI-valued variables are untrusted IRIs to be retrieved with the user's own authorisation, with server-side receivers guarding against request forgery. Receiving applications are encouraged to accept only expected URL schemes for IRI-valued variables, for example https:, and to refuse others such as file:, data:, and javascript: before dereferencing or navigating to them. Receiving applications are encouraged to ignore variable names they do not recognise rather than treat them as errors, to treat every variable as optional, and to fail safe when a variable is absent or empty, since a Consumer may supply only the variables it recognises. Receipt of an invocation implies nothing about grants or permissions. It is a request.

Note: URI Fragment

Passing invocation parameters via the fragment identifier is a pragmatic convention rather than strict conformance with Fragment [RFC3986], which defines fragment semantics as determined by the media type of the retrieved representation. The convention is adopted here because fragment content is not included in HTTP request targets (RFC 9110), preventing the application host from learning the IRI of the resource being opened. In practice, the WHATWG HTML specification's hashchange event allows single-page applications to read fragment-encoded parameters client-side without a page reload. As noted in the Introduction, no existing specification defines a general-purpose mechanism for client-side application invocation via URI. This convention fills that gap and can be superseded by a more principled approach in future work.

Note: Cross-Origin Fetch

When a property specifies client-side fetching, e.g., open, login, in a template using the fragment form, their use is subject to the target server's Cross-Origin Resource Sharing (CORS) policy [FETCH], and fails if the target does not participate in CORS. Consumers concerned about this limit can look for a proxy among the invocation's mapped properties and supply one when available, otherwise the application handles the fetch another way.

Note: URI Query

A template can carry invocation variables in the query (?) component instead of the fragment (#) component, but the two are not equivalent. The query component is part of the data that identifies a resource (Query [RFC3986]), and it is included in the request target sent to the server (RFC 9110). Each expansion of a query-form template therefore identifies a distinct resource on the application's host, and the expanded values, including the IRI of the resource being opened, are disclosed to that host. A fragment, by contrast, identifies a secondary resource relative to the retrieved representation and is not transmitted in the request.

Applications are encouraged to use the fragment form so that invocation parameters are processed entirely client-side and, when the application is already loaded, without a further request to its host. Implementations that process invocations server-side can use the query form, accepting that the parameters become part of the request. See Threat Model for the associated disclosure.

Example: Fragment-form invocation and its expansion, opening a resource for viewing.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#invoke-open",
  "type": "UriTemplateInvocation",
  "template": "#open={open}",
  "mapping": [
    {
      "variable": "open",
      "property": "ac:open"
    }
  ]
}

Resolved against application IRI https://app.example/ with
     open = https://data.example/article :

https://app.example/#open=https%3A%2F%2Fdata.example%2Farticle
Example: Fragment-form invocation combining open and output: the Consumer selects the transform capability whose output matches the desired output value, then constructs the IRI with both variables.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#invoke-transform",
  "type": "UriTemplateInvocation",
  "template": "#open={open}&output={output}",
  "mapping": [
    { "variable": "open", "property": "ac:open" },
    { "variable": "output", "property": "ac:output" }
  ]
}

Resolved against application IRI https://app.example/ with
     open   = https://data.example/report.md
     output = text/html :

https://app.example/#open=https%3A%2F%2Fdata.example%2Freport.md&output=text%2Fhtml
Example: Functional-form invocation with a selector, opening a resource focused on the segment a Web Annotation TextQuoteSelector identifies. The selector(…) syntax is defined by [SELECTORS-STATES].
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#invoke-selector",
  "type": "UriTemplateInvocation",
  "template": "#selector(type=TextQuoteSelector,prefix={prefix},exact={exact},suffix={suffix})",
  "mapping": [
    { "variable": "prefix", "property": "oa:prefix" },
    { "variable": "exact",  "property": "oa:exact" },
    { "variable": "suffix", "property": "oa:suffix" }
  ]
}

Resolved against application IRI https://app.example/ with
     prefix = "dokieli is an "
     exact  = "open source project"
     suffix = " using open web standards." :

https://app.example/#selector(type=TextQuoteSelector,prefix=dokieli%20is%20an%20,exact=open%20source%20project,suffix=%20using%20open%20web%20standards.)
Example: Query-form invocation carrying a Media Fragments [MEDIA-FRAGS] temporal segment, opening a clip from 30 to 60 seconds. The t dimension (a start,end time in seconds) is defined by Media Fragments. The field properties are application-defined.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#invoke-clip",
  "type": "UriTemplateInvocation",
  "template": "#t={start},{end}",
  "mapping": [
    { "variable": "start", "property": "https://app.example/ns#start" },
    { "variable": "end",   "property": "https://app.example/ns#end" }
  ]
}

Resolved against application IRI https://app.example/ with
     start = 30
     end   = 60 :

https://app.example/#t=30,60

Invocation Properties

This section defines properties that give invocation variables their meaning. A template variable is a local placeholder. Its meaning comes from the property it is mapped to, whether a property defined here or an application-defined one. A Consumer resolves each variable by its property, not by its name, and can still expand the template with the variables whose property it recognises. Using a property's local name as the variable name, for example {open} for open, is a convention for readability.

The properties defined here parameterise the IRI used to invoke an application. They do not represent user-activated operations or UI events within the running application. Those are the concern of the user agent and the relevant browser specifications.

Each entry below is an invocation property, shown by its conventional variable name. The name is what you use in a template and mapping. The property it denotes is what a Consumer resolves.

open
The IRI of a resource to open. The application renders, displays, or edits the identified resource.
selector
A selector identifying a segment of the resource to focus on, as defined in [SELECTORS-STATES]. Its value is carried in functional form as selector(…), whose fields (for example oa:exact, oa:prefix, oa:suffix) become the template variables.
state
A state identifying a specific version or representation of the resource, as defined in [SELECTORS-STATES]. Its value is carried in functional form as state(…).
search
A query or search expression submitted to the application. The format and interpretation are application-defined: the value can be a freetext string, a structured query, or any other expression the application understands.
output
The media type of the desired output. Used when invoking a transform capability: its value ought to match the output declared by the selected Capability. A Consumer that wants HTML output selects the capability declaring output: text/html and passes output=text/html in the invocation IRI.
login
The IRI of a user profile (e.g. a WebID) identifying who to authenticate as. This is a hint, not authentication: the application remains responsible for authenticating the user.
proxy
The URL of a proxy through which the application is intended to route network requests. This variable has no effect on its own. When present alongside open or other variables that involve fetching a resource, the application uses the proxy URL for those requests.

Applications can use properties beyond those defined here, referenced by their own variable names, as described in Invocation Extension.

Requirement

A requirement is a resource of type Requirement that declares one environmental requirement an application has: a CSP directive the host server ought to include, or a browser permission the application can request at runtime. Where a Capability declares what an application can do, a Requirement declares what the environment needs to provide for the application to function. An application links to one or more Requirement declarations via requirement. Declaring requirements as discrete resources allows each requirement to carry its own purpose annotation and to be individually identified and referenced.

Application requirements serve two roles in this specification. As declarative self-description, they are readable by any Consumer: a catalogue ranking applications by permission footprint, a user agent presenting requirements to a user before invocation, or an authorisation agent reviewing access. As protocol input, they are delivered by a Sender to a Receiver, which reviews and acts on them by applying CSP headers or addressing declared authorisation needs. This active use is described in the Notifications section. The two roles are independent: a Consumer can read and act on declared requirements without any Sender–Receiver exchange having taken place.

Requirements are independent of the invocation mechanism: a Consumer evaluates them before invoking, whichever invocation it selects. Consumers are encouraged to ignore requirement properties they do not recognise rather than treat them as errors.

cspDirective
One or more CSP directives (CSP Level 3 syntax) that the host server ought to include with responses of resources the application creates, modifies, or opens, so that the content of those resources functions as intended for any consumer of them.
browserPermission
One or more browser permission names (Permissions API) the application can request at runtime.
hasPurpose
Links to a DPV purpose class expressing why the application needs the declared permissions, supporting transparency and informed review.
Example: A requirement declaring a CSP directive, with its purpose annotation. One declaration per requirement. The application's other CSP requirements (styles, connect) follow the same pattern.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#requirement-scripts",
  "type": "Requirement",
  "cspDirective": "script-src 'self' https://app.example/scripts/app.js",
  "hasPurpose": "dpv:ServiceProvision"
}

Note: Scope of CSP Requirements

A CSP directive governs the document it is served with. For example, an article created by the application that includes <script src="https://app.example/scripts/app.js"> depends on the script-src directive the Receiver serves with it, whichever application opens it. An embedded frame likewise depends on frame-src. Where a resource embeds the application, the application's own requirements are part of that content's needs: the embedded application depends on directives such as connect-src for the resources it reaches from within the article. The declaration can also inform a server that hosts, or is considering hosting, the application itself, where the application is the document. It does not concern resources that an application deployed at its own origin accesses through cross-origin requests: CSP served with a fetched resource has no effect on the fetching application. That interaction is governed by Cross-Origin Resource Sharing and access control.

Example: A requirement declaring a browser permission, with its purpose annotation.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#requirement-notifications",
  "type": "Requirement",
  "browserPermission": "notifications",
  "hasPurpose": "dpv:CommunicationManagement"
}

Policy

A policy is a resource of type odrl:Policy [ODRL-MODEL] an application issues about its own conduct. Where a Capability declares an affordance the application can perform, a policy declares a self-imposed constraint on exercising it. Both may use the same odrl:action terms. A self-issued permission compels no one, so an issued policy's substance is usually its prohibitions and obligations. An application links to one or more policies via issuedPolicy, as with capability and requirement.

Policies are declarations, not authorisations. A Consumer can compare an application's issued policies against policies issued by other parties, for example, a user's policies of type odrl:Preference, terms the issuer prefers but can renegotiate, discovered from the user's profile via the same issuedPolicy property, and surface discrepancies to the user before invocation, e.g., an action permitted by the application's policy but prohibited by the user's. Locating a user's profile is out of scope. How policies are matched is left to the Consumer, which may apply ODRL conflict-resolution strategies (odrl:conflict). Consumers are encouraged to ignore policy content they do not recognise rather than treat it as an error.

Note: Comparing Policies

A policy constrains only the party it binds, and a permission compels no one: an application that prohibits itself from an action a user permits simply abstains, which is not a discrepancy. A discrepancy worth surfacing is one where an action a party's policy permits is prohibited by another party's policy, for example an application permitting itself an action the user prohibits.

Note: Policies Targeting the Application

Policies whose rules target the application itself, for example terms of use of the application, are expressed with odrl:hasPolicy as defined by ODRL and are not further specified here.

Example: An application issues a policy prohibiting itself from selling data it processes.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#i",
  "issuedPolicy": {
    "id": "https://app.example/#policy-conduct",
    "type": "odrl:Policy",
    "odrl:prohibition": {
      "odrl:assignee": { "id": "https://app.example/#i" },
      "odrl:action": { "id": "odrl:sell" }
    }
  }
}

Embedded Descriptions

This section is non-normative.

The properties defined in Capability Description attach to any resource identifying an application. An application already described by another vocabulary (e.g., Web Application Manifest, Web Extensions manifest, Description of a Project, Activity Vocabulary, schema.org, Web of Things, or OAuth) can therefore carry them on its existing subject without restructuring:

Example: Capability and requirements statements on a subject described by another vocabulary.
{
  "@context": [
    "https://www.w3.org/ns/solid/oidc-context.jsonld",
    "https://www.w3.org/ns/ac.jsonld"
  ],
  "id": "https://app.example/#i",
  "client_name": "Example App",
  "capability": ["https://app.example/#capability-open"],
  "requirement": ["https://app.example/#requirement-scripts"]
}

A JSON-based format that is not JSON-LD can carry a capability description as a self-contained member under its own key, whose value is a JSON-LD object using this specification's context. Processors of the host format ignore the member, and Consumers extract and process it as JSON-LD.

Example: Capability description embedded in a Web Application Manifest.
{
  "name": "Example App",
  "start_url": "/",
  "ac": {
    "@context": "https://www.w3.org/ns/ac.jsonld",
    "id": "https://app.example/#i",
    "capability": ["https://app.example/#capability-open"],
    "requirement": ["https://app.example/#requirement-scripts"]
  }
}
Example: Capability description embedded in a Web Extension manifest.
{
  "manifest_version": 3,
  "name": "Example Extension",
  "version": "1.0",
  "ac": {
    "@context": "https://www.w3.org/ns/ac.jsonld",
    "id": "https://app.example/#i",
    "capability": ["https://app.example/#capability-open"],
    "requirement": ["https://app.example/#requirement-scripts"]
  }
}

The ac member name in the non-JSON-LD examples is illustrative: the key under which a host format carries an embedded capability description is declared by that format, not by this specification. Once the member is extracted and processed as JSON-LD, Discovery is unaffected: the application IRI remains the subject of the capability and requirement statements.

An HTML document can carry a capability description in a <script type="application/ld+json"> element, the standard mechanism for embedding JSON-LD in HTML. The element's content is a JSON-LD object using this specification's context, which a Consumer extracts and processes as JSON-LD.

Example: Capability description embedded in an HTML document as a JSON-LD script.
<script type="application/ld+json">
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#i",
  "capability": ["https://app.example/#capability-open"],
  "requirement": ["https://app.example/#requirement-scripts"]
}
</script>

Notifications

Consumers and Receivers can discover and act on a capability description entirely on their own. In addition, a Sender can proactively communicate with a Receiver about an application by delivering a notification to the Receiver's inbox. A notification of this kind expresses a request: it asks the Receiver to review information concerning an application and to act within its own authority, for example by serving the Content Security Policy headers an application requires, or by authorising an agent to access a resource.

The request notification is a general mechanism. This section describes two kinds of information a request can carry, a Requirements Review and an Access Request, but a request is not limited to these.

A Receiver that wishes to receive request notifications advertises an inbox IRI in its own resource description or in error responses (see Inbox).

Request Notification

A Sender uses a request notification to explain its needs to a Receiver. When the request concerns an application, the notification includes the application IRI, the subject of the application's capability description, which the Receiver can dereference (see Discovery). This specification does not constrain which property carries the application IRI. In the examples below it appears as object. When the request pertains to particular resources, the notification includes their IRIs. A request can include or reference one or more objects describing what is requested. This specification does not constrain the vocabulary of those objects.

Example: A request notification. The actor makes the request, the object identifies the application, and the target identifies the resource concerned. Objects describing what is requested vary by the kind of request. See Requirements Review and Access Request.
{
  "@context": [
    "https://www.w3.org/ns/activitystreams",
    "https://www.w3.org/ns/ac.jsonld"
  ],
  "type": "Request",
  "actor": "https://agent.example/#i",
  "object": "https://app.example/#i",
  "target": "https://example.org/article"
}

Note: Protecting the Inbox

Access control on the inbox, sender authentication, payload constraints, and abuse mitigation are orthogonal to this interaction and are handled by the underlying notification and access control mechanisms (see Security Considerations).

The Receiver's response to a delivery concerns the notification itself: accepting the HTTP request creates the notification in the inbox, independently of any decision about its contents. The Receiver then reviews the stored request, by operator decision or by automated policy, and records the outcome. The Receiver is encouraged to deliver a notification indicating the outcome to an inbox associated with the request: the inbox stated in the request notification if any, otherwise the inbox in the application's capability description. The outcome notification identifies the request notification so that the two can be correlated.

Example: Outcome notification. The object references the request notification resource created in the Receiver's inbox. Accept or Reject indicates the outcome.
{
  "@context": [
    "https://www.w3.org/ns/activitystreams",
    "https://www.w3.org/ns/ac.jsonld"
  ],
  "type": "Accept",
  "actor": "https://example.org/#i",
  "object": "https://example.org/inbox/d3aa37",
  "target": "https://example.org/article",
  "summary": "Requested access modes granted."
}

Requirements Review

An application embedded in or injected into an arbitrary HTML document depends on the server hosting that document to issue appropriate Content Security Policy (CSP) headers. Without server cooperation, the browser can block scripts, fetches, or other operations the application requires in order to function. A request can ask a Receiver to review the requirements declared in an application's capability description and act on them, for example by including approved CSP directives in responses served in the context of that application.

A Sender publishes a capability description in which the application links to one or more Requirement declarations via requirement. The Receiver obtains the application IRI, whether at registration time, during policy setup, on first encounter with the application, or from a Request Notification, dereferences the capability description, and reviews the declared requirements as described in Request Notification. A review covers only the requirements the Receiver recognises. When serving responses in the context of that application, the Receiver includes CSP headers reflecting the approved requirements.

Example: A capability description declaring CSP requirements, and a server response reflecting the approved requirements in responses served in the context of the application.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#i",
  "type": "ac:Application",
  "inbox": "https://app.example/inbox/",
  "requirement": [
    {
      "id": "https://app.example/#requirement-scripts",
      "type": "Requirement",
      "cspDirective": "script-src 'self' https://app.example/scripts/app.js",
      "hasPurpose": "dpv:ServiceProvision"
    },
    {
      "id": "https://app.example/#requirement-connect",
      "type": "Requirement",
      "cspDirective": "connect-src 'self' https:"
    }
  ]
}
HTTP/1.1 200 OK
Content-Type: text/html
Content-Security-Policy: script-src 'self' https://app.example/scripts/app.js;
                         connect-src 'self' https:

Access Request

A request can express that an agent seeks access to a resource. An access request identifies the agent for whom access is requested, the resource or resources concerned, and the operations desired. This specification does not require a particular authorisation or policy vocabulary for expressing the requested access. The Receiver evaluates the request and enacts the outcome through its own access control mechanism. The representation and enforcement of any resulting authorisation, and the review process itself, are outside the scope of this specification.

A common flow, continuing from Error Response Inbox Discovery: an agent using an application attempts an operation on a resource, receives a 403 response advertising an inbox, and delivers an access request to that inbox describing the access it needs. The review is decoupled from the inbox itself: any application authorised to act on the Receiver's behalf can process stored access requests and enact outcomes.

Example: Access request whose object expresses the desired authorisation using Web Access Control.
{
  "@context": [
    "https://www.w3.org/ns/activitystreams",
    "https://www.w3.org/ns/ac.jsonld",
    { "acl": "http://www.w3.org/ns/auth/acl#" }
  ],
  "type": "Request",
  "actor": "https://agent.example/#i",
  "target": "https://example.org/article",
  "object": {
    "type": "acl:Authorization",
    "acl:agent": { "id": "https://agent.example/#i" },
    "acl:accessTo": { "id": "https://example.org/article" },
    "acl:mode": [ { "id": "acl:Read" }, { "id": "acl:Write" } ]
  }
}
Example: Access request expressed as an ODRL Request policy. The purpose constraint uses the same DPV purposes as the application's requirement declarations.
{
  "@context": "http://www.w3.org/ns/odrl.jsonld",
  "type": "Request",
  "uid": "https://app.example/requests/e3b7",
  "permission": [{
    "assignee": "https://agent.example/#i",
    "target": "https://example.org/article",
    "action": ["read", "modify"],
    "constraint": [{
      "leftOperand": "purpose",
      "operator": "eq",
      "rightOperand": "https://w3id.org/dpv#ServiceProvision"
    }]
  }]
}

Inbox

An inbox is a resource to which notifications are delivered [LDN]. A target resource advertises its inbox, in the Link header and/or as an ldp:inbox relation in its body, and senders and consumers discover it from the target.

Both an application and a Receiver advertise inboxes, for opposite directions of the same exchange:

  • An application advertises an inbox in its capability description, through the inbox property, so that it can receive feedback about its requests, such as the outcome of a Requirements Review.
  • A Receiver advertises an inbox on a target resource it controls, in the resource's own description or in an error response, so that it can learn what an application needs from it.
Inbox Discovery

Senders and consumers MUST discover the target's inbox as follows, in order [LDN]:

  1. from the Link header with a rel value of http://www.w3.org/ns/ldp#inbox
  2. if none is found there, from the response body parsed as JSON-LD [JSON-LD11], where an http://www.w3.org/ns/ldp#inbox relation has the target as subject and the inbox IRI as object.

The Sender then delivers a notification to the inbox, conveying information about its application, including the application IRI. Receipt does not oblige the Receiver to act. A Consumer acting on the Receiver's behalf can dereference the capability description from that IRI to verify it, then the Receiver follows the review process described in Request Notification.

A Consumer that has obtained a Sender's capability description, whether directly from the Sender's IRI or via a Receiver, can use it to prepare invocations independently of whether the Sender–Receiver interaction has taken place.

Error Response Inbox Discovery

A client error response is a useful place to advertise an inbox: when a Receiver rejects a request with a 4xx, advertising an inbox in the response lets the requester follow up rather than being left without recourse. For example, an agent denied access can discover the inbox and deliver an Access Request for the access it needs, or convey its application's requirements for a Requirements Review (see Request Notification).

Example: 403 response advertising an inbox. The Sender discovers the inbox and delivers a notification referencing its capability description.
PUT /article HTTP/1.1
Host: example.org
Content-Type: text/html;charset=utf-8

HTTP/1.1 403 Forbidden
Link: <https://example.org/inbox/>; rel="http://www.w3.org/ns/ldp#inbox"

Consuming Notifications

A Consumer can read and process the notifications an inbox holds, rather than deliver them. It discovers the inbox as in Inbox Discovery, then retrieves the inbox to obtain the notifications it contains and retrieves each in turn, as in [LDN]. For example, a Consumer acting on a Receiver's behalf reviews an application's needs from the collected request notifications and acts within the Receiver's authority (see Requirements Review and Access Request).

Extensions

Extensions incorporate additional features beyond what is defined in this specification. Extensions MUST NOT contradict nor cause the non-conformance of functionality defined in this specification.

Invocation Extension

This section is non-normative.

Applications can use properties beyond those defined in Invocation Properties by declaring a mapping that pairs a template variable with the property that defines its meaning. Consumers that do not recognise a property still expand the template with the variables whose property they do recognise, and receiving applications treat extension values as untrusted input, per the receiver rules in URI Template Invocation.

The following properties illustrate invocation extensions:

diff
The IRI of a resource to compare. It is supplied twice, as the original version then the changed version, and the application renders their difference.
graph
The IRI of an RDF dataset or named graph to load and render.
style
The IRI of a stylesheet to apply when rendering the resource.
view
An application-defined value encoding the UI view in which to open the application, such as which panels are active or the current mode. The encoding and interpretation of this variable are not further specified.
Example: An extension variable declared via an explicit mapping. The application defines the property that gives the variable its semantics. Consumers that recognise the property can supply a value, and receiving applications treat it as untrusted input like any other variable.
{
  "@context": "https://www.w3.org/ns/ac.jsonld",
  "id": "https://app.example/#invoke-graph",
  "type": "UriTemplateInvocation",
  "template": "#graph={graph}",
  "mapping": [
    {
      "variable": "graph",
      "property": "https://vocab.example/graph"
    }
  ]
}

Requirement Extension

This section is non-normative.

Applications can state environmental needs beyond those defined in Requirement by including properties from other vocabularies.

Considerations

This section details application considerations, security and privacy considerations, a threat model, a security and privacy review, a societal impact review, and accessibility and internationalization considerations.

Some of the normative references with this specification point to documents with a Living Standard or Draft status, meaning their contents can still change over time. It is advised to monitor these documents, as such changes might have implications.

Application Considerations

This section is non-normative.

Senders are strongly encouraged to declare their permission needs accurately and completely. Understating requirements in order to gain access, or overstating them to acquire unnecessary capabilities, undermines the trust model on which this specification relies.

Senders are encouraged to use permissions granted by a Receiver exclusively in the interests of the user on whose behalf those permissions were granted, consistent with the declared purpose expressed via hasPurpose in the capability description.

Senders are encouraged to maintain stability in the URI Templates declared in their capability descriptions, since Consumers and catalogues can cache and rely on these patterns. Where changes are necessary, Senders could provide a transition period during which both the old and new patterns remain functional.

Security Considerations

This section is non-normative.

Capability descriptions are strongly encouraged to be published at a location controlled by the application they identify, so that Consumers and Receivers can rely on the serving IRI as a trust anchor.

An application is identified by its IRI, so the same software deployed at different origins constitutes distinct applications. Each publishes its own capability description at its own origin and is trusted on that basis. There is no cross-origin identity by which one deployment could be trusted on the basis of another.

Privacy Considerations

This section is non-normative.

Privacy is one of the ethical values that underpin the web. To empower people with needs to have strong privacy protections with respect to information flows, implementers as well as developers of specifications are encouraged to consider privacy-related design choices as per W3C Privacy Principles [PRIVACY-PRINCIPLES].

Applications that use the fragment (#) form for invocation parameters, as described in this specification, are encouraged to document this choice explicitly, noting that fragment content is not included in the HTTP request target and so is not disclosed to the application's host through the request. It can still reach others by other paths: script in the loaded application can read it (for example via location.hash), a redirect's Location can inherit it (RFC 9110), and it persists in history, bookmarks, and shared URLs.

Senders are encouraged to apply the principle of data minimisation when publishing capability descriptions, disclosing only the information necessary for discovery, invocation, and policy review by Consumers and Receivers.

An invocation whose observable outcome depends on content that the party supplying a value cannot otherwise read can act as an oracle: by supplying candidate values and observing the result, that party infers the content. Applications are encouraged to limit what an invocation's outcome reveals, noting that the outcome can reach the supplier through side channels such as timing, observable effects, or a browsing context the supplier retains, and not only through a deliberate response. See the Threat Model.

Threat Model

This section is non-normative.

This threat analysis follows the framework of the W3C Threat Model for the Web [THREAT-MODEL-WEB] and draws on terminology from the Privacy Principles. Security Threats are classified by a STRIDE threat type and Privacy Threats by a LINDDUN threat type. Each is assigned a risk level from the RISK Extension to DPV taxonomy [DPV-RISK].

Security Threats and Mitigations
Feature Threat STRIDE type Threat-model element Risk level Mitigation
#discovery Description substitution. An attacker at another origin serves a capability description that claims to represent a Sender it is not, so Consumers or Receivers act on a fraudulent description. Spoofing B1 Web Origin Boundary High Consumers and Receivers are strongly encouraged to accept a description only when its serving IRI matches the Sender's declared identity, which is the trust anchor rather than the metadata.
#discovery Description tampering. A network attacker alters a description in transit to widen its declared CSP directives or permissions. Tampering B2 Network Boundary High Consumers and Receivers are strongly encouraged to fetch descriptions only over HTTPS.
#discovery Stale description. A Consumer or Receiver acts on a cached description that no longer matches the Sender's current requirements. Tampering B3 Browser State Boundary Moderate Receivers are encouraged to apply HTTP caching, re-fetch before acting, and treat an expired description as needing re-verification.
#capability-description Application impersonation. A malicious application copies another application's name, description, or homepage to gain unearned trust. Spoofing B1 Web Origin Boundary High Receivers and Consumers are strongly encouraged to judge an application by its serving origin, not its metadata.
#capability-description Statement injection. A description merged into a shared store adds statements about other subjects and changes unrelated behaviour. Tampering B1 Web Origin Boundary Moderate Consumers and Receivers are encouraged to isolate a processed description or accept only statements about its declared IRI.
#uri-template-invocation Open redirect via invocation. A server-side application that receives invocation parameters in the query component becomes an open redirect when an invocation value such as open is an unvalidated redirect target. Spoofing B1 Web Origin Boundary High Receiving applications are strongly encouraged to validate invocation values before using them as redirect or navigation targets, and to restrict targets to expected origins.
#uri-template-invocation, #invocation-extension Server-side request forgery via invocation. A server-side application that fetches the resource named by open or another IRI value can be aimed at private or internal addresses. Information disclosure B1.8 Local Network Boundary High Receiving applications are strongly encouraged to validate invocation IRIs and deny private and internal addresses before fetching.
#uri-template-invocation, #invocation-extension Invocation parameter injection. A hostile party supplies invocation values, such as a forged login or a script-bearing stylesheet IRI, that a receiver processes without validation. Tampering B1 Web Origin Boundary High Receiving applications are strongly encouraged to treat all invocation values as untrusted input and validate them before use.
#invocation-properties Proxy interception via invocation. A hostile proxy value routes the receiving application's outbound requests through an attacker-controlled server, exposing the content and any credentials of the resources it fetches, or aiming those requests at private or internal addresses. Information disclosure B2 Network Boundary High Receiving applications are strongly encouraged to treat proxy as untrusted, to route requests through it only with explicit user awareness, and to restrict it to origins the user or application already trusts.
#requirement Permission inflation. A Sender declares broader CSP directives, permissions, or access than its function needs. Elevation of privilege B1 Web Origin Boundary Moderate Senders are strongly encouraged to declare only the permissions their function needs, and Receivers to treat declarations as input to review rather than automatic grants.
#policy Policy misrepresentation. A Sender issues policies it does not follow, so a favourable comparison grants unearned trust. Spoofing B1 Web Origin Boundary Moderate Consumers are strongly encouraged to present policy comparison as input to a user decision, not as assurance of conduct.
#policy Policy change after reliance. A Sender issues agreeable policies, then narrows them after users or Receivers have relied on the earlier version. Tampering B1 Web Origin Boundary Moderate Consumers are encouraged to re-fetch and re-compare policies rather than act on a cached comparison.
#notifications Post-approval behavior change. A Sender shows minimal declarations during review, then changes the application to exploit the approved access. Elevation of privilege B1 Web Origin Boundary Moderate Receivers are encouraged to re-fetch and re-review periodically, and to treat any change in declared requirements as needing renewed review.
#notifications Inbox flooding. An advertised inbox invites bulk or junk notifications that exhaust storage or the review process. Denial of service B2 Network Boundary Moderate Receivers are encouraged to require authenticated senders, apply access control and rate limits, validate payloads, or use short-lived inboxes.
#requirements-review CSP allowlist scope creep. CSP directives approved for one application are broad enough to benefit others on the host or to enable cross-site scripting. Elevation of privilege B1 Web Origin Boundary Moderate Receivers are encouraged to evaluate approved directives against the whole host document and to prefer narrow source expressions.
#error-response-inbox-discovery Inbox forgery. A Sender names a third party's inbox as the Receiver's, or an attacker forges approval notifications. Spoofing B1 Web Origin Boundary Moderate Consumers and Receivers are encouraged to discover an inbox only from the Receiver's own responses, and to verify high-stakes approvals out of band.
Privacy Threats and Mitigations
Feature Threat LINDDUN type Threat-model element Risk level Mitigation
#discovery Capability description fetch as tracking. A server that hosts its capability description can log who fetches it, when Consumers need to use the description or to verify an application IRI received in a Request Notification. These fetches can let the host identify who is using the description and correlate repeated fetches to track them. Linking, Detecting B1 Web Origin Boundary Low Consumers are encouraged to fetch without credentials and with minimal headers, and application hosts to minimise the logging and retention of fetch metadata.
#uri-template-invocation Invocation IRI disclosure. A template that carries invocation parameters in the query component sends the target resource IRI to the application's host, which can reveal personal data or browsing behaviour. Data Disclosure B1 Web Origin Boundary Moderate Senders are encouraged to carry invocation parameters in the fragment component, and to document the disclosure when the query component is used.
#uri-template-invocation User identification via invocation. An invocation value can identify the user directly, for example a login profile IRI. Even without such a value, a host that receives invocations can correlate repeated ones to single out the same user. Identifying B1 Web Origin Boundary Moderate Consumers are encouraged to supply identifying values such as login only when needed, and Receivers not to retain or correlate them beyond the invoked function.
#uri-template-invocation Unawareness of invocation disclosure. A user may not know that an invocation discloses information, such as parameters placed in the query component being sent to the host, and cannot intervene. Unawareness & Unintervenability B0 User Agent Boundary Moderate Consumers are encouraged to show what an invocation discloses, and to whom, before acting, and to prefer carrying parameters in the fragment component.
#uri-template-invocation Invocation outcome as oracle. When the observable outcome of an invocation depends on content the supplier of a value cannot otherwise read, for example whether a selector or search value matches within a resource opened under the user's authorisation, the supplier can infer that content by varying the value and observing the result. The outcome can reach the supplier through side channels such as timing, observable effects, or a retained browsing context, without the application intending to disclose it. Detecting B1 Web Origin Boundary Low Applications are encouraged to limit the granularity of value-dependent matching and to reduce observable differences between a match and a miss, so that an outcome does not reveal content to the party that supplied the value.
#requirement Purpose mismatch. A Sender uses granted permissions for purposes other than its declared hasPurpose, such as profiling. Non-compliance B1 Web Origin Boundary Moderate Senders are encouraged to declare each purpose via hasPurpose, and Receivers to grant only for the declared purposes and treat use beyond them as non-compliance.
#notifications Non-repudiable request records. Delivering a notification records the requester's application IRI, which can remove deniability that a request was made. Non-repudiation B1 Web Origin Boundary Low Senders are encouraged to convey only the identity the Receiver needs, and Receivers to retain records only as long as needed.

Security and Privacy Review

This section is non-normative.

These questions provide an overview of security and privacy considerations for this specification as guided by [SECURITY-PRIVACY-QUESTIONNAIRE].

What information does this feature expose, and for what purposes?
Capability descriptions are public and advertise an application's capabilities, invocation templates, and inbox so Consumers can discover and invoke them. An invocation IRI exposes the variables a Consumer supplies, such as the resource to open, to the receiving application. See the Threat Model.
Do features in your specification expose the minimum amount of information necessary to implement the intended functionality?
Yes. An invocation carries only the variables a Consumer chooses to supply, and the fragment form keeps them from the application's host.
Do the features in your specification expose personal information, personally-identifiable information (PII), or information derived from either?
Not inherently. Variables such as login or open can reference a person or their resources. These are supplied by the Consumer and retrieved under the user's own authorization.
How do the features in your specification deal with sensitive information?
The features do not require sensitive information. Receivers treat any values a Consumer supplies as untrusted input.
Does data exposed by your specification carry related but distinct information that may not be obvious to users?
An invocation IRI can reveal the resource being opened, and in the query form disclose it to the application's host. See the Threat Model.
Do the features in your specification introduce state that persists across browsing sessions?
No.
Do the features in your specification expose information about the underlying platform to origins?
No.
Does this specification allow an origin to send data to the underlying platform?
No.
Do features in this specification enable access to device sensors?
No.
Do features in this specification enable new script execution/loading mechanisms?
No. This specification defines no script execution or loading mechanism. Invocation values are data, treated as untrusted input and validated or sanitised before use.
Do features in this specification allow an origin to access other devices?
No.
Do features in this specification allow an origin some measure of control over a user agent's native UI?
No.
What temporary identifiers do the features in this specification create or expose to the web?
None.
How does this specification distinguish between behavior in first-party and third-party contexts?
It does not distinguish them. An invocation can come from any party, receipt implies no grant, and receivers treat all values as untrusted.
How do the features in this specification work in the context of a browser's Private Browsing or Incognito mode?
No difference. The features introduce no persistent state.
Does this specification have both "Security Considerations" and "Privacy Considerations" sections?
Yes. See Security Considerations, Privacy Considerations, and the Threat Model.
Do features in your specification enable origins to downgrade default security protections?
No. Cross-origin fetching of an invocation target remains subject to CORS [FETCH].
What happens when a document that uses your feature is kept alive in BFCache (instead of getting destroyed) after navigation, and potentially gets reused on future navigations back to the document?
Not applicable.
What happens when a document that uses your feature gets disconnected?
Not applicable.
Does your spec define when and how new kinds of errors should be raised?
No new error types. Receivers are encouraged to fail safe and ignore variables they do not recognise.
Does your feature allow sites to learn about the user's use of assistive technology?
No.
What should this questionnaire have asked?
¯\_(ツ)_/¯

Societal Impact Review

This section is non-normative.

These questions provide an overview of ethical considerations and societal impact as guided by [SOCIETAL-IMPACT-QUESTIONNAIRE].

What kinds of activities do you anticipate your specification becoming a critical part of?
Discovering and choosing applications to act on resources: opening, editing, annotating, transforming, and searching. It can become part of how documents and applications interoperate without prior coordination.
What kinds of activities could your specification become a part of that you are not designing for?
Harvesting capability descriptions to profile applications and their operators, and automated agents invoking applications at scale.
Have you considered whether your use cases are sufficiently diverse?
The use cases centre on document-centric applications. Capabilities for other classes, such as media or non-visual agents, are currently expressible through the extension mechanism. As they become better understood, they can inform the core.
What risks do you see in features of your specification being misused, or used differently from how you intended?
An application can misrepresent its capabilities to attract invocations, and invocation IRIs can be crafted to direct a user or application to attacker-chosen resources. See the Threat Model.
Can users of the Web Platform choose not to use features of your specification?
Yes. Applications work without declaring capabilities, and Consumers can ignore declarations. Receipt of an invocation implies nothing, and a Receiver can ignore it.
What groups of people are excluded from using features of your specification?
Publishing a capability description requires an IRI and web hosting, so those without access to hosting depend on providers. Human-readable names and descriptions are only as multilingual as their publishers make them.
What effect may features of your specification have on minority groups?
Any application can describe its capabilities on equal terms, and discovery does not privilege incumbents. Catalogues built on top of these descriptions can introduce their own selection biases.
How might features of your specification affect individuals' psychological well-being, including stress, social interactions, or susceptibility to compulsive use?
No direct effect is anticipated. Notifications to capability inboxes could be a vector for unwanted contact. See Threat Model mitigations on inbox flooding.
What are the power dynamics at play in implementations of your specification?
Publishers control what they claim, Consumers control what they trust and invoke, and Receivers retain authority over what an invocation does. No party needs permission from a platform or registry to participate.
What points of centralization does your feature bring to the web platform?
None required. Descriptions are self-published and discovered from the resources themselves or via notifications. Catalogues can emerge as aggregation points but are optional.
How does your new technology open up ways in which people might be surveilled?
Query-form invocations disclose the target resource to the application's host, and inboxes observe who sends notifications. The fragment form and the Threat Model mitigations limit this.
To what extent do the features in your specification impact the natural environment?
Minimal. Capability descriptions are small documents, and fragment-form invocation is processed client-side without additional requests to the application's host.
What is the expected lifetime of your specification feature(s)?
The features build on stable web technologies (HTTP, IRI), and the extension mechanism allows evolution without breaking deployed descriptions.
Have you completed the Security & Privacy Self-review Questionnaire?
Yes. See Security and Privacy Review.

Accessibility Considerations

This section is non-normative.

Internationalization Considerations

This section is non-normative.

Changelog

Acknowledgements

The Community Group gratefully acknowledges the work that led to the creation of this specification, and extends sincere appreciation to those individuals that worked on technologies and specifications that deeply influenced our work.

The Community Group would like to thank the following individuals for their useful comments, both large and small, that have led to changes to this specification over the years:

  • elf Pavlik
  • JG10
  • Marcos Caceres
  • Michael Peters
  • Sarven Capadisli
  • Virginia Balseiro

References

Normative References

[ACTIVITYSTREAMS-VOCABULARY]
Activity Vocabulary. James Snell; Evan Prodromou. W3C. 23 May 2017. W3C Recommendation. URL: https://www.w3.org/TR/activitystreams-vocabulary/
[ANNOTATION-VOCAB]
Web Annotation Vocabulary. Robert Sanderson; Paolo Ciccarese; Benjamin Young. W3C. 23 February 2017. W3C Recommendation. URL: https://www.w3.org/TR/annotation-vocab/
[DC-TERMS]
DCMI Metadata Terms. DCMI Usage Board. DCMI. 20 January 2020. DCMI Recommendation. URL: http://dublincore.org/specifications/dublin-core/dcmi-terms/2020-01-20/
[DPV]
Data Privacy Vocabulary (DPV). Harshvardhan J. Pandit; Beatriz Esteves; Georg P. Krog. W3C Data Privacy Vocabularies and Controls Community Group. 25 February 2026. Final Community Group Report. URL: https://w3id.org/dpv
[HYDRA]
Hydra Core Vocabulary. Markus Lanthaler. W3C Hydra Community Group. Unofficial Draft. URL: https://www.hydra-cg.com/spec/latest/core/
[IANA-MEDIA-TYPES]
Media Types. IANA. URL: https://www.iana.org/assignments/media-types/
[JSON-LD11]
JSON-LD 1.1. Gregg Kellogg; Pierre-Antoine Champin; Dave Longley. W3C. 16 July 2020. W3C Recommendation. URL: https://www.w3.org/TR/json-ld11/
[LDN]
Linked Data Notifications. Sarven Capadisli; Amy Guy. W3C. 2 May 2017. W3C Recommendation. URL: https://www.w3.org/TR/ldn/
[LDP]
Linked Data Platform 1.0. Steve Speicher; John Arwe; Ashok Malhotra. W3C. 26 February 2015. W3C Recommendation. URL: https://www.w3.org/TR/ldp/
[ODRL-MODEL]
ODRL Information Model 2.2. Renato Iannella; Serena Villata. W3C. 15 February 2018. W3C Recommendation. URL: https://www.w3.org/TR/odrl-model/
[ODRL-VOCAB]
ODRL Vocabulary & Expression 2.2. Renato Iannella; Michael Steidl; Stuart Myles; Víctor Rodríguez-Doncel. W3C. 15 February 2018. W3C Recommendation. URL: https://www.w3.org/TR/odrl-vocab/
[RDF-SCHEMA]
RDF Schema 1.1. Dan Brickley; Ramanathan Guha. W3C. 25 February 2014. W3C Recommendation. URL: https://www.w3.org/TR/rdf-schema/
[RFC2119]
Key words for use in RFCs to Indicate Requirement Levels. S. Bradner. IETF. March 1997. Best Current Practice. URL: https://datatracker.ietf.org/doc/html/rfc2119
[RFC3986]
Uniform Resource Identifier (URI): Generic Syntax. T. Berners-Lee; R. Fielding; L. Masinter. IETF. January 2005. Internet Standard. URL: https://datatracker.ietf.org/doc/html/rfc3986
[RFC3987]
Internationalized Resource Identifiers (IRIs). M. Duerst; M. Suignard. IETF. January 2005. Proposed Standard. URL: https://www.rfc-editor.org/info/rfc3987
[RFC6570]
URI Template. J. Gregorio; R. Fielding; M. Hadley; M. Nottingham; D. Orchard. IETF. March 2012. Proposed Standard. URL: https://www.rfc-editor.org/info/rfc6570
[RFC8174]
Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words. B. Leiba. IETF. May 2017. Best Current Practice. URL: https://www.rfc-editor.org/info/rfc8174
[SELECTORS-STATES]
Selectors and States. Ivan Herman; Robert Sanderson; Paolo Ciccarese; Benjamin Young. W3C. 23 February 2017. W3C Working Group Note. URL: https://www.w3.org/TR/selectors-states/
[XPTR-FRAMEWORK]
XPointer Framework. Paul Grosso; Eve Maler; Jonathan Marsh; Norman Walsh. W3C. 25 March 2003. W3C Recommendation. URL: https://www.w3.org/TR/xptr-framework/

Informative References

[DPV-RISK]
Risk Extension. Harshvardhan J. Pandit. W3C Data Privacy Vocabularies and Controls Community Group. 25 February 2026. Final Community Group Report. URL: https://w3id.org/dpv/risk
[FETCH]
Fetch Standard. Anne van Kesteren. WHATWG. Living Standard. URL: https://fetch.spec.whatwg.org/
[MEDIA-FRAGS]
Media Fragments URI 1.0 (basic). Raphaël Troncy; Erik Mannens; Silvia Pfeiffer; Davy Van Deursen. W3C. 25 September 2012. W3C Recommendation. URL: https://www.w3.org/TR/media-frags/
[PRIVACY-PRINCIPLES]
Privacy Principles. Robin Berjon; Jeffrey Yasskin. W3C. 15 May 2025. W3C Statement. URL: https://www.w3.org/TR/privacy-principles/
[SECURITY-PRIVACY-QUESTIONNAIRE]
Self-Review Questionnaire: Security and Privacy. Theresa O'Connor; Peter Snyder. W3C. 18 April 2025. W3C Group Note. URL: https://www.w3.org/TR/security-privacy-questionnaire/
[SOCIETAL-IMPACT-QUESTIONNAIRE]
Self-Review Questionnaire: Societal Impact. Sarven Capadisli; Lola Odelola. W3C. 19 March 2026. W3C Group Draft Note. URL: https://www.w3.org/TR/societal-impact-questionnaire/
[THREAT-MODEL-WEB]
Threat Model for the Web. Simone Onofri; Joe Andrieu; Giovanni Corti. W3C. 21 July 2026. W3C Group Note Draft. URL: https://www.w3.org/TR/threat-model-web/