Class: Protege::AgentMailbox

Inherits:
ActionMailbox::Base
  • Object
show all
Defined in:
app/mailboxes/protege/agent_mailbox.rb

Overview

Inbound edge of the Gateway: routes every received email toward the inference pipeline.

Action Mailbox delivers parsed mail here, exposing mail and inbound_email as instance methods and calling #process as the single entry point. The mailbox resolves every agent addressed in the To: header, then hands each off to Gateway.accept_smtp_message, which enqueues an InferenceJob per agent — so an email to several proteges is handled by each independently. The inbound Message-ID is forwarded as the correlation ID so the trace token survives the async boundary and is restored inside the job.

Recursion guard

Agent-sent mail carries an X-Protege-Recursion hop-count header (+Gateway::RECURSION_HEADER+): 1 on fresh mail, the inbound count plus one on a reply. A human mail client never echoes the header back, so conversations with people don't accumulate — only an unbroken Protege-to-Protege reply chain does. Any inbound email whose count has reached the configured limit (+config.recursion_limit+, default 50) is silently dropped, preventing infinite loops when one agent replies to another. Unroutable mail (no matching agent) is bounced with an unrouted notice instead.

Access guardrail

Each addressed agent is checked against its own inbound access guardrail (+Gateway::AccessControl+): the committed global ceiling intersected with that agent's runtime rules. The email is delivered only to the agents that permit the sender; if none do, it is bounced with an access-denied notice and never reaches inference.

Instance Method Summary collapse

Instance Method Details

#processvoid

This method returns an undefined value.

Route the inbound email: drop on exhausted recursion budget, bounce when no addressed agent matches, bounce when the sender may reach none of them, bounce on an attachment breach, else accept it for every addressed agent the sender is permitted to reach (one email to several proteges is handled by each independently).



35
36
37
38
39
40
41
42
# File 'app/mailboxes/protege/agent_mailbox.rb', line 35

def process
  return handle_recursion_limit       if recursion_limit_reached?
  return bounce_with_unrouted         if agents.empty?
  return bounce_with_access_denied    if permitted_agents.empty?
  return bounce_with_attachment_error if attachment_violation

  permitted_agents.each { |agent| Gateway.accept_smtp_message(inbound_email:, agent:) }
end