<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE rfc [
  <!ENTITY nbsp "&#160;">
]>
<?xml-model href="rfc7991bis.rnc"?>
<rfc
  xmlns:xi="http://www.w3.org/2001/XInclude"
  category="info"
  docName="draft-mackay-aacp-00"
  ipr="trust200902"
  obsoletes=""
  updates=""
  submissionType="independent"
  xml:lang="en"
  version="3">

  <front>
    <title abbrev="AACP">Agent Action Compression Protocol (AACP) Version 1.1</title>

    <seriesInfo name="Internet-Draft" value="draft-mackay-aacp-00"/>

    <author fullname="Andrew Mackay" initials="A." surname="Mackay">
      <organization>Independent</organization>
      <address>
        <email>mackayandrewr@gmail.com</email>
        <uri>https://aacp.dev</uri>
      </address>
    </author>

    <date day="28" month="May" year="2026"/>

    <area>General</area>
    <workgroup>Independent Submission</workgroup>

    <keyword>AACP</keyword>
    <keyword>agent</keyword>
    <keyword>multi-agent</keyword>
    <keyword>LLM</keyword>
    <keyword>compression</keyword>
    <keyword>coordination</keyword>
    <keyword>protocol</keyword>

    <abstract>
      <t>
        This document defines the Agent Action Compression Protocol (AACP),
        a pipe-delimited coordination format for agent-to-agent communication
        in multi-agent large language model (LLM) systems. AACP replaces
        verbose natural language instructions exchanged between autonomous
        agents with a compact, structured, machine-parseable packet format.
      </t>
      <t>
        Measured against live API tokenisation on Claude Sonnet 4.5 and
        GPT-4o, AACP reduces coordination token usage by approximately 23
        percent versus equivalent natural language instructions across a
        four-hop payroll workflow benchmark.
      </t>
      <t>
        AACP operates above transport protocols such as the Model Context
        Protocol (MCP) and Agent-to-Agent Protocol (A2A), compressing
        message payload content rather than addressing routing or delivery.
        The protocol is transport-agnostic, model-agnostic, and designed
        to complement rather than replace existing agent coordination
        infrastructure.
      </t>
    </abstract>

  </front>

  <middle>

    <section numbered="true" toc="default">
      <name>Introduction</name>
      <t>
        Multi-agent LLM systems coordinate by exchanging instructions
        between autonomous agents. In current implementations, these
        coordination messages are typically written in natural language --
        verbose, ambiguous, and token-expensive.
      </t>
      <t>
        Consider a four-agent payroll workflow where an orchestrating agent
        must instruct an HRMS agent to retrieve salary records. A typical
        English instruction might read:
      </t>
      <artwork><![CDATA[
"Please retrieve the employee salary records for the period
ending 31 August 2024. I need all active employees, their
departments, cost centres, base salary, any changes made this
month, and pension contribution rates. Return as JSON array."
      ]]></artwork>
      <t>
        This instruction consumes 56 tokens on Claude Sonnet 4.5. The
        equivalent AACP packet:
      </t>
      <artwork><![CDATA[
FETCH|HR|return:HR-Agent|p:1|aacp:1.1|res:emp_salary|
period:2024-08|filter:status=active|fmt:json
      ]]></artwork>
      <t>
        consumes 52 tokens -- a 7.1 percent reduction on this hop alone,
        with larger reductions observed on hops with longer instructions
        (33.8 percent on a MERGE instruction). Across a four-hop payroll
        workflow the total coordination token reduction is 22.9 percent on
        Claude Sonnet 4.5 and 23.7 percent on GPT-4o.
      </t>
      <t>Beyond token reduction, AACP provides:</t>
      <ul>
        <li>Unambiguous, machine-parseable coordination messages</li>
        <li>Schema validation before transmission</li>
        <li>Deterministic encoding for known workflow types</li>
        <li>Structured audit trails for compliance purposes</li>
        <li>Model-agnostic format interpretable across LLM providers</li>
      </ul>
      <t>This document specifies AACP version 1.1.</t>
    </section>

    <section numbered="true" toc="default">
      <name>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>
      <dl>
        <dt>Agent:</dt>
        <dd>An autonomous software process that receives instructions,
        performs tasks using one or more LLM API calls, and returns
        results.</dd>

        <dt>Coordination message:</dt>
        <dd>An instruction sent from one agent to another that describes
        what action to take, on what resource, with what parameters,
        and where to return the result. Distinct from task content
        (the actual work the receiving agent performs).</dd>

        <dt>AACP packet:</dt>
        <dd>A pipe-delimited string conforming to the format defined in
        Section 4, used as a coordination message.</dd>

        <dt>Task tokens:</dt>
        <dd>Tokens consumed by an agent performing its actual work (reading
        documents, generating reports, analysing data). AACP does not
        compress task tokens.</dd>

        <dt>Coordination tokens:</dt>
        <dd>Tokens consumed by the coordination message itself. AACP
        compresses these.</dd>

        <dt>Rule-based encoder:</dt>
        <dd>A deterministic encoder that produces AACP packets from
        structured input without an LLM call. Zero API cost.</dd>

        <dt>LLM encoder:</dt>
        <dd>An encoder that uses an LLM API call to compress an English
        instruction into an AACP packet. Used for novel instructions
        outside known workflow patterns.</dd>
      </dl>
    </section>

    <section numbered="true" toc="default">
      <name>Motivation and Problem Statement</name>
      <t>
        The problem of verbosity in agent communication has been
        independently identified in published research. Mou et al. (2025)
        <xref target="ECOLANG"/> observed that "there exists redundancy in
        current agent communication: when expressing the same intention,
        agents tend to use lengthy and repetitive language" and achieved
        greater than 20 percent token reduction through evolved compression
        language for social simulation.
      </t>
      <t>
        AACP addresses the same observed problem with a different approach:
        a structured, typed packet schema targeting business workflow
        coordination rather than evolved natural language compression.
      </t>
      <t>
        The specific technical gap AACP fills: neither MCP <xref target="MCP"/>
        nor A2A <xref target="A2A"/> address the semantic content of
        coordination messages. Both protocols operate at the transport and
        routing layers. AACP operates at the content layer, compressing what
        agents say to each other rather than how messages are delivered.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>Packet Format</name>
      <t>
        An AACP packet is a sequence of pipe-delimited fields. The pipe
        character (U+007C, "|") is the field separator.
      </t>
      <artwork><![CDATA[
packet = task "|" dom "|" named-fields
      ]]></artwork>
      <t>
        TASK and DOM are positional (fields 0 and 1 respectively). All
        other fields MUST be named key:value pairs. Empty positional
        slots MUST NOT appear in v1.1 packets.
      </t>

      <section numbered="true" toc="default">
        <name>Positional Fields</name>
        <dl>
          <dt>Field 0 -- TASK:</dt>
          <dd>The action verb. REQUIRED. MUST be one of the values defined
          in Section 5.1.</dd>

          <dt>Field 1 -- DOM:</dt>
          <dd>The business domain context. REQUIRED. MUST be one of the
          values defined in Section 5.2.</dd>
        </dl>
      </section>

      <section numbered="true" toc="default">
        <name>Named Fields</name>
        <t>
          After the two positional fields, all fields are named using the
          format key:value where key is a lowercase ASCII string and value
          is the field content.
        </t>
        <t>The following named fields MUST appear in every packet:</t>
        <dl>
          <dt>return:</dt>
          <dd>The agent identifier or role that receives the result. REQUIRED.</dd>
          <dt>aacp:</dt>
          <dd>The protocol version. REQUIRED. MUST be "1.1" for packets
          conforming to this specification.</dd>
        </dl>
        <t>The following named fields are RECOMMENDED where applicable:</t>
        <dl>
          <dt>p:</dt>
          <dd>Priority. Values: 1 (critical), 2 (medium), 3 (low). Defaults to 2 if omitted.</dd>
          <dt>res:</dt>
          <dd>The resource identifier the action applies to.</dd>
          <dt>period:</dt>
          <dd>A time period for the action, expressed as YYYY-MM or similar abbreviated form.</dd>
          <dt>filter:</dt>
          <dd>A filter expression applied to the resource.</dd>
          <dt>fields:</dt>
          <dd>Comma-separated list of return fields requested. SHOULD be
          omitted when the receiving agent has default field definitions
          in its system configuration.</dd>
          <dt>fmt:</dt>
          <dd>The requested response format (e.g. json, pdf, xlsx).</dd>
        </dl>
      </section>

      <section numbered="true" toc="default">
        <name>Extended Fields</name>
        <t>
          Additional named fields MAY be appended after the core fields.
          The following extended field keys are defined in this version:
          src, src_prev, rules, validate, tmpl, data_ptr, amt, ccy, sup,
          match, terms, type, party, clause, issue, risk, block, flags,
          req, highlight, status, to, subj, att, flag_msg, tone,
          sentiment, actor, chain, prog, ltv, loyalty, urgency.
        </t>
        <t>
          Unknown extended keys MUST generate advisory warnings in
          validators, not errors. This permits forward compatibility and
          organisation-private extensions.
        </t>
      </section>

      <section numbered="true" toc="default">
        <name>Packet Examples</name>
        <t>Fetch active employee salary records:</t>
        <artwork><![CDATA[
FETCH|HR|return:HR-Agent|p:1|aacp:1.1|res:emp_salary|
period:2024-08|filter:status=active|fmt:json
        ]]></artwork>
        <t>Merge datasets and run payroll calculation:</t>
        <artwork><![CDATA[
MERGE|HR|return:HR-Agent|p:1|aacp:1.1|rules:payroll_v2|
validate:budget_cc
        ]]></artwork>
        <t>Flag a legal clause for senior review:</t>
        <artwork><![CDATA[
FLAG|LEGAL|return:LEG-Agent|p:1|aacp:1.1|type:NDA|
party:Acme-Ltd|clause:s7|issue:ip_rights_restriction|
risk:high|block:signature
        ]]></artwork>
        <t>Build IT user account:</t>
        <artwork><![CDATA[
BUILD|IT|return:IT-Agent|p:1|aacp:1.1|res:ad_account|
filter:usr=j.smith|fields:email,dept,grp,pwd_reset
        ]]></artwork>
      </section>
    </section>

    <section numbered="true" toc="default">
      <name>Valid Field Values</name>

      <section numbered="true" toc="default">
        <name>TASK Values</name>
        <t>
          The following TASK values are defined in AACP v1.1:
          FETCH, PROC, FLAG, RESOLVE, LOG, SEND, BUILD, MERGE,
          CALC, REPORT, ACK, SYNC.
        </t>
        <t>
          Implementations MUST warn on unrecognised TASK values.
          Implementations MUST NOT reject packets with unrecognised
          TASK values, to permit forward compatibility.
        </t>
      </section>

      <section numbered="true" toc="default">
        <name>DOM Values</name>
        <t>
          The following DOM values are defined in AACP v1.1:
          HR, FIN, SALES, LEGAL, IT, CS, MKT.
        </t>
        <t>
          Domain extensions MAY be defined by implementors.
          Unrecognised DOM values SHOULD generate advisory warnings.
        </t>
      </section>

      <section numbered="true" toc="default">
        <name>Priority Values</name>
        <t>
          The p: field accepts the following values:
          1 (critical -- process immediately),
          2 (medium -- standard processing, default),
          3 (low -- process when capacity allows).
        </t>
      </section>
    </section>

    <section numbered="true" toc="default">
      <name>Encoding</name>

      <section numbered="true" toc="default">
        <name>Rule-Based Encoding</name>
        <t>
          For known, repetitive workflow types, a rule-based encoder
          deterministically produces AACP packets from structured input
          without an LLM API call. This approach has zero API cost and
          produces identical output for identical input.
        </t>
        <t>
          Reference implementations are provided for: Payroll
          (PayrollEncoder, 6 coordination hops), IT Provisioning
          (ITEncoder, 6 hops), Invoice Processing (InvoiceEncoder, 3 hops),
          and Contract Review (ContractEncoder, 3 hops).
        </t>
      </section>

      <section numbered="true" toc="default">
        <name>LLM-Assisted Encoding</name>
        <t>
          For novel instructions outside known workflow patterns, an
          LLM-assisted encoder produces AACP packets by submitting the
          English instruction to a language model with the AACP
          specification as a system prompt.
        </t>
      </section>

      <section numbered="true" toc="default">
        <name>Fallback and Registry</name>
        <t>
          A fallback encoder routes structured input to rule-based encoding
          and English input to LLM-assisted encoding. Every LLM-assisted
          encoding call is logged to a local registry as a candidate for
          future rule-based encoding. This creates a self-improving loop:
          novel patterns are encoded once via LLM and subsequently encoded
          deterministically at zero cost.
        </t>
      </section>
    </section>

    <section numbered="true" toc="default">
      <name>Validation</name>
      <t>AACP validators MUST check the following:</t>
      <ul>
        <li>Field 0 (TASK) is present and is a recognised TASK value</li>
        <li>Field 1 (DOM) is present and is a recognised DOM value</li>
        <li>A return: named field is present and non-empty</li>
        <li>An aacp: named field is present</li>
      </ul>
      <t>AACP validators SHOULD warn on:</t>
      <ul>
        <li>Unrecognised TASK or DOM values</li>
        <li>Missing p: field</li>
        <li>AACP version mismatch</li>
        <li>sentiment: field present without tone: field</li>
        <li>ltv: field present without ccy: field</li>
        <li>Unknown extended field keys</li>
      </ul>
      <t>
        Validation errors MUST be reported before packet transmission.
        Validation warnings SHOULD be logged but MUST NOT prevent
        transmission.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>Decoding</name>
      <t>
        AACP packets are designed to be human-readable as written.
        Decoders MAY expand packets into structured English for audit
        purposes, user interfaces, or debugging.
      </t>
      <t>
        For audit purposes, the AACP packet itself is the canonical
        record. Decoded English output is advisory only.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>Compression Boundaries</name>
      <t>
        Coordination tokens compress well: routing instructions, resource
        references, structured intent, action verbs, and metadata are
        efficiently expressed in AACP.
      </t>
      <t>
        Task tokens do not compress: the actual work an agent performs
        is expressed in task content passed alongside the coordination
        packet. AACP does not and cannot compress task tokens.
      </t>
      <t>
        Emotional and relational context compresses poorly. Implementors
        SHOULD use AACP for routing and metadata in these cases and pass
        full English context in the task content field.
      </t>
      <t>
        Total workflow cost impact depends on the ratio of coordination
        to task tokens. Coordination-heavy workflows benefit most.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>Tokenisation Benchmark</name>

      <section numbered="true" toc="default">
        <name>Methodology</name>
        <t>
          Coordination token counts were measured using live API
          usage_metadata. Each message was submitted as a bare user
          message with no system prompt and max_tokens=1 to isolate
          coordination token counts. English baseline is the full verbose
          instruction the AACP packet replaces in production. Benchmark
          date: May 2026.
        </t>
      </section>

      <section numbered="true" toc="default">
        <name>Results</name>
        <t>Four-hop payroll workflow. Token counts from live API.</t>
        <artwork><![CDATA[
+---------------------+-------+------+--------+--------+
| Hop                 |English| AACP |Claude% |GPT-4o% |
+---------------------+-------+------+--------+--------+
| fetch employees     |    56 |   52 |  -7.1% | -12.7% |
| fetch budgets       |    57 |   47 | -17.5% | -16.0% |
| merge and calculate |    65 |   43 | -33.8% | -31.6% |
| generate report     |    62 |   43 | -30.6% | -33.3% |
+---------------------+-------+------+--------+--------+
| TOTAL               |   240 |  185 | -22.9% | -23.7% |
+---------------------+-------+------+--------+--------+
        ]]></artwork>
      </section>

      <section numbered="true" toc="default">
        <name>Findings</name>
        <t>
          AACP v1.1 pipe-delimited format achieves consistent coordination
          token reduction across both tested models and all four workflow
          hops. Four formats were evaluated before selecting pipe-delimited.
          The bracket-based [KEY:VALUE] format increased token count by
          approximately 45 percent on Claude versus English, due to the
          tokenisation cost of bracket and colon characters.
        </t>
        <t>
          Embedding field lists and URI data pointers in packets increases
          token count significantly and SHOULD be avoided where the
          receiving agent has default field definitions in its system
          configuration.
        </t>
      </section>
    </section>

    <section numbered="true" toc="default">
      <name>Relationship to Existing Protocols</name>
      <t>
        MCP <xref target="MCP"/> defines how agents access external tools
        and resources. AACP operates inside MCP message payloads,
        compressing the coordination instructions. The two protocols are
        complementary.
      </t>
      <t>
        A2A <xref target="A2A"/> defines agent discovery and task routing
        between agents. AACP compresses the content of messages that A2A
        routes. The two protocols are complementary.
      </t>
      <t>
        AACP fills a distinct layer: semantic compression of coordination
        message content. No existing published protocol addresses this
        specific layer.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>Extensibility</name>
      <t>
        Unknown named fields generate advisory warnings, not errors.
        Implementors MAY define organisation-private fields using a
        namespacing convention to avoid collision with future AACP fields.
      </t>
      <t>
        Implementors MAY define domain values beyond the seven defined
        in Section 5.2. A community encoding registry is planned for v2.0.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>Version Policy</name>
      <t>
        The aacp: field MUST be included in every packet and MUST specify
        the protocol version. Breaking changes increment the major version.
        Additive changes increment the minor version. Implementations
        SHOULD warn on version mismatch but MUST NOT reject packets on
        version mismatch alone.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>Security Considerations</name>
      <t>
        Packet injection: AACP packets are plain text and MUST be treated
        as untrusted input. Validators MUST be applied to all received
        packets before processing. Implementations MUST NOT execute actions
        based on unvalidated packets.
      </t>
      <t>
        Prompt injection via packets: malicious content in AACP field
        values could be interpreted as instructions by a receiving LLM
        agent. Implementations SHOULD sanitise field values before
        including them in LLM prompts. Field values SHOULD be treated
        as data, not instructions.
      </t>
      <t>
        Replay attacks: AACP v1.1 does not include sequence numbers or
        timestamps. Implementations operating in security-sensitive
        environments SHOULD add replay protection at the transport layer.
      </t>
      <t>
        Sensitive data in packets: sensitive data (PII, financial records,
        credentials) MUST NOT be embedded in AACP field values. Use
        data pointer references (data_ptr:) that resolve through
        authenticated data access layers instead.
      </t>
    </section>

    <section numbered="true" toc="default">
      <name>IANA Considerations</name>
      <t>This document has no IANA actions.</t>
    </section>

  </middle>

  <back>

    <references>
      <name>References</name>

      <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="S. Bradner"/>
            <date year="1997" month="March"/>
          </front>
          <seriesInfo name="BCP" value="14"/>
          <seriesInfo name="RFC" value="2119"/>
        </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="B. Leiba"/>
            <date year="2017" month="May"/>
          </front>
          <seriesInfo name="BCP" value="14"/>
          <seriesInfo name="RFC" value="8174"/>
        </reference>

      </references>

      <references>
        <name>Informative References</name>

        <reference anchor="ECOLANG" target="https://arxiv.org/abs/2505.06904">
          <front>
            <title>EcoLANG: Towards Efficient Agent Communication via Evolved Language</title>
            <author surname="Mou" initials="Y."/>
            <date year="2025" month="May"/>
          </front>
          <refcontent>arXiv:2505.06904</refcontent>
        </reference>

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

        <reference anchor="A2A" target="https://google.github.io/A2A/">
          <front>
            <title>Agent-to-Agent Protocol</title>
            <author>
              <organization>Google</organization>
            </author>
            <date year="2025"/>
          </front>
        </reference>

      </references>
    </references>

  </back>
</rfc>
