<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE rfc [
  <!ENTITY nbsp    "&#160;">
  <!ENTITY zwsp   "&#8203;">
  <!ENTITY nbhy   "&#8209;">
  <!ENTITY wj     "&#8288;">
]>
<rfc xmlns:xi="http://www.w3.org/2001/XInclude"
     ipr="trust200902"
     category="exp"
     submissionType="independent"
     docName="draft-gaikwad-woa-00"
     version="3">

  <front>
    <title abbrev="WoA">The Web of Agents (WoA)</title>

    <author fullname="Madhava Gaikwad" surname="Gaikwad">
      <address>
        <email>gaikwad.madhav@gmail.com</email>
      </address>
    </author>

    <date year="2025" month="December" day="01"/>

    <area>Applications and Real-Time</area>
    <workgroup>Independent Submission</workgroup>

    <abstract>
      <t>
        This document defines the Web of Agents (WoA), a minimal JSON based
        description format and invocation convention that allows HTTP hosts
        to advertise AI agents and for clients to invoke those agents in a
        uniform way. A WoA document is typically served from a well known
        location on an HTTP origin and uses JSON Schema to describe agent
        inputs and outputs. WoA does not define a discovery protocol itself
        but is designed to be used as a host level primitive by higher level
        discovery systems.
      </t>
    </abstract>
  </front>

  <middle>

    <!-- 1. Introduction -->
    <section anchor="intro">
      <name>Introduction</name>

      <t>
        AI agents are increasingly exposed as network reachable services,
        such as text based large language model interfaces, task specific
        tools, and composite workflows that call other services. Today these
        agents are typically documented using ad hoc JSON documents or
        provider specific formats. This makes it difficult for generic
        clients to discover which agents exist on a given origin and to
        invoke them in a predictable way.
      </t>

      <t>
        The Web of Agents (WoA) defines:
      </t>

      <ul>
        <li>a JSON based document format, usually served from a well known
        path on an origin, that lists agents and their properties</li>
        <li>a JSON Schema based description of agent inputs and outputs</li>
        <li>a small set of transport configuration objects that define how
        a client constructs an invocation request</li>
        <li>a simple invocation envelope used by some transports</li>
      </ul>

      <t>
        WoA is intentionally small in scope. It does not attempt to define a
        global discovery system or a capability vocabulary. It is designed
        to complement such systems by providing a host level primitive that
        discovery mechanisms can fetch, cache, and index. For example, a
        cross platform discovery system such as
        <xref target="CUI-AGENT-DISCOVERY"/> could use WoA documents as one
        of its inputs when building a search index.
      </t>

      <t>
        This document is targeted at the Independent Submission Stream with
        category "exp". The intent is to provide a concrete and
        implementable format that can be experimented with by client and
        host implementers.
      </t>
    </section>

    <!-- 1.1 Conventions and Terminology -->
    <section anchor="conventions">
      <name>Conventions and Terminology</name>

      <t>
        The key words "MUST", "MUST NOT", "REQUIRED", "SHALL",
        "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED",
        "NOT RECOMMENDED", "MAY", and "OPTIONAL" in this document
        are to be interpreted as described in BCP 14
        <xref target="RFC2119"/> <xref target="RFC8174"/> when, and
        only when, they appear in all capitals, as shown here.
      </t>

      <t>
        This document uses the JSON data model defined in
        <xref target="RFC8259"/> and HTTP terminology from
        <xref target="RFC9110"/>.
      </t>

      <section anchor="terminology">
        <name>Terms</name>

        <dl>
          <dt>WoA document</dt>
          <dd>
            A JSON document served by an HTTP origin that describes one or
            more agents and their transport configurations according to this
            specification.
          </dd>

          <dt>Agent</dt>
          <dd>
            A logical AI powered capability exposed by a host. An agent has
            an identifier, a human readable name and description, a JSON
            Schema based input and output description, and one or more
            transport options that describe how to invoke it.
          </dd>

          <dt>Host</dt>
          <dd>
            An HTTP origin that serves a WoA document and optionally
            implements one or more transports for agents described in that
            document.
          </dd>

          <dt>WoA Client</dt>
          <dd>
            A component that retrieves the WoA document and invokes agents.
            A WoA client may be a user facing application, an orchestration
            engine, or another independent agent, enabling agent to agent
            (A2A) interactions.
          </dd>

          <dt>Transport</dt>
          <dd>
            A named mechanism that defines how a client constructs and sends
            an invocation request. This document defines the
            "rest" and "mcp" transports. Additional
            transports may be registered in the WoA Transport Registry.
          </dd>
        </dl>
      </section>
    </section>

    <!-- 2. Architecture -->
    <section anchor="architecture">
      <name>Architecture</name>

      <t>
        A typical deployment has an HTTP origin that serves a WoA document
        at a well known path, and one or more transports that accept
        invocation requests.
      </t>

      <figure anchor="fig-arch">
        <name>High Level WoA Architecture</name>
        <artwork><![CDATA[
+-----------+         GET /.well-known/woa.json        +-----------+
|           | ---------------------------------------> |           |
|   Client  |                                          |    Host   |
|           | <--------------------------------------- |           |
+-----------+         200 application/woa+json         +-----------+
      |
      |  Select agent and transport
      v
+-----------+       HTTP POST (REST transport)         +-----------+
|           | ---------------------------------------> |           |
|   Client  |                                          |    Host   |
|           | <--------------------------------------- |           |
+-----------+             JSON response                +-----------+
]]></artwork>
      </figure>

      <t>
        A client fetches the WoA document from a host, selects an agent,
        chooses a transport supported by both client and host, constructs an
        invocation request according to the transport rules, and processes
        the response. Higher level discovery systems may crawl or index WoA
        documents but are out of scope for this specification.
      </t>
    </section>

    <!-- 3. WoA Document Schema -->
    <section anchor="woa-schema">
      <name>WoA Document Schema</name>

      <t>
        A WoA document is a single JSON object with the following top level
        fields:
      </t>

      <ul>
        <li><tt>woa_version</tt>:
        A string identifying the WoA document version. For this
        specification the value MUST be the string "1".</li>

        <li><tt>agents</tt>:
        An array of agent objects as defined in <xref target="agent-object"/>.</li>

        <li><tt>transports</tt>:
        An object whose keys are transport names and whose values are
        transport configuration objects as defined in
        <xref target="transport-configs"/>.</li>
      </ul>

      <section anchor="agent-object">
        <name>Agent Objects</name>

        <t>
          Each element of the <tt>agents</tt> array is an
          object with the following fields:
        </t>

        <ul>
          <li><tt>id</tt> (string, REQUIRED):
          A token that uniquely identifies the agent within the WoA document.
          The value MUST match the following ABNF
          (using <xref target="RFC5234"/>):
          </li>
        </ul>

        <sourcecode type="abnf">
