> ## Documentation Index
> Fetch the complete documentation index at: https://docs.erdo.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# RetireDecisionAPI mirrors erdo_retire_decision.




## OpenAPI

````yaml /api/openapi.json post /v1/decisions/{decisionSlug}/retire
openapi: 3.0.0
info:
  title: Erdo API
  description: >-
    Erdo's REST API: query and write datasets, run agents, manage threads,
    integrations, pages, evals, workstreams, experiments, and bounded outreach.
    Authenticate with a Bearer API key (erdo_api_...) or scoped token
    (erdo_token_...).
  version: '2026-10-27'
servers:
  - url: https://api.erdo.ai
    description: Production
security:
  - bearerAuth: []
paths:
  /v1/decisions/{decisionSlug}/retire:
    post:
      summary: |
        RetireDecisionAPI mirrors erdo_retire_decision.
      operationId: POST:mcp.RetireDecisionAPI
      parameters:
        - allowEmptyValue: true
          explode: false
          in: path
          name: decisionSlug
          required: true
          schema:
            type: string
          style: simple
      requestBody:
        content:
          application/json:
            schema:
              properties:
                organization_slug:
                  type: string
                reason:
                  type: string
              type: object
              required:
                - reason
        required: true
      responses:
        '200':
          content:
            application/json:
              schema:
                properties:
                  created:
                    type: boolean
                  decision:
                    $ref: '#/components/schemas/types.DecisionSummary'
                  retirement:
                    $ref: '#/components/schemas/types.DecisionSummary'
                type: object
          description: Success response
        default:
          $ref: '#/components/responses/APIError'
