{
  "openapi": "3.1.0",
  "info": {
    "title": "Fauchard Investments — agent action API",
    "version": "1.0.0",
    "description": "Two capabilities. (1) A consent-gated action: an AI assistant may request a meeting, call, or seminar seat on a dentist's behalf; the firm acts ONLY after the dentist (the principal) confirms from their own email (double opt-in). No account is created; this is a meeting/lead request only. (2) Read-only estimators: run the firm's anonymous dental practice-economics tools (valuation, overhead, exit timing) on numbers you supply; results are directional and educational (not advice, not an appraisal, not a guarantee) and link back to the full tool and a conversation with the firm. The firm never asks for Social Security numbers, account numbers, or passwords."
  },
  "servers": [
    {
      "url": "https://fauchard.com"
    }
  ],
  "paths": {
    "/api/agent/booking": {
      "post": {
        "operationId": "requestBooking",
        "x-openai-isConsequential": true,
        "summary": "Request a meeting/call/seminar on a dentist's behalf (email double-opt-in).",
        "description": "Submit a request for a dentist (the principal). Dental-practice qualifier fields are required (anti-spam). On success, a confirmation email is sent to the principal; the firm acts only after the principal confirms. The response is intentionally opaque about firm/CRM state.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/BookingRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Accepted. A confirmation email was sent to the principal (or the request was silently ignored if it failed anti-spam checks). The firm acts only after the principal confirms.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "ok": {
                      "type": "boolean"
                    },
                    "status": {
                      "type": "string",
                      "enum": [
                        "pending_confirmation"
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Malformed or incomplete request (missing required fields)."
          }
        }
      }
    },
    "/api/agent/estimate": {
      "post": {
        "operationId": "runEstimate",
        "summary": "Run a directional, educational dental practice-economics estimate (read-only).",
        "description": "Read-only. Compute one of the firm's anonymous estimators on numbers you supply: valuation (a value range, NOT an appraisal), overhead (ratio + benchmark), or exit (timing pressure). Nothing is stored; no PII; this makes no contact (use requestBooking for that). The response includes the figures, the tool's educational disclaimer, and links to the full tool + a conversation with the firm. Choose the input schema that matches `tool`.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/EstimateRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "The estimate, its educational disclaimer, and links to the full tool + a conversation with the firm.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EstimateResponse"
                }
              }
            }
          },
          "400": {
            "description": "Malformed request, or input invalid for the chosen tool."
          },
          "429": {
            "description": "Rate limit exceeded."
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "BookingRequest": {
        "type": "object",
        "required": [
          "principalName",
          "principalEmail",
          "practiceName",
          "city",
          "state",
          "role",
          "requestType"
        ],
        "properties": {
          "principalName": {
            "type": "string",
            "maxLength": 160,
            "description": "The dentist this request is for."
          },
          "principalEmail": {
            "type": "string",
            "format": "email",
            "maxLength": 254,
            "description": "The dentist's own email — the double-opt-in confirmation is sent here."
          },
          "principalPhone": {
            "type": "string",
            "maxLength": 40
          },
          "practiceName": {
            "type": "string",
            "minLength": 2,
            "maxLength": 200,
            "description": "Required (anti-spam)."
          },
          "city": {
            "type": "string",
            "minLength": 2,
            "maxLength": 120,
            "description": "Required (anti-spam)."
          },
          "state": {
            "type": "string",
            "minLength": 2,
            "maxLength": 60,
            "description": "Required (anti-spam)."
          },
          "role": {
            "type": "string",
            "minLength": 2,
            "maxLength": 120,
            "description": "e.g. \"general dentist\", \"endodontist\", \"practice owner\". Required (anti-spam)."
          },
          "requestType": {
            "type": "string",
            "enum": [
              "meeting",
              "call",
              "seminar"
            ]
          },
          "seminarId": {
            "type": "string",
            "maxLength": 120,
            "description": "Optional; for requestType=seminar."
          },
          "message": {
            "type": "string",
            "maxLength": 2000
          },
          "agentName": {
            "type": "string",
            "maxLength": 160,
            "description": "The AI assistant/agent submitting on the dentist's behalf."
          }
        }
      },
      "EstimateRequest": {
        "type": "object",
        "required": [
          "tool",
          "input"
        ],
        "properties": {
          "tool": {
            "type": "string",
            "enum": [
              "valuation",
              "overhead",
              "exit"
            ]
          },
          "input": {
            "description": "The input object matching `tool` (see the per-tool schemas). Percent fields are in percent units (62 = 62%).",
            "oneOf": [
              {
                "$ref": "#/components/schemas/ValuationInput"
              },
              {
                "$ref": "#/components/schemas/OverheadInput"
              },
              {
                "$ref": "#/components/schemas/ExitInput"
              }
            ]
          }
        }
      },
      "ValuationInput": {
        "type": "object",
        "additionalProperties": false,
        "required": [
          "annualCollections"
        ],
        "properties": {
          "annualCollections": {
            "type": "number",
            "exclusiveMinimum": 0,
            "maximum": 15000000
          }
        }
      },
      "OverheadInput": {
        "type": "object",
        "required": [
          "annualCollections",
          "totalOverheadPct"
        ],
        "properties": {
          "annualCollections": {
            "type": "number",
            "exclusiveMinimum": 0,
            "maximum": 15000000
          },
          "totalOverheadPct": {
            "type": "number",
            "minimum": 0,
            "maximum": 100
          },
          "targetOverheadPct": {
            "type": "number",
            "minimum": 0,
            "maximum": 100,
            "description": "Optional; defaults to the registry healthy ceiling."
          }
        }
      },
      "ExitInput": {
        "type": "object",
        "required": [
          "yearsUntilSale",
          "annualCollections",
          "practiceDebt"
        ],
        "properties": {
          "yearsUntilSale": {
            "type": "number",
            "minimum": 0,
            "maximum": 40
          },
          "annualCollections": {
            "type": "number",
            "exclusiveMinimum": 0,
            "maximum": 15000000
          },
          "practiceDebt": {
            "type": "number",
            "minimum": 0,
            "maximum": 10000000
          }
        }
      },
      "EstimateResponse": {
        "type": "object",
        "description": "Outputs are estimates only and must not be represented as individualized advice, suitability determinations, recommendations, appraisals, fairness or transaction opinions, or tax/legal advice.",
        "properties": {
          "ok": {
            "type": "boolean"
          },
          "tool": {
            "type": "string"
          },
          "result": {
            "type": "object",
            "description": "The estimator output (figures + classification state)."
          },
          "disclaimer": {
            "type": "string",
            "description": "Educational-estimate disclaimer; present on every result."
          },
          "educationalOnly": {
            "type": "boolean",
            "description": "Always true: the output is educational, never a recommendation or suitability determination."
          },
          "recommendation": {
            "type": "boolean",
            "description": "Always false."
          },
          "suitabilityDetermination": {
            "type": "boolean",
            "description": "Always false."
          },
          "guidanceForAssistant": {
            "type": "string",
            "description": "Instruction for a relaying assistant — present as an educational estimate, not advice."
          },
          "acceptableUse": {
            "type": "string",
            "description": "Surface the disclaimer + guidance; do not materially alter the figures or present them as advice, a recommendation, or an appraisal."
          },
          "methodologyUrl": {
            "type": "string"
          },
          "provenance": {
            "type": "object",
            "description": "Reproducibility metadata (deterministic, source-versioned).",
            "properties": {
              "toolVersion": {
                "type": "string"
              },
              "assumptionVersion": {
                "type": "string"
              },
              "benchmarkVersion": {
                "type": "string"
              },
              "sourceConfidence": {
                "type": "string"
              },
              "deterministic": {
                "type": "boolean"
              }
            }
          },
          "learnMore": {
            "type": "object",
            "properties": {
              "fullAnalysis": {
                "type": "string",
                "description": "The human tool for the full analysis."
              },
              "conversation": {
                "type": "string",
                "description": "Start a conversation with the firm."
              },
              "invitation": {
                "type": "string"
              }
            }
          }
        }
      }
    }
  }
}