agent-id = 1*( ALPHA / DIGIT / "-" / "_" )
</sourcecode>

        <ul>
          <li><tt>name</tt> (string, REQUIRED):
          A short, human readable name for the agent.</li>

          <li><tt>description</tt> (string, REQUIRED):
          A human readable description of what the agent does. Clients MUST
          treat this field as untrusted input for security reasons
          (see <xref target="security"/>).</li>

          <li><tt>version</tt> (string, OPTIONAL):
          A version identifier for the agent implementation, such as
          "1.0.0".</li>

          <li><tt>capabilities</tt> (array of strings, OPTIONAL):
          A list of capability identifiers. This specification does not
          define a controlled vocabulary. Implementations MAY use URIs
          (for example, "https://example.com/capability/summarization")
          or URN like identifiers as long as they are stable.</li>

          <li><tt>inputs</tt> (object, REQUIRED):
          A JSON Schema document that describes the expected request body
          when invoking the agent. See <xref target="json-schema-usage"/>.</li>

          <li><tt>outputs</tt> (object, REQUIRED):
          A JSON Schema document that describes the successful response body
          produced by the agent.</li>

          <li><tt>transports</tt> (array of strings, REQUIRED):
          Names of transport configurations (keys in the top level
          <tt>transports</tt> object) that can be used to
          invoke this agent.</li>

          <li><tt>operations</tt> (array of objects, OPTIONAL):
          A list of operation descriptors for agents that support multiple
          logical operations via a single transport endpoint.
          If <tt>operations</tt> is not present, the
          agent is considered to have a single unnamed operation.</li>
        </ul>

        <t>
          Each operation object in the <tt>operations</tt> array has:
        </t>

        <ul>
          <li><tt>name</tt> (string, REQUIRED):
          A token naming the operation.</li>
          <li><tt>description</tt> (string, REQUIRED):
          Human readable description of the operation.</li>
          <li><tt>inputs</tt> (object, OPTIONAL):
          JSON Schema overriding the agent level inputs for this
          operation.</li>
          <li><tt>outputs</tt> (object, OPTIONAL):
          JSON Schema overriding the agent level outputs for this
          operation.</li>
        </ul>

        <t>
          Clients MUST NOT assume that two agents with the same
          <tt>id</tt> on different origins have the same
          behavior or schema.
        </t>
      </section>

      <section anchor="json-schema-usage">
        <name>JSON Schema Usage for Inputs and Outputs</name>

        <t>
          The <tt>inputs</tt>,
          <tt>outputs</tt>, and any operation level
          <tt>inputs</tt> or
          <tt>outputs</tt> fields MUST be valid JSON
          Schema documents compliant with the JSON Schema 2020-12 core and
          validation specifications <xref target="JSON-SCHEMA-CORE"/>
          <xref target="JSON-SCHEMA-VAL"/>.
        </t>

        <t>
          At minimum, implementations MUST support JSON Schema documents
          whose root is an object with:
        </t>

        <ul>
          <li>a <tt>type</tt> of "object"</li>
          <li>a <tt>properties</tt> object describing
          named properties</li>
          <li>an optional <tt>required</tt> array
          naming required properties</li>
        </ul>

        <t>
          More advanced JSON Schema features such as
          <tt>oneOf</tt>, <tt>allOf</tt>,
          and <tt>format</tt> MAY be used by hosts and
          SHOULD be ignored by clients that do not understand them, as long
          as the client can still construct a conforming request.
        </t>

        <t>
          Hosts SHOULD provide concise and accurate JSON Schema documents
          to enable static validation and tooling. Clients MAY validate
          request bodies locally against the <tt>inputs</tt>
          schema before sending them and MAY validate successful responses
          against the <tt>outputs</tt> schema.
        </t>
      </section>

      <section anchor="transport-configs">
        <name>Transport Configurations</name>

        <t>
          The top level <tt>transports</tt> object maps
          transport names to configuration objects. Transport names are
          strings. This document defines the <tt>rest</tt>
          and <tt>mcp</tt> transports. Additional
          transports MAY be defined and registered in the WoA Transport
          Registry (see <xref target="iana-woa-transport"/>).
        </t>

        <section anchor="rest-transport">
          <name>REST Transport</name>

          <t>
            A <tt>rest</tt> transport configuration
            object MUST contain:
          </t>

          <ul>
            <li><tt>base</tt> (string, REQUIRED):
            An absolute HTTPS URL that identifies the base of the REST API.
            The URL scheme MUST be "https" and the server SHOULD support TLS
            1.3 <xref target="RFC8446"/>.</li>

            <li><tt>invoke_path</tt> (string, REQUIRED):
            An absolute path beginning with "/" that, when combined with
            <tt>base</tt>, yields the invocation URL
            template. The path MAY contain a query component. Within the
            path, the case sensitive substring "{agent_id}" MAY appear as a
            placeholder.</li>
          </ul>

          <t>
            To construct the invocation URL, the client concatenates the
            <tt>base</tt> URL and the
            <tt>invoke_path</tt> value. If the
            <tt>invoke_path</tt> contains the case
            sensitive substring "{agent_id}", the client MUST replace it
            with the target agent's <tt>id</tt> value.
          </t>

          <t>
            Clients invoking an agent via the REST transport MUST use HTTP
            POST and MUST send a request body encoded as JSON with media
            type <tt>application/json</tt>. The request
            body for the REST transport is defined in
            <xref target="invocation"/>. Hosts using the REST transport
            MUST respond with JSON and SHOULD use the
            <tt>application/problem+json</tt> media type
            for errors as specified in <xref target="RFC9457"/>.
          </t>
        </section>

        <section anchor="mcp-transport">
          <name>MCP Transport</name>

          <t>
            A <tt>mcp</tt> transport configuration object
            describes how an agent is exposed via a Model Context Protocol
            (MCP) server <xref target="MCP"/>. The configuration object
            MUST contain:
          </t>

          <ul>
            <li><tt>server</tt> (string, REQUIRED):
            An identifier or URL for the MCP server endpoint. The exact
            format is defined by the MCP specification.</li>

            <li><tt>tool_namespace</tt> (string, REQUIRED):
            A string that identifies the logical namespace of tools on the
            MCP server.</li>

            <li><tt>tool_field</tt> (string, REQUIRED):
            The name of the field in the invocation envelope that contains
            the tool name for this MCP server.</li>
          </ul>

          <t>
            When using the MCP transport, the client translates the WoA
            invocation envelope into the appropriate MCP tool invocation as
            defined by the MCP specification <xref target="MCP"/>. For
            example, if <tt>tool_field</tt> is "agent",
            the client MAY pass the value of the envelope's
            <tt>agent</tt> field as the tool name.
          </t>
        </section>

        <section anchor="private-transports">
          <name>Private Transports</name>

          <t>
            Hosts MAY define private transport names for experimental use.
            Private transport names MUST use a reverse DNS prefix, such as
            "com.example.mytransport", to avoid collisions with registered
            transports. Private transports MUST NOT be registered in the WoA
            Transport Registry.
          </t>
        </section>
      </section>
    </section>

    <!-- 4. Invocation -->
    <section anchor="invocation">
      <name>Invocation</name>

      <t>
        This section describes the invocation envelope and how it is used
        with the REST and MCP transports. Other transports MAY define their
        own invocation rules.
      </t>

      <section anchor="inv-envelope">
        <name>Invocation Envelope</name>

        <t>
          When a transport uses a JSON request body that contains metadata
          about the invocation in addition to the agent specific input
          object, this document refers to that JSON object as the
          "invocation envelope".
        </t>

        <t>
          For the REST transport defined in this document, the invocation
          envelope is an object with the following fields:
        </t>

        <ul>
          <li><tt>agent</tt> (string, REQUIRED):
          The agent identifier as listed in the WoA document.</li>

          <li><tt>operation</tt> (string, OPTIONAL):
          The operation name, if the agent defines an
          <tt>operations</tt> array. If omitted for an
          agent that defines operations, the name "default" is RECOMMENDED
          as the implied operation.</li>

          <li><tt>input</tt> (object, REQUIRED):
          A JSON object that MUST conform to the JSON Schema specified in
          the selected operation's <tt>inputs</tt>
          schema, or to the agent level <tt>inputs</tt>
          if there is no per operation override.</li>
        </ul>

        <t>
          Transports MAY add additional fields to the invocation envelope
          as long as they do not conflict with the fields defined above.
        </t>
      </section>

      <section anchor="rest-invocation">
        <name>REST Transport Invocation</name>

        <t>
          When using the REST transport, the client constructs the
          invocation URL as described in <xref target="rest-transport"/>
          and sends an HTTP POST request with media type
          <tt>application/json</tt> and a request body
          containing the invocation envelope.
        </t>

        <t>
          The <tt>agent</tt> field in the envelope MUST
          match the intended agent's <tt>id</tt>. If the
          REST invocation URL template includes an "{agent_id}" placeholder,
          the host can infer the agent from the URL. In that case:
        </t>

        <ul>
          <li>If the host derives an agent identifier from the URL and the
          <tt>agent</tt> field is absent in the
          envelope, the host MAY use the identifier from the URL.</li>

          <li>If the host derives an agent identifier from the URL and the
          envelope contains an <tt>agent</tt> field with
          a different value, the host MUST reject the request with HTTP
          status 400 (Bad Request). The host SHOULD return a
          <tt>application/problem+json</tt> body
          explaining the mismatch.</li>
        </ul>

        <t>
          On success, the host MUST return a 2xx status code and a JSON
          response body that conforms to the JSON Schema specified in the
          selected operation's <tt>outputs</tt> schema,
          or the agent level <tt>outputs</tt> schema if
          there is no per operation override.
        </t>

        <t>
          On error, the host SHOULD return a 4xx or 5xx status code and a
          response body using the problem details format defined in
          <xref target="RFC9457"/> with media type
          <tt>application/problem+json</tt>. Problem
          type URIs and error code taxonomies are deployment specific.
        </t>
      </section>

      <section anchor="mcp-invocation">
        <name>MCP Transport Invocation</name>

        <t>
          When using the MCP transport, the client translates the invocation
          envelope into the appropriate MCP tool invocation. The exact
          mapping is defined by the MCP specification
          <xref target="MCP"/> and is not repeated here. As a typical
          pattern, the <tt>agent</tt> or
          <tt>operation</tt> fields of the envelope may
          map to tool names and the <tt>input</tt> object
          may map to MCP tool arguments.
        </t>

        <t>
          WoA does not define the wire protocol for MCP and does not impose
          additional security requirements beyond those defined by the MCP
          specification. The security considerations in
          <xref target="security"/> still apply to the host that publishes
          the WoA document.
        </t>
      </section>
    </section>

    <!-- 5. Authorization -->
    <section anchor="authorization">
      <name>Authorization</name>

      <t>
        WoA deliberately separates the question of "which agent exists and
        how can it be invoked" from "who is allowed to invoke this agent".
        The WoA document format does not contain access tokens and does not
        mandate a particular authorization protocol. Hosts MAY use OAuth 2.0
        <xref target="RFC6749"/>, mutual TLS, or other mechanisms to
        protect invocation endpoints.
      </t>

      <t>
        A host MAY include additional metadata in the WoA document to help
        clients understand the authorization expectations for an agent. For
        example, a deployment using the SOUTH stochastic authorization
        protocol <xref target="I-D.gaikwad-south-authorization"/> might
        include an <tt>authz</tt> object with pointers
        to policy endpoints. Such metadata is deployment specific and out
        of scope for the core WoA specification.
      </t>
    </section>

    <!-- 6. Caching -->
    <section anchor="caching">
      <name>Caching</name>

      <t>
        WoA documents are likely to be fetched frequently by clients and
        discovery systems. Hosts SHOULD include HTTP caching headers, such
        as <tt>ETag</tt>, <tt>Last-Modified</tt>,
        and appropriate <tt>Cache-Control</tt> directives,
        on responses that carry a WoA document to reduce unnecessary
        network traffic. Clients SHOULD honor these headers when polling
        for updates.
      </t>
    </section>

    <!-- 7. Security Considerations -->
    <section anchor="security">
      <name>Security Considerations</name>

      <t>
        WoA is a descriptive format and does not execute code by itself, but
        it is used in contexts where agents may execute untrusted input or
        perform sensitive actions. Both hosts and clients need to consider
        the following security aspects.
      </t>

      <section anchor="sec-transport">
        <name>Transport Security</name>

        <t>
          Hosts that serve WoA documents and implement REST transports
          MUST use HTTPS. The underlying TLS version SHOULD be TLS 1.3
          <xref target="RFC8446"/>. Clients MUST validate server
          certificates according to normal HTTPS rules. Plain HTTP MUST NOT
          be used for WoA documents or REST invocations on the open
          Internet.
        </t>
      </section>

      <section anchor="sec-ssrf">
        <name>Server Side Request Forgery and Origin Validation</name>

        <t>
          A malicious WoA document could advertise transport URLs that point
          to internal or otherwise sensitive endpoints. Automated clients
          that unconditionally invoke agents based on WoA documents risk
          being used as a vector for server side request forgery.
        </t>

        <t>
          Clients SHOULD validate that transport URLs provided in a WoA
          document resolve to allowed domains or IP address ranges before
          invoking agents. In particular, clients SHOULD NOT automatically
          send invocation requests to URLs that resolve to private or link
          local address ranges, such as those defined in <xref target="RFC1918"/>,
          unless explicitly configured to do so by an administrator.
          Clients SHOULD also be cautious of HTTP redirects that change the
          authority component of the URL and SHOULD apply the same
          validation to the redirect target.
        </t>
      </section>

      <section anchor="sec-prompt-injection">
        <name>Indirect Prompt Injection</name>

        <t>
          The <tt>name</tt> and
          <tt>description</tt> fields of an agent are
          free form strings controlled by the host. Clients that use a
          large language model to reason about or select agents based on
          these fields MUST treat them as untrusted input. A malicious host
          could embed text that attempts to influence the client side model
          in ways that bypass user intent, a pattern sometimes referred to
          as indirect prompt injection.
        </t>

        <t>
          Implementers SHOULD design any agent selection logic that uses
          LLMs with appropriate input isolation, such as explicit
          system level instructions that describe which fields are trusted
          and which are untrusted, and with guardrails that restrict the
          actions that can be taken based on WoA content.
        </t>
      </section>

      <section anchor="sec-agent-output">
        <name>Agent Output Trust</name>

        <t>
          WoA itself does not provide integrity or authenticity guarantees
          for agent outputs. Clients SHOULD treat agent responses as
          untrusted data and apply appropriate validation, sandboxing, and
          authorization checks before using them to take actions such as
          executing code, issuing network requests, or changing external
          state.
        </t>
      </section>
    </section>

    <!-- 8. IANA Considerations -->
    <section anchor="iana">
      <name>IANA Considerations</name>

      <section anchor="iana-well-known">
        <name>Well Known URI Registration</name>

        <t>
          This document requests registration of a new well known URI suffix
          in the "Well Known URIs" registry as defined in
          <xref target="RFC8615"/>.
        </t>

        <t>
          The registration template is:
        </t>

        <artwork><![CDATA[
URI suffix: woa.json
Change controller: IETF
Specification document: This document
Status: permanent
Related information: none
]]></artwork>
      </section>

      <section anchor="iana-media-type">
        <name>Media Type Registration</name>

        <t>
          This document requests registration of the
          <tt>application/woa+json</tt> media type in the
          "Media Types" registry according to <xref target="RFC6838"/>.
        </t>

        <t>
          The registration template is:
        </t>

        <artwork><![CDATA[
Type name: application
Subtype name: woa+json
Required parameters: none
Optional parameters: none
Encoding considerations: binary
  WoA documents are encoded as UTF-8 JSON text.
Security considerations: See Section 7 of this document.
Interoperability considerations: none
Published specification: This document.
Applications that use this media type:
  WoA hosts and clients that exchange WoA documents.
Fragment identifier considerations: none
Additional information: none
Person & email address to contact:
  Madhava Gaikwad <gaikwad.madhav@gmail.com>
Intended usage: COMMON
Restrictions on usage: none
Author: Madhava Gaikwad <gaikwad.madhav@gmail.com>
Change controller: IETF
]]></artwork>
      </section>

      <section anchor="iana-woa-transport">
        <name>WoA Transport Registry</name>

        <t>
          This document requests the creation of a new registry titled
          "WoA Transport Registry". The registry records transport names
          used in the top level <tt>transports</tt>
          object of WoA documents.
        </t>

        <t>
          Each entry in the registry has the following fields:
        </t>

        <ul>
          <li>Transport name: a short string identifying the transport.</li>
          <li>Reference: a stable specification that defines the transport.</li>
        </ul>

        <t>
          Registration policy for the WoA Transport Registry is
          "Specification Required" as defined in <xref target="RFC8126"/>.
        </t>

        <t>
          This document registers the following initial entries:
        </t>

        <artwork><![CDATA[
Transport name: rest
Reference: This document

Transport name: mcp
Reference: Model Context Protocol specification [MCP]
]]></artwork>
      </section>
    </section>

  </middle>

  <back>

    <!-- Normative References -->
    <references>
      <name>Normative References</name>

      <reference anchor="RFC2119" target="https://www.rfc-editor.org/info/rfc2119">
        <front>
          <title>Key words for use in RFCs to Indicate Requirement Levels</title>
          <author initials="S." surname="Bradner" fullname="Scott Bradner"/>
          <date year="1997" month="March"/>
        </front>
        <seriesInfo name="BCP" value="14"/>
        <seriesInfo name="RFC" value="2119"/>
        <seriesInfo name="DOI" value="10.17487/RFC2119"/>
      </reference>

      <reference anchor="RFC8174" target="https://www.rfc-editor.org/info/rfc8174">
        <front>
          <title>Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words</title>
          <author initials="B." surname="Leiba" fullname="Barry Leiba"/>
          <date year="2017" month="May"/>
        </front>
        <seriesInfo name="BCP" value="14"/>
        <seriesInfo name="RFC" value="8174"/>
        <seriesInfo name="DOI" value="10.17487/RFC8174"/>
      </reference>

      <reference anchor="RFC8259" target="https://www.rfc-editor.org/info/rfc8259">
        <front>
          <title>The JavaScript Object Notation (JSON) Data Interchange Format</title>
          <author initials="T." surname="Bray" fullname="Tim Bray"/>
          <date year="2017" month="December"/>
        </front>
        <seriesInfo name="STD" value="90"/>
        <seriesInfo name="RFC" value="8259"/>
        <seriesInfo name="DOI" value="10.17487/RFC8259"/>
      </reference>

      <reference anchor="RFC9110" target="https://www.rfc-editor.org/info/rfc9110">
        <front>
          <title>HTTP Semantics</title>
          <author initials="R." surname="Fielding" fullname="Roy T. Fielding"/>
          <author initials="M." surname="Nottingham" fullname="Mark Nottingham"/>
          <author initials="J." surname="Reschke" fullname="Julian Reschke"/>
          <date year="2022" month="June"/>
        </front>
        <seriesInfo name="STD" value="97"/>
        <seriesInfo name="RFC" value="9110"/>
        <seriesInfo name="DOI" value="10.17487/RFC9110"/>
      </reference>

      <reference anchor="RFC8446" target="https://www.rfc-editor.org/info/rfc8446">
        <front>
          <title>The Transport Layer Security (TLS) Protocol Version 1.3</title>
          <author initials="E." surname="Rescorla" fullname="Eric Rescorla"/>
          <date year="2018" month="August"/>
        </front>
        <seriesInfo name="RFC" value="8446"/>
        <seriesInfo name="DOI" value="10.17487/RFC8446"/>
      </reference>

      <reference anchor="RFC8615" target="https://www.rfc-editor.org/info/rfc8615">
        <front>
          <title>Well-Known Uniform Resource Identifiers (URIs)</title>
          <author initials="M." surname="Nottingham" fullname="Mark Nottingham"/>
          <date year="2019" month="May"/>
        </front>
        <seriesInfo name="RFC" value="8615"/>
        <seriesInfo name="DOI" value="10.17487/RFC8615"/>
      </reference>

      <reference anchor="RFC6838" target="https://www.rfc-editor.org/info/rfc6838">
        <front>
          <title>Media Type Specifications and Registration Procedures</title>
          <author initials="N." surname="Freed" fullname="Ned Freed"/>
          <author initials="J." surname="Klensin" fullname="John Klensin"/>
          <author initials="T." surname="Hansen" fullname="Tony Hansen"/>
          <date year="2013" month="January"/>
        </front>
        <seriesInfo name="BCP" value="13"/>
        <seriesInfo name="RFC" value="6838"/>
        <seriesInfo name="DOI" value="10.17487/RFC6838"/>
      </reference>

      <reference anchor="RFC9457" target="https://www.rfc-editor.org/info/rfc9457">
        <front>
          <title>Problem Details for HTTP APIs</title>
          <author initials="M." surname="Nottingham" fullname="Mark Nottingham"/>
          <author initials="E." surname="Wilde" fullname="Erik Wilde"/>
          <author initials="S." surname="Dalal" fullname="Sanjay Dalal"/>
          <date year="2023" month="July"/>
        </front>
        <seriesInfo name="RFC" value="9457"/>
        <seriesInfo name="DOI" value="10.17487/RFC9457"/>
      </reference>

      <reference anchor="RFC6749" target="https://www.rfc-editor.org/info/rfc6749">
        <front>
          <title>The OAuth 2.0 Authorization Framework</title>
          <author initials="D." surname="Hardt" fullname="Dick Hardt"/>
          <date year="2012" month="October"/>
        </front>
        <seriesInfo name="RFC" value="6749"/>
        <seriesInfo name="DOI" value="10.17487/RFC6749"/>
      </reference>

      <reference anchor="RFC5234" target="https://www.rfc-editor.org/info/rfc5234">
        <front>
          <title>Augmented BNF for Syntax Specifications: ABNF</title>
          <author initials="D." surname="Crocker" fullname="Dave Crocker"/>
          <author initials="P." surname="Overell" fullname="Paul Overell"/>
          <date year="2008" month="January"/>
        </front>
        <seriesInfo name="STD" value="68"/>
        <seriesInfo name="RFC" value="5234"/>
        <seriesInfo name="DOI" value="10.17487/RFC5234"/>
      </reference>

      <reference anchor="RFC8126" target="https://www.rfc-editor.org/info/rfc8126">
        <front>
          <title>Guidelines for Writing an IANA Considerations Section in RFCs</title>
          <author initials="M." surname="Cotton" fullname="Michelle Cotton"/>
          <author initials="B." surname="Leiba" fullname="Barry Leiba"/>
          <author initials="T." surname="Narten" fullname="Thomas Narten"/>
          <date year="2017" month="June"/>
        </front>
        <seriesInfo name="BCP" value="26"/>
        <seriesInfo name="RFC" value="8126"/>
        <seriesInfo name="DOI" value="10.17487/RFC8126"/>
      </reference>

      <reference anchor="RFC1918" target="https://www.rfc-editor.org/info/rfc1918">
        <front>
          <title>Address Allocation for Private Internets</title>
          <author initials="Y." surname="Rekhter" fullname="Yakov Rekhter"/>
          <author initials="B." surname="Moskowitz" fullname="Bob Moskowitz"/>
          <author initials="D." surname="Karrenberg" fullname="Daniel Karrenberg"/>
          <author initials="G." surname="de Groot" fullname="Geert Jan de Groot"/>
          <author initials="E." surname="Lear" fullname="Eliot Lear"/>
          <date year="1996" month="February"/>
        </front>
        <seriesInfo name="BCP" value="5"/>
        <seriesInfo name="RFC" value="1918"/>
        <seriesInfo name="DOI" value="10.17487/RFC1918"/>
      </reference>

      <reference anchor="JSON-SCHEMA-CORE" target="https://json-schema.org/draft/2020-12/json-schema-core">
        <front>
          <title>JSON Schema: A Media Type for Describing JSON Documents</title>
          <author initials="A." surname="Wright" fullname="Austin Wright"/>
          <author initials="H." surname="Andrews" fullname="Henry Andrews"/>
          <author initials="B." surname="Hutton" fullname="Ben Hutton"/>
          <author initials="G." surname="Dennis" fullname="Greg Dennis"/>
          <date year="2020" month="December"/>
        </front>
      </reference>

      <reference anchor="JSON-SCHEMA-VAL" target="https://json-schema.org/draft/2020-12/json-schema-validation">
        <front>
          <title>JSON Schema Validation: A Vocabulary for Structural Validation of JSON</title>
          <author initials="A." surname="Wright" fullname="Austin Wright"/>
          <author initials="H." surname="Andrews" fullname="Henry Andrews"/>
          <author initials="B." surname="Hutton" fullname="Ben Hutton"/>
          <date year="2020" month="December"/>
        </front>
      </reference>

      <reference anchor="I-D.gaikwad-south-authorization" target="https://datatracker.ietf.org/doc/draft-gaikwad-south-authorization/">
        <front>
          <title>SOUTH: Stochastic Authorization for Agent and Service Requests</title>
          <author initials="M." surname="Gaikwad" fullname="Madhava Gaikwad"/>
          <date year="2025" month="October"/>
        </front>
        <seriesInfo name="Internet-Draft" value="draft-gaikwad-south-authorization"/>
      </reference>

    </references>

    <!-- Informative References -->
    <references>
      <name>Informative References</name>

      <reference anchor="CUI-AGENT-DISCOVERY" target="https://datatracker.ietf.org/doc/draft-cui-ai-agent-discovery-invocation/">
        <front>
          <title>HTTP-Based AI Agent Discovery and Invocation Protocol</title>
          <author initials="Y." surname="Cui" fullname="Yong Cui"/>
          <author initials="Y." surname="Chao" fullname="Yihan Chao"/>
          <author initials="C." surname="Du" fullname="Chenguang Du"/>
          <date year="2025" month="October"/>
        </front>
        <seriesInfo name="Internet-Draft" value="draft-cui-ai-agent-discovery-invocation"/>
      </reference>

      <reference anchor="MCP" target="https://modelcontextprotocol.io">
        <front>
          <title>Model Context Protocol Specification</title>
          <author>
            <organization>Anthropic</organization>
          </author>
          <date year="2024" month="November"/>
        </front>
      </reference>

    </references>

    <!-- Appendix A: SOUTH Example -->
    <section anchor="appendix-south" numbered="false">
      <name>Appendix A: Example Use with SOUTH (Non-Normative)</name>

      <t>
        This appendix sketches how a deployment might combine WoA with the
        SOUTH stochastic authorization protocol
        <xref target="I-D.gaikwad-south-authorization"/>. It is
        non-normative and does not modify the core WoA format.
      </t>

      <t>
        A host could add an <tt>authz</tt> object at the
        top level of the WoA document or within an agent object that points
        to a SOUTH policy endpoint. For example:
      </t>

      <sourcecode type="json"><![CDATA[
{
  "woa_version": "1",
  "agents": [
    {
      "id": "summarizer",
      "name": "Document Summarizer",
      "description": "Summarizes English text.",
      "version": "1.0.0",
      "capabilities": [
        "https://example.com/capability/summarization"
      ],
      "inputs": { "...": "JSON Schema elided" },
      "outputs": { "...": "JSON Schema elided" },
      "transports": ["rest"],
      "authz": {
        "scheme": "south",
        "policy_uri":
          "https://authz.example.com/south/policies/summarizer",
        "token_header": "Authorization"
      }
    }
  ],
  "transports": {
    "rest": {
      "base": "https://api.example.com",
      "invoke_path": "/agents/{agent_id}/invoke"
    }
  }
}
]]></sourcecode>

      <t>
        A client that understands SOUTH could first obtain a token from the
        SOUTH authorization server according to
        <xref target="I-D.gaikwad-south-authorization"/> and then include
        it as a SOUTH token in the HTTP request:
      </t>

      <sourcecode type="http"><![CDATA[
POST /agents/summarizer/invoke HTTP/1.1
Host: api.example.com
Content-Type: application/json
Authorization: SOUTH eyJhbGciOi...

{
  "agent": "summarizer",
  "operation": "default",
  "input": {
    "text": "Long document text here..."
  }
}
]]></sourcecode>

      <t>
        The details of how SOUTH evaluates policies and issues tokens are
        defined in <xref target="I-D.gaikwad-south-authorization"/> and are
        not repeated here.
      </t>
    </section>

    <!-- Appendix B: Complete Example -->
    <section anchor="appendix-example" numbered="false">
      <name>Appendix B: Complete Example WoA Flow (Non-Normative)</name>

      <t>
        This appendix provides a complete example showing a WoA document, a
        client fetching it, invoking an agent via the REST transport, and
        receiving a successful response.
      </t>

      <section anchor="example-woa-doc" numbered="false">
        <name>Example WoA Document</name>

        <t>
          Consider a host at <tt>https://api.example.com</tt>
          that serves the following WoA document at
          <tt>https://api.example.com/.well-known/woa.json</tt>
          using the <tt>application/woa+json</tt> media type.
        </t>

        <sourcecode type="json"><![CDATA[
{
  "woa_version": "1",
  "agents": [
    {
      "id": "summarizer",
      "name": "Document Summarizer",
      "description": "Summarizes English text.",
      "version": "1.0.0",
      "capabilities": [
        "https://example.com/capability/summarization"
      ],
      "inputs": {
        "$schema": "https://json-schema.org/draft/2020-12/schema",
        "type": "object",
        "properties": {
          "text": {
            "type": "string",
            "description": "Input document text in English."
          },
          "max_words": {
            "type": "integer",
            "minimum": 10,
            "maximum": 500,
            "description": "Maximum number of words in the summary."
          }
        },
        "required": ["text"]
      },
      "outputs": {
        "$schema": "https://json-schema.org/draft/2020-12/schema",
        "type": "object",
        "properties": {
          "summary": {
            "type": "string",
            "description": "The generated summary."
          }
        },
        "required": ["summary"]
      },
      "transports": ["rest"],
      "operations": [
        {
          "name": "default",
          "description": "Default summarization operation."
        }
      ]
    }
  ],
  "transports": {
    "rest": {
      "base": "https://api.example.com",
      "invoke_path": "/agents/{agent_id}/invoke"
    }
  }
}
]]></sourcecode>
      </section>

      <section anchor="example-fetch" numbered="false">
        <name>Client Fetches WoA Document</name>

        <t>
          A client fetches the WoA document:
        </t>

        <sourcecode type="http"><![CDATA[
GET /.well-known/woa.json HTTP/1.1
Host: api.example.com
Accept: application/woa+json, application/json
]]></sourcecode>

        <t>
          The host responds:
        </t>

        <sourcecode type="http"><![CDATA[
HTTP/1.1 200 OK
Content-Type: application/woa+json
ETag: "abc123"
Cache-Control: max-age=300

{ ... JSON from previous section ... }
]]></sourcecode>

        <t>
          The client parses the JSON, locates the agent with
          <tt>id</tt> "summarizer", and notes that it
          supports the <tt>rest</tt> transport.
        </t>
      </section>

      <section anchor="example-invoke" numbered="false">
        <name>Client Invokes the Agent</name>

        <t>
          The client constructs the invocation URL by concatenating the
          <tt>base</tt> and
          <tt>invoke_path</tt> values and substituting
          "{agent_id}" with "summarizer":
        </t>

        <sourcecode type="text"><![CDATA[
https://api.example.com/agents/summarizer/invoke
]]></sourcecode>

        <t>
          The client then builds an invocation envelope that conforms to the
          agent's <tt>inputs</tt> schema:
        </t>

        <sourcecode type="json"><![CDATA[
{
  "agent": "summarizer",
  "operation": "default",
  "input": {
    "text": "The IETF is an open community of designers.",
    "max_words": 40
  }
}
]]></sourcecode>

        <t>
          The client sends the HTTP request:
        </t>

        <sourcecode type="http"><![CDATA[
POST /agents/summarizer/invoke HTTP/1.1
Host: api.example.com
Content-Type: application/json
Accept: application/json

{
  "agent": "summarizer",
  "operation": "default",
  "input": {
    "text": "The IETF is an open community of designers.",
    "max_words": 40
  }
}
]]></sourcecode>

        <t>
          The host validates the request against the JSON Schema in
          <tt>inputs</tt>, performs the summarization,
          and returns a response that matches the
          <tt>outputs</tt> schema:
        </t>

        <sourcecode type="http"><![CDATA[
HTTP/1.1 200 OK
Content-Type: application/json

{
  "summary": "The IETF is a community focused on Internet evolution."
}
]]></sourcecode>

        <t>
          The client MAY validate the response body against the
          <tt>outputs</tt> schema and then present the
          summary to the user or feed it into subsequent processing.
        </t>
      </section>
    </section>

  </back>
</rfc>