components:
  schemas:
    types.DecisionSummary:
      description: >
        continuing agent and a returning operator read.


        It is the same shape for both audiences on purpose. The agent's copy of
        what the organization has committed to cannot be the only one, or a
        human coming back to the workstream has no way to check what it is
        acting on — so the projection carries decision, rationale, authority,
        execution and supersession, and both surfaces render those five facts
        rather than each deriving their own.


        It is deliberately not the whole record: the envelope's declared
        effects, its per-action inputs and its measurement contract are a
        drill-in, and putting them here would push the ledger read past what a
        model can usefully hold.
      properties:
        age_seconds:
          format: int64
          type: integer
        agent_run_id:
          format: uuid
          type: string
        alternatives_considered:
          description: >
            before proposing this — the WHY's companion, so a reader can tell a
            choice from the only idea anyone had. Empty is ordinary: most calls
            had no real alternative, and the record says so rather than
            inventing one.
          title: >
            AlternativesConsidered is the producer's account of what else it
            weighed
          type: string
        applicability:
          description: >
            that outlives the work it authorized, or an authorization for
            exactly the actions it named. It travels with the summary because
            the two are read differently — a standing decision applies until its
            review deadline or explicit retirement, while a one\_shot in the
            current list is work still in flight to see through, not a strategy
            to keep running.
          title: >
            Applicability is standing or one_shot: whether this decision is a
            course
          type: string
        approval_id:
          description: >
            approval producer family. It travels on the row so the join runs in
            both directions from one read: a caller holding an approval filters
            the list by it, and a caller reading a page of decisions can index
            them by the approvals they answer without a call per row.
          format: uuid
          title: >
            ApprovalID is the ask this decision was made on, present only for
            the
          type: string
        authorized_at:
          format: date-time
          type: string
        decided_by_name:
          description: >
            name, else email), so a surface can say "X did Y" without carrying a
            user lookup of its own. Empty when no human decided (an agent or a
            policy did), or when the id could not be resolved in the caller's
            organization — a manager acting into a client org is the case that
            does not resolve, and the raw id stays on DecidedByUserID for that.
            It is display-only and never a filter.
          title: >
            DecidedByName is the human decider resolved to a name (display name,
            else
          type: string
        decided_by_user_id:
          format: uuid
          type: string
        decider_kind:
          description: |
            deterministic\_policy, safe\_default or system.
          title: |
            DeciderKind is who exercised the judgement: human, llm_agent,
          type: string
        decider_rationale:
          description: >
            they supplied any. Usually empty — approving a card records no
            sentence.
          title: >
            DeciderRationale is the deciding human's own words about the answer,
            when
          type: string
        decision_class:
          description: >
            (\`paid\_media.ad\_group.pause\`), provider-agnostic and stable
            across the tools that implement it. Source is the producer family
            that recorded it.
          title: |
            DecisionClass is what KIND of decision this is
          type: string
        evidence_kind:
          description: >
            specified state exists), experimental (a controlled comparison), or
            observational (a before/after movement with no control). Empty when
            the settled effects disagree — a decision with one experimental and
            one deterministic result has no single kind, and picking one would
            attach the stronger claim to both.
          title: |
            EvidenceKind is what KIND of evidence settled it: deterministic (the
          type: string
        execution_status:
          description: >
            change the decision authorized actually reached the outside world.
            pending | started | succeeded | failed | unknown, and empty when the
            decision authorized no action at all.
          title: >
            ExecutionStatus rolls the child actions up into one word: whether
            the
          type: string
        exit_condition:
          type: string
        has_pending_effects:
          description: >
            outcome. An effective decision can legitimately be in this state
            between its action landing and the settlement sweep starting
            measurement, so clients must not infer that an empty outcome means
            the decision is finished.
          title: >
            HasPendingEffects says whether at least one measurable effect still
            owes an
          type: boolean
        lapsed:
          type: boolean
        outcome_label:
          description: >
            says the same thing about the same row rather than each deriving its
            own vocabulary from the pair above. Only an experiment may say a
            change "worked"; deterministic evidence says "confirmed" and
            observational says "moved as expected".


            Empty whenever the pair cannot support one phrase — mixed outcomes,
            mixed evidence kinds — because there is no honest single sentence
            for those and the per-effect labels in the detail read are the
            answer.
          title: >
            OutcomeLabel is the server's own words for this outcome, so every
            surface
          type: string
        outcome_status:
          description: >
            not\_met, inconclusive, or \`mixed\` when they disagree. Empty while
            nothing has settled, which is a different fact from inconclusive —
            one says the answer is not in yet, the other says the evidence could
            not produce one.


            Effects that are unmeasurable, censored, or parked in
            measurement\_unavailable contribute nothing here. They are coverage,
            they are visible as such in the detail read and the scorecard, and
            folding them in would let a decision nobody could measure read as
            one that did not work.
          title: >
            OutcomeStatus rolls this decision's SETTLED effects into one word:
            met,
          type: string
        proposed_at:
          format: date-time
          type: string
        rejected_at:
          description: >
            whose status is \`rejected\`.


            It is nullable when the source has no trustworthy answer fact, and
            is never inferred from a write clock.
          format: date-time
          title: >
            RejectedAt is when the proposal was refused, and it is present only
            on a

            decision
          type: string
        review_by:
          description: >
            never a lifecycle status or a destructive rewrite of the original
            record.
          format: date-time
          title: >
            ReviewBy includes the legacy creation-time fallback. Lapsed is
            derived,
          type: string
        slug:
          type: string
        source:
          type: string
        status:
          type: string
        subject_kind:
          description: |
            names it — a campaign, a page, a lead form.
          title: >
            SubjectKind / SubjectLabel name what the decision is about, as the
            operator
          type: string
        subject_label:
          type: string
        superseded_by_decision_slug:
          description: >
            decision that later replaced this one. It carries the same
            past-authorization rule the currentness read applies — a reversal
            somebody PROPOSED and a human then refused has not replaced
            anything, and showing it here would report a course as retired
            exactly when the human voted to keep it.
          title: >
            SupersededByDecisionSlug is the other direction of the same link:
            the
          type: string
        supersedes_decision_slug:
          description: >
            the producer declared the link explicitly — a reversal states what
            it reverses, and nothing infers it from two decisions sharing a
            subject.
          title: >
            SupersedesDecisionSlug names the decision this one replaced. Set
            only when
          type: string
        what:
          description: >
            PRODUCER's rationale — the argument the proposal was made on. When a
            human gave their own reason for the answer it is in
            DeciderRationale, never merged into this one: reading a proposal's
            argument as the approver's reason for accepting it is how a record
            starts attributing motives.
          title: |
            What is the decision in one line of business English; Why is the
          type: string
        why:
          type: string
        workstream_id:
          description: >
            filed under and the run that proposed it. They travel on the summary
            so a surface rendering one row can link the workstream without a
            second read — the same reason ApprovalID travels. Both are optional
            in fact as well as shape: an org-level decision belongs to no
            workstream, and a deterministic producer may have no run.
          format: uuid
          title: >
            WorkstreamID / AgentRunID are provenance: the workstream the
            decision was
          type: string
      title: |
        DecisionSummary is the compact projection of one decision that both a
      type: object
  responses:
    APIError:
      content:
        application/json:
          schema:
            externalDocs:
              url: https://pkg.go.dev/encore.dev/beta/errs#Error
            properties:
              code:
                description: Error code
                example: not_found
                externalDocs:
                  url: https://pkg.go.dev/encore.dev/beta/errs#ErrCode
                type: string
              details:
                description: Error details
                type: object
              message:
                description: Error message
                type: string
            title: APIError
            type: object
      description: Error response
  securitySchemes:
    bearerAuth:
      type: http
      scheme: bearer
      description: An Erdo API key (erdo_api_...) or scoped token (erdo_token_...).

````

This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.