This document specifies RDF Protocol Documents, an extension to the
Agent2Agent (A2A) protocol [[A2A]] defined through A2A's own extension mechanism
(specification §4.6) — no changes to core A2A are proposed. Two agents that interact
repeatedly negotiate once in natural language, then crystallise the routine into a
Protocol Document: a content-addressed (hash-pinned) RDF document whose body
is a SHACL shape [[shacl]]. Thereafter every exchange under that protocol is a
SHACL-validated RDF graph carried in ordinary A2A message Parts —
machine-checkable, vocabulary-grounded, and requiring no LLM inference on the hot path.
The extension defines the extension URI and Agent Card declaration, the upgrade handshake
(including a fail-closed no-silent-downgrade rule for security-bearing exchanges),
the message-content binding for handshake, intent, and response payloads, and how an intent
composes with ODRL policies [[odrl-model]] and Agent Authorization Credentials
[[AGENT-AUTHZ]] for the authorization story. The design follows the hash-pinned
protocol-document result of AGORA [[AGORA]], made RDF/SHACL-native.
This is an unofficial draft prepared as a candidate proposal to the Linux
Foundation A2A project under its extension governance process [[A2A-GOVERNANCE]]. It has
not been submitted to, discussed with, or endorsed by the A2A project; per
that process, submission is a proposal issue on a2aproject/A2A, which only the
editor (not an automated agent) will open. Until the proposal is sponsored, the extension URI
lives under the editor's w3id.org/jeswr namespace; if the extension is adopted
into the A2A organization, a successor URI under
https://a2a-protocol.org/extensions/ would supersede it (see
).
This draft was AI-assisted (drafted by Claude Fable 5 against the A2A v1.0.0 specification,
the A2A extensions topic guide, and the @jeswr/solid-a2a reference codec) and
awaits review by its human editor. The implementation-status inventory in
was verified against the named repositories on
2026-07-03.
A2A [[A2A]] gives heterogeneous agents a common envelope: discovery via Agent Cards, tasks,
and messages whose Parts carry text, files, or structured data. The natural-language
parts maximise reach — any two LLM-backed agents can talk — but they carry two standing
costs. First, inference cost and nondeterminism: two agents that perform the same
routine exchange thousands of times pay LLM inference, latency, and a nonzero
misinterpretation risk on every round. Second, opacity: an enterprise that must
audit or policy-check agent traffic has only prose to parse.
AGORA [[AGORA]] showed that networks of LLM agents scale when routine exchanges crystallise into protocol documents: negotiated once in natural language, pinned by a cryptographic hash, and executed deterministically thereafter. This extension carries that result one step further by making the protocol document's body a SHACL shape [[shacl]] over an RDF data model [[rdf11-concepts]]: post-handshake payloads are not merely "the JSON we agreed on" but schema-validated, vocabulary-grounded Linked Data. That buys:
The extension is deliberately shaped to A2A's published extension mechanics: it is a
profile-style extension in the taxonomy of [[A2A-EXTENSIONS]] (it overlays structure
on core messages), defines no new RPC methods, adds no task states, and modifies no core data
structure — all payloads ride in the existing Part content fields, all custom
per-part attributes live in Part.metadata, and per-message tagging uses the
core Message.extensions field, exactly as §4.6 of [[A2A]] provides. Related
prior discussion in the A2A tracker: .
This extension is the L5 (agent-communication) protocol piece of the accountable-agent
architecture mapped in [[AGENTIC-SOLID-NOTE]]. It composes with — and deliberately
does not restate — the ODRL Agent-Delegation Profile [[ODRL-DELEGATION]] (delegation-chain
semantics, fail-closed policy evaluation) and Agent Authorization Credentials
[[AGENT-AUTHZ]] (per-hop Verifiable Credentials over those policies). The
@jeswr/solid-a2a library [[SOLID-A2A-IMPL]] is the reference codec for the
handshake and payload formats defined here; @jeswr/solid-agent-card
[[SOLID-AGENT-CARD-IMPL]] is the reference producer of the Agent Card declaration.
Linked Web Storage (JLWS). A JLWS storage ([[JLWS-CORE]]) is a natural
substrate for this extension's documents: Protocol Documents, ODRL policies, credential
chains, and PROV traces are ordinary JLWS data resources under ordinary JLWS
authorization — the storage server never speaks this extension. Three properties of that
substrate matter here. (1) Hash stability across representations: the
protocol hash is computed over the RDFC-1.0 canonicalization of the parsed
graph (), not over bytes — so a PD stored as Turtle
and served as JSON-LD under JLWS's advertised ContentNegotiation capability
([[JLWS-RDF-TRANSFORM]] Transformation semantics: the derived representation is
graph-isomorphic to the authoritative one) pins identically in either representation.
(2) Discovery: a storage whose controller operates an A2A agent MAY advertise
it with the extension service entry
https://w3id.org/jeswr/a2a-rdf/v1#AgentInteractionService
— this document hereby defines that term (the fragment resolves here): serviceEndpoint is the agent's A2A Agent Card
URL (the card, not the A2A endpoint; the card carries the endpoint and the
capabilities.extensions declaration per ), and
conformsTo asserts that the agent declares this extension's URI — in its
storage description, using [[JLWS-CORE]]'s extension-service mechanism (Capability
registry: extension services use absolute URIs; unknown types are ignored).
(3) Downgrade resistance is independent of the storage's authentication
posture: the hash — not the host, its TLS, or its token-presentation mode — is the
trust anchor (), so whether the PD's storage authenticates
readers under JLWS's Bearer baseline or a negotiated proof-of-possession profile
([[JLWS-CORE]] Proof-of-possession profiles), a fetched PD that misses its pin
MUST be rejected and the exchange treated as never upgraded; and a consuming client that
cannot retrieve or verify a pinned PD declines the offer, where the no-silent-downgrade
rule () still forbids natural-language fallback for a
required (security-bearing) exchange. None of these adds a requirement
to A2A agents or to JLWS servers; the composition detail is recorded in
docs/lws-alignment.md.
Two conformance classes are defined. An offering agent is an A2A agent (server role) that declares this extension in its Agent Card and accepts protocol-document exchanges. A consuming client is an A2A client that activates this extension and sends protocol-document exchanges. A single implementation frequently plays both roles; the requirements below name the role they bind.
a2a:ProtocolDocument, whose body is
one SHACL request shape (and optionally one response shape) plus Dublin Core metadata. Its
identity for pinning purposes is its protocol hash, not its IRI.sha256: followed by the lowercase hexadecimal SHA-256 digest of
the canonical N-Quads form of the Protocol Document's full graph (see
).a2a:Intent, expressing a requested action; under an
active protocol it MUST conform to the pinned Protocol Document's request shape.
The a2a: RDF namespace predates this extension (it is the
@jeswr/solid-a2a vocabulary) and is distinct from the
extension URI. The prefix collision with the A2A protocol's own name is unfortunate but
contained: the namespace never appears in A2A envelope fields, only inside RDF payloads.
The extension is identified by the URI:
https://w3id.org/jeswr/a2a-rdf/v1
Per §4.6.3 of [[A2A]], the version is carried in the URI; a breaking change to this
specification MUST mint a new URI (…/v2). This URI is the value used in
AgentCard.capabilities.extensions[].uri, in the A2A-Extensions
service parameter, and in Message.extensions /
Artifact.extensions arrays. It is an identifier first; the w3id redirect to
this document is pending (interim location:
https://github.com/jeswr/a2a-rdf-extension).
An offering agent declares the extension with an AgentExtension object
(§4.4.4 of [[A2A]]: uri, description, required,
params) inside AgentCard.capabilities.extensions:
{
"capabilities": {
"extensions": [
{
"uri": "https://w3id.org/jeswr/a2a-rdf/v1",
"description": "Accepts SHACL-validated RDF intents under hash-pinned protocol documents; negotiates upgrades from natural language.",
"required": false,
"params": {
"formats": ["text/turtle", "application/ld+json"],
"nlNegotiation": true,
"protocolDocuments": [
{
"name": "Grant access",
"source": "https://alice.pod.example/protocols/grant-access",
"hash": "sha256:4af1e70e42283872cbc0dd3a5eeaa1bd86adda728c993447bed8930d990ab509"
}
]
}
}
]
}
}
The params object is defined as follows (all members optional):
| Member | Type | Meaning |
|---|---|---|
formats |
array of string | RDF media types the agent accepts and produces for extension payloads. When absent,
defaults to ["text/turtle"]. An offering agent MUST support
text/turtle [[turtle]] and SHOULD support
application/ld+json [[json-ld11]] (the interop baseline;
). |
nlNegotiation |
boolean | Whether the agent will negotiate new Protocol Documents in natural
language (the AGORA loop). false means only the pre-declared
protocolDocuments are spoken. Default: true. |
protocolDocuments |
array of object | Protocol Documents the agent already implements, each
{"name"?: string, "source": string, "hash": string} where
source is a dereferenceable HTTPS URL for the PD and hash
is its protocol hash. Pre-declaring lets a client that already implements a
listed PD skip the handshake entirely (). |
Per the guidance of [[A2A-EXTENSIONS]] that data-only extensions and generally
capability-adding extensions should not be card-required, an offering agent
SHOULD declare "required": false: the extension's baseline behaviour degrades
gracefully to ordinary natural-language A2A for extension-unaware clients. Card-level
required: true is reserved for agents that only accept structured
RDF exchanges (e.g. an audited enterprise endpoint); such an agent MUST reject requests
that do not activate the extension, as §4.6 of [[A2A]] provides. Note the distinction from
the per-exchange required flag of an upgrade offer
().
Activation follows §3.2.6 / §4.6 of [[A2A]] unchanged: a consuming client requests
activation by listing the extension URI in the A2A-Extensions service
parameter (an HTTP header in HTTP-based bindings; gRPC metadata in gRPC bindings), and an
agent that activates it SHOULD echo the URI in the response's A2A-Extensions.
In addition:
Message or Artifact that carries an extension payload
part () MUST list the extension URI in its
extensions array (the core per-message tagging field, §4.1.4 of [[A2A]]).required offer, triggers the
no-silent-downgrade rule ().
A Protocol Document is an RDF graph containing exactly one subject typed
a2a:ProtocolDocument (the PD subject), with:
| Property | Card. | Meaning |
|---|---|---|
a2a:requestShape | 1..* | IRI(s) of the
sh:NodeShape(s) every request intent under this protocol MUST
conform to. The shape triples are part of the PD graph (self-contained: nothing to
fetch at validation time). |
a2a:responseShape | 0..* | IRI(s) of the
sh:NodeShape(s) a structured response MUST conform to, when the protocol
defines one. |
dcterms:title, dcterms:description,
dcterms:hasVersion | 0..1 each | Human-readable metadata. |
The PD graph MUST be self-contained: a validator MUST NOT dereference IRIs mentioned in
the shapes (no owl:imports-style loading) — everything the SHACL engine needs
is inside the hashed graph. Example (execution-verified against the reference codec):
@prefix a2a: <https://w3id.org/jeswr/a2a#>.
@prefix schema: <https://schema.org/>.
@prefix sh: <http://www.w3.org/ns/shacl#>.
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>.
@prefix dcterms: <http://purl.org/dc/terms/>.
<https://alice.pod.example/protocols/grant-access> a a2a:ProtocolDocument;
dcterms:title "Grant access";
dcterms:hasVersion "1.0.0";
a2a:requestShape a2a:GrantIntentShape.
a2a:GrantIntentShape a sh:NodeShape;
sh:targetClass a2a:Intent;
sh:property [ a sh:PropertyShape;
sh:path a2a:action; sh:minCount 1; sh:maxCount 1; sh:name "action";
sh:node [ a sh:NodeShape;
sh:property
[ a sh:PropertyShape; sh:path rdf:type; sh:minCount 1; sh:hasValue a2a:GrantAction ],
[ a sh:PropertyShape; sh:path schema:object; sh:minCount 1; sh:name "target"; sh:nodeKind sh:IRI ],
[ a sh:PropertyShape; sh:path schema:recipient; sh:minCount 1; sh:name "recipient"; sh:nodeKind sh:IRI ],
[ a sh:PropertyShape; sh:path a2a:mode; sh:minCount 1; sh:name "mode"; sh:nodeKind sh:IRI ] ] ].
The protocol hash pins the content of a PD independent of where it is hosted. It is computed as:
"sha256:" + lowercase-hex(digest).
A party that dereferences a PD from a protocolSource (or a card-declared
source) MUST recompute the hash over the fetched graph and MUST reject the
document — treating the exchange as never upgraded — if it does not equal the pinned hash.
The hash, not the URL and not TLS, is the trust anchor: a compromised or substituted host
cannot alter a pinned protocol.
Within this extension, the sha256: prefix denotes exactly this construction —
RDFC-1.0 canonical N-Quads, then SHA-256 — as a fixed pair. A change to either the
canonicalization or the digest algorithm is a breaking change to this specification: it
MUST use a new, distinct prefix and is only introducible under a new extension URI
(). Implementations MUST reject hash strings whose prefix they
do not recognise.
The reference codec [[SOLID-A2A-IMPL]] computes ProtocolDocument.hash over the
RDFC-1.0 canonical N-Quads form via rdf-canonize, the W3C reference
implementation (landed in solid-a2a 0.2.0) — its ProtocolDocument.hash
values are conformant to this section, and any independent RDFC-1.0 implementation agrees on
the same canonical bytes. See .
PDs SHOULD be published at HTTPS URLs whose representations are immutable (content-addressed paths or versioned documents); a PD is typically hosted in the offering party's own storage (in the Solid deployment profile, a pod) so protocol definitions inherit the host's access control and availability story.
The handshake is how two agents move a conversation from natural language onto a pinned Protocol Document. It is a pair of extension payloads carried in ordinary A2A messages (binding in ); it adds no RPC methods and no task states.
| Member | Type | Req. | Meaning |
|---|---|---|---|
kind | string | yes | The literal
"upgrade-offer". |
protocolHash | string | yes | The protocol hash of the offered PD. |
protocolSource | string | yes | HTTPS URL from which the PD can be fetched (and MUST be hash-verified; ). |
required | boolean | yes | true
marks this a security-bearing exchange that MUST NOT be silently downgraded to
natural language (). Receivers MUST reject an offer whose
required is present but not a JSON boolean — a malformed flag MUST NOT be
coerced to false. |
protocolName | string | no | Human-readable protocol name. |
{
"kind": "upgrade-offer",
"protocolHash": "sha256:4af1e70e42283872cbc0dd3a5eeaa1bd86adda728c993447bed8930d990ab509",
"protocolSource": "https://alice.pod.example/protocols/grant-access",
"required": true,
"protocolName": "Grant access"
}
Both payloads also have an equivalent RDF form (one subject typed
a2a:UpgradeOffer / a2a:UpgradeResponse with predicates
a2a:protocolHash, a2a:protocolSource, a2a:protocolName,
a2a:required, a2a:accept, a2a:reason;
booleans as xsd:boolean literals). A handshake graph MUST contain exactly one
such typed subject; receivers MUST reject ambiguous graphs (zero, multiple, or mixed
handshake subjects) rather than splice triples across subjects.
Given an offer O and a purported response R, natural-language fallback for the exchange is permitted only when all of the following hold — otherwise the sender MUST NOT proceed in natural language:
R.protocolHash == O.protocolHash — a response about any other protocol
(or an unparseable / absent response) never authorises downgrade (fail closed; this
forecloses using an unrelated decline to justify NL fallback);O.required == false — a security-bearing offer declined means the
exchange is aborted with an error (), not
retried in prose; andR.accept == false — if the peer accepted, the exchange proceeds in
validated RDF and NL is simply not used.The rule is the codec-level half of downgrade resistance: it makes silent downgrade a protocol violation rather than a default. It does not by itself authenticate the response — transport/message authentication is the A2A binding's concern, and credential-level protections compose via .
required flags, two scopes
When an Agent Card pre-declares a PD in params.protocolDocuments
() and the client already implements a PD with the same
protocol hash, the client MAY send a conforming intent directly — tagging the part
with that hash () — without a prior offer/response round. The
Agent Card declaration is the standing offer. The agent MUST still validate the
intent against the shape before acting.
All extension payloads ride in A2A Parts (§4.1.6 of [[A2A]]): the
data content field for JSON payloads, the text content field with
an RDF mediaType for serialized RDF. Core data structures are never altered;
per-part attributes go in Part.metadata, per §4.6's extension-point rules.
Two metadata keys are defined, namespaced by the extension URI:
| Key | Value | On |
|---|---|---|
https://w3id.org/jeswr/a2a-rdf/v1/kind |
one of "upgrade-offer", "upgrade-response",
"intent", "intent-response", "authorization" |
every extension part (REQUIRED — receivers dispatch on it without sniffing payloads) |
https://w3id.org/jeswr/a2a-rdf/v1/protocolHash |
the protocol hash the part claims conformance to | intent and intent-response parts (REQUIRED) |
kind | Content field | mediaType | Payload |
|---|---|---|---|
upgrade-offer / upgrade-response |
data |
application/json |
The JSON object of / . (The RDF form
MAY instead be sent as a text part with an RDF media type; the JSON
form is the interop baseline.) |
intent |
text or data |
text/turtle for text;
application/ld+json for data |
The intent graph. MUST contain exactly one subject typed
a2a:Intent and MUST conform to the pinned PD's
a2a:requestShape(s). |
intent-response |
text or data |
as for intent |
The structured response graph; MUST conform to the PD's
a2a:responseShape(s) when the PD defines any. |
authorization |
data |
application/vp (or application/ld+json) |
A [[vc-data-model-2.0]] Verifiable Presentation packaging the acting agent's Agent Authorization Credential chain, root-first, per [[AGENT-AUTHZ]] (). |
A receiving agent MUST SHACL-validate every intent part against the pinned
PD's request shape(s) before acting on it, and MUST refuse (with the error of
) an intent that does not conform, whose claimed
protocolHash is unknown to the conversation, or whose graph is ambiguous
(zero or multiple a2a:Intent subjects). Validation is against the local,
hash-verified copy of the PD only — never against shapes fetched at message time.
An example intent graph under the grant-access PD of
(execution-verified against the reference codec, including its conforms: true
validation result):
@prefix a2a: <https://w3id.org/jeswr/a2a#>.
@prefix schema: <https://schema.org/>.
@prefix acl: <http://www.w3.org/ns/auth/acl#>.
<urn:a2a:intent:kxs8cv> a a2a:Intent;
a2a:action [ a a2a:GrantAction;
schema:object <https://alice.pod.example/notes/>;
schema:recipient <https://bob.example/profile#me>;
a2a:mode acl:Read, acl:Write ].
Extensions cannot add enum values or alter core structures (§4.6 limitations, per
[[A2A-EXTENSIONS]]), so failures are signalled with core mechanisms plus one metadata key:
a refusing agent SHOULD fail the request using the binding's standard error path (e.g. a
JSON-RPC error or a failed task state) and SHOULD attach, on the error's message or
metadata, the key
https://w3id.org/jeswr/a2a-rdf/v1/error with one of:
This extension has no required dependencies on other A2A extensions. The authorization composition () depends only on W3C document formats (VC 2.0, ODRL), not on any A2A extension. Per [[A2A-EXTENSIONS]], a client activates this extension alone.
/v1 segment of the extension URI; breaking
changes MUST mint /v2 (§4.6.3 of [[A2A]]).dcterms:hasVersion is informative labelling only.https://a2a-protocol.org/extensions/ prefix; this
document would then declare the mapping and deprecate the w3id.org/jeswr
URI.In addition to §4.6's general guidance (validate all extension data rigorously; apply the same authentication and authorization to extension traffic as to core traffic):
owl:imports, no context fetching for JSON-LD beyond a
locally-pinned context); treat malformed graphs as refusals, never best-effort repairs.
Handshake graphs with zero/multiple/mixed typed subjects MUST be rejected
() — splicing predicates across subjects is a spoofing vector.required and accept
flags are security-bearing. A missing or non-boolean value MUST cause rejection of the
message, never a default: coercing a malformed required to false
or a malformed accept to false re-opens the downgrade the rule
exists to close.required offer aborts. Implementers
MUST NOT add "helpful" NL retries around a refused security-bearing exchange.protocolSource is a
user/peer-supplied URL. Fetchers MUST require HTTPS, SHOULD refuse private, loopback, and
link-local address targets (including post-DNS-resolution, in server-side deployments),
MUST cap response size and time, and SHOULD NOT follow cross-origin redirects. Hash
verification () MUST happen before any use of the fetched
graph; the hash — not the URL, not TLS — is what makes the PD trustworthy.messageId, taskId/contextId
scoping) and, where credentials are presented, on the challenge/domain binding of the
Verifiable Presentation ([[AGENT-AUTHZ]] presentations) for replay resistance — and SHOULD
treat a repeated messageId within a context as a duplicate, not a new
instruction.sh:node recursion, large graphs). Receivers SHOULD bound
graph size and validation time and refuse over-limit inputs; PDs a party agrees to speak
SHOULD be reviewed for pathological shapes before acceptance — accepting a PD is accepting
a validation workload.required pressure. Marking the whole extension
card-required excludes baseline clients; per [[A2A-EXTENSIONS]], use it only where an
RDF-only surface is genuinely intended (see ).
Structured, vocabulary-grounded messages are easier to mine than prose; the same property
that enables auditing enables profiling. Agent Card protocolDocuments listings
reveal what routines an agent speaks — publishers should treat the card as public metadata
and keep sensitive protocols negotiable-on-request (nlNegotiation) rather than
card-listed. Authorization parts carry credential chains: present the minimal chain, per the
minimisation guidance of [[AGENT-AUTHZ]].
Verified against the named repositories on 2026-07-03. Nothing below is an endorsement by the A2A project.
Alice's agent (client) asks Bob's agent (server) to grant Bob read+write access to a
container. The exchange is security-bearing, so the offer is required. Payloads
marked ✔ were generated and validated with the reference codec [[SOLID-A2A-IMPL]]; the
protocol hash shown was computed conformantly to with an
independent RDFC-1.0 implementation (rdf-canonize 5.0.0) over the codec-built
Protocol Document graph.
Bob's Agent Card carries the declaration of (with the grant-access PD pre-listed). Alice's agent does not yet implement that PD, so it runs the full handshake rather than the skip of .
POST /a2a HTTP/1.1
Host: agent.bob.example
Content-Type: application/json
A2A-Extensions: https://w3id.org/jeswr/a2a-rdf/v1
{
"jsonrpc": "2.0", "method": "SendMessage", "id": "1",
"params": { "message": {
"messageId": "m-1", "role": "ROLE_USER",
"extensions": ["https://w3id.org/jeswr/a2a-rdf/v1"],
"parts": [
{ "text": "I'd like to set up access sharing. Happy to do this over your grant-access protocol." },
{ "data": {
"kind": "upgrade-offer",
"protocolHash": "sha256:4af1e70e42283872cbc0dd3a5eeaa1bd86adda728c993447bed8930d990ab509",
"protocolSource": "https://alice.pod.example/protocols/grant-access",
"required": true,
"protocolName": "Grant access"
},
"mediaType": "application/json",
"metadata": { "https://w3id.org/jeswr/a2a-rdf/v1/kind": "upgrade-offer" } }
] } }
}
✔ offer object. Bob's agent fetches the PD from protocolSource (HTTPS,
size/time-capped), recomputes the RDFC-1.0 hash, and confirms it matches. ✔ the shown hash
is the recomputable RDFC-1.0 hash of the PD graph in .
HTTP/1.1 200 OK
Content-Type: application/json
A2A-Extensions: https://w3id.org/jeswr/a2a-rdf/v1
{
"jsonrpc": "2.0", "id": "1",
"result": { "message": {
"messageId": "m-2", "role": "ROLE_AGENT",
"extensions": ["https://w3id.org/jeswr/a2a-rdf/v1"],
"parts": [
{ "data": {
"kind": "upgrade-response",
"protocolHash": "sha256:4af1e70e42283872cbc0dd3a5eeaa1bd86adda728c993447bed8930d990ab509",
"accept": true
},
"mediaType": "application/json",
"metadata": { "https://w3id.org/jeswr/a2a-rdf/v1/kind": "upgrade-response" } }
] } }
}
Had Bob declined, required: true means Alice's agent aborts with
"protocol-required" — it does not re-ask in prose
().
POST /a2a HTTP/1.1
Host: agent.bob.example
Content-Type: application/json
A2A-Extensions: https://w3id.org/jeswr/a2a-rdf/v1
{
"jsonrpc": "2.0", "method": "SendMessage", "id": "2",
"params": { "message": {
"messageId": "m-3", "role": "ROLE_USER", "contextId": "ctx-1",
"extensions": ["https://w3id.org/jeswr/a2a-rdf/v1"],
"parts": [
{ "text": "@prefix a2a: .\n@prefix schema: .\n@prefix acl: .\n\n a a2a:Intent;\n a2a:action [ a a2a:GrantAction;\n schema:object ;\n schema:recipient ;\n a2a:mode acl:Read, acl:Write ].",
"mediaType": "text/turtle",
"metadata": {
"https://w3id.org/jeswr/a2a-rdf/v1/kind": "intent",
"https://w3id.org/jeswr/a2a-rdf/v1/protocolHash": "sha256:4af1e70e42283872cbc0dd3a5eeaa1bd86adda728c993447bed8930d990ab509"
} }
] } }
}
✔ intent graph; ✔ SHACL validation against the PD returns conforms: true. Bob's
agent validates the graph against the pinned request shape, then hands the intent to its
authorization layer. Were this a delegated agent acting under a mandate, the message would
also carry an authorization part with the credential-chain presentation
(). No LLM ran on either side of this step.
Bob's agent performs the grant and replies; if the PD had declared an
a2a:responseShape, the reply would carry a conforming
intent-response part. On validation failure it would instead fail the request
with "validation-failed" and MAY attach the SHACL report as a Turtle part
().