{
 "openapi": "3.1.0",
 "info": {
  "title": "Alishahi Insurance quote requests",
  "version": "1.0.0",
  "description": "Request an insurance quote from Alishahi Insurance, an independent broker (Sam Alishahi; CA License #4348151, NPN 21022298, licensed in all 50 states and Washington, DC). Built for AI assistants and agents acting for a person: no sign-up, no key, no bot check. Ask the person, confirm they want to be contacted, then submit. The person gets their application link by email right away and an update at each step. No prices are given and no coverage is bound until confirmed in writing. Never send Social Security, driver's license, bank or card numbers."
 },
 "servers": [
  {
   "url": "https://alishahiinsurance.com"
  }
 ],
 "paths": {
  "/agent/coverages.json": {
   "get": {
    "operationId": "listCoverages",
    "summary": "List the coverages Alishahi Insurance quotes, with a page for each.",
    "responses": {
     "200": {
      "description": "Coverages",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "broker": {
           "type": "string"
          },
          "license": {
           "type": "string"
          },
          "coverages": {
           "type": "array",
           "items": {
            "type": "object",
            "properties": {
             "coverage": {
              "type": "string"
             },
             "page": {
              "type": "string"
             },
             "summary": {
              "type": "string"
             }
            }
           }
          }
         }
        }
       }
      }
     }
    }
   }
  },
  "/api/agent/questions": {
   "get": {
    "operationId": "getQuoteQuestions",
    "summary": "Get the questions to ask for one coverage. All are optional.",
    "parameters": [
     {
      "name": "coverage",
      "in": "query",
      "required": true,
      "schema": {
       "type": "string"
      },
      "description": "A coverage name from listCoverages, e.g. Homeowners or Tow truck."
     }
    ],
    "responses": {
     "200": {
      "description": "Questions",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "coverage": {
           "type": "string"
          },
          "questions": {
           "type": "array",
           "items": {
            "type": "object",
            "properties": {
             "name": {
              "type": "string"
             },
             "type": {
              "type": "string"
             },
             "choices": {
              "type": "array",
              "items": {
               "type": "string"
              }
             }
            }
           }
          }
         }
        }
       }
      }
     },
     "404": {
      "description": "Unknown coverage"
     }
    }
   }
  },
  "/api/agent/quote": {
   "post": {
    "operationId": "submitQuoteRequest",
    "summary": "Send the person's quote request to Alishahi Insurance. Only after they confirm they want to be contacted. Use real values from the person; if a field is unknown, leave it out.",
    "x-openai-isConsequential": true,
    "requestBody": {
     "required": true,
     "content": {
      "application/json": {
       "schema": {
        "type": "object",
        "required": [
         "coverage",
         "name",
         "email",
         "contact_consent"
        ],
        "properties": {
         "coverage": {
          "type": "string",
          "description": "Coverage name from listCoverages."
         },
         "other_coverages": {
          "type": "array",
          "items": {
           "type": "string"
          },
          "description": "Other coverages from listCoverages the person wants on the same request (for example General liability with Commercial auto)."
         },
         "name": {
          "type": "string"
         },
         "phone": {
          "type": "string",
          "description": "Phone number (optional; everything also goes by email)."
         },
         "email": {
          "type": "string",
          "description": "The person's email; their application link and updates go here."
         },
         "zip": {
          "type": "string"
         },
         "answers": {
          "type": "object",
          "additionalProperties": {
           "type": "string"
          },
          "description": "Answers keyed by question name from getQuoteQuestions. Select questions must use one of the listed choices."
         },
         "notes": {
          "type": "string",
          "description": "Anything else Sam should know, such as deadlines or lender requirements."
         },
         "contact_consent": {
          "type": "boolean",
          "description": "True only after the person confirmed they want Sam Alishahi to contact them by phone or email."
         }
        }
       }
      }
     }
    },
    "responses": {
     "200": {
      "description": "Sent",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          },
          "reference": {
           "type": "string"
          },
          "message": {
           "type": "string"
          }
         }
        }
       }
      }
     },
     "400": {
      "description": "Missing or invalid information; the message says what to ask for",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          },
          "error": {
           "type": "string"
          },
          "message": {
           "type": "string"
          }
         }
        }
       }
      }
     },
     "422": {
      "description": "validation_failed: nothing was sent. Each entry in fields says which value to fix and how; ask the person, don't invent values, then send again.",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          },
          "error": {
           "type": "string"
          },
          "fields": {
           "type": "array",
           "items": {
            "type": "object",
            "properties": {
             "field": {
              "type": "string"
             },
             "code": {
              "type": "string"
             },
             "message": {
              "type": "string"
             }
            }
           }
          },
          "message": {
           "type": "string"
          }
         }
        }
       }
      }
     },
     "429": {
      "description": "rate_limited: too many requests; retry after the Retry-After seconds or ask the person to call (424) 552-4545.",
      "headers": {
       "Retry-After": {
        "schema": {
         "type": "integer"
        }
       }
      },
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          },
          "error": {
           "type": "string"
          },
          "retry_after": {
           "type": "integer"
          },
          "message": {
           "type": "string"
          }
         }
        }
       }
      }
     }
    }
   }
  },
  "/api/agent/application": {
   "get": {
    "operationId": "getApplication",
    "summary": "Read a quote application Sam started from the person's email: every field, its choices, what's filled in and what's still required.",
    "description": "The id and t values are in the link in Sam Alishahi's reply email. Add format=text for a plain-text version.",
    "parameters": [
     {
      "name": "id",
      "in": "query",
      "required": true,
      "schema": {
       "type": "string"
      },
      "description": "application_id from Sam's email (Reference APP-<id>)."
     },
     {
      "name": "t",
      "in": "query",
      "required": true,
      "schema": {
       "type": "string"
      },
      "description": "The token from the link in Sam's email."
     },
     {
      "name": "format",
      "in": "query",
      "required": false,
      "schema": {
       "type": "string",
       "enum": [
        "json",
        "text"
       ]
      }
     }
    ],
    "responses": {
     "200": {
      "description": "The application",
      "content": {
       "application/json": {
        "schema": {
         "$ref": "#/components/schemas/Application"
        }
       }
      }
     },
     "404": {
      "description": "Link not valid"
     }
    }
   },
   "post": {
    "operationId": "completeApplication",
    "summary": "Add the person's answers to the application. Only send what the person told you or confirmed.",
    "x-openai-isConsequential": true,
    "parameters": [
     {
      "name": "id",
      "in": "query",
      "required": true,
      "schema": {
       "type": "string"
      }
     },
     {
      "name": "t",
      "in": "query",
      "required": true,
      "schema": {
       "type": "string"
      }
     }
    ],
    "requestBody": {
     "required": true,
     "content": {
      "application/json": {
       "schema": {
        "type": "object",
        "required": [
         "answers"
        ],
        "properties": {
         "answers": {
          "type": "object",
          "additionalProperties": {
           "type": "string"
          },
          "description": "Answers keyed by field name. Select fields take one of their choices; dates are YYYY-MM-DD; numbers are digits."
         },
         "notes": {
          "type": "string",
          "description": "Anything else the person wants Sam to know."
         },
         "submit": {
          "type": "boolean",
          "description": "True when the person is done, even if optional fields are blank."
         }
        }
       }
      }
     }
    },
    "responses": {
     "200": {
      "description": "The updated application, with saved and rejected answers",
      "content": {
       "application/json": {
        "schema": {
         "$ref": "#/components/schemas/Application"
        }
       }
      }
     },
     "404": {
      "description": "Link not valid"
     },
     "429": {
      "description": "Too many updates today"
     }
    }
   }
  },
  "/api/who-insures": {
   "post": {
    "operationId": "whoIsLikelyToInsure",
    "summary": "Who is likely to insure a described risk: admitted carriers that write the line in the state first, then surplus lines, then the market of last resort, each with a reason, from state regulators' public lists, premium by line, published appetite rules and last-resort plans. Never a price or a guarantee; ends with the next step, a quote request through Alishahi Insurance, which Sam sends to the insurers he works with that fit the risk. A listed company isn't necessarily one he is appointed with.",
    "requestBody": {
     "required": true,
     "content": {
      "application/json": {
       "schema": {
        "type": "object",
        "required": [
         "scenario"
        ],
        "properties": {
         "scenario": {
          "type": "string",
          "description": "What they need insured, where, and the facts an underwriter would weigh (claims, cancellations, age, occupancy, hazards)"
         },
         "state": {
          "type": "string",
          "description": "Two-letter state code if known"
         }
        }
       }
      }
     }
    },
    "responses": {
     "200": {
      "description": "Reading of the scenario, ranked likely insurers with reasons, what makes it harder, what to prepare, next step, directory pages to cite",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "read": {
           "type": "object"
          },
          "answer": {
           "type": "object",
           "properties": {
            "summary": {
             "type": "string"
            },
            "likely": {
             "type": "array",
             "items": {
              "type": "object",
              "properties": {
               "name": {
                "type": "string"
               },
               "type": {
                "type": "string"
               },
               "why": {
                "type": "string"
               },
               "confidence": {
                "type": "string"
               },
               "url": {
                "type": "string"
               }
              }
             }
            },
            "harder_because": {
             "type": "array",
             "items": {
              "type": "string"
             }
            },
            "prepare": {
             "type": "array",
             "items": {
              "type": "string"
             }
            },
            "next_step": {
             "type": "string"
            }
           }
          },
          "pages": {
           "type": "array"
          },
          "quote_url": {
           "type": "string"
          },
          "cite": {
           "type": "string"
          }
         }
        }
       }
      }
     },
     "429": {
      "description": "Rate limited (20 an hour per address)"
     }
    }
   }
  },
  "/api/directory/company/{naic}": {
   "get": {
    "operationId": "directoryCompany",
    "summary": "One insurer by NAIC number: admitted or surplus lines status in each state loaded, licensed lines, premium rank by line, Treasury surety listing, page to cite.",
    "parameters": [
     {
      "name": "naic",
      "in": "path",
      "required": true,
      "schema": {
       "type": "string"
      }
     }
    ],
    "responses": {
     "200": {
      "description": "Company record"
     },
     "404": {
      "description": "Not on the lists loaded"
     }
    }
   }
  },
  "/api/directory/search": {
   "get": {
    "operationId": "directorySearch",
    "summary": "Insurers by name or NAIC prefix (up to 50).",
    "parameters": [
     {
      "name": "q",
      "in": "query",
      "required": true,
      "schema": {
       "type": "string"
      }
     }
    ],
    "responses": {
     "200": {
      "description": "Matches"
     }
    }
   }
  },
  "/api/directory/state/{state}": {
   "get": {
    "operationId": "directoryState",
    "summary": "Every P&C insurer on a state's regulator lists; filter with status=ad|sl and line=<line_key>.",
    "parameters": [
     {
      "name": "state",
      "in": "path",
      "required": true,
      "schema": {
       "type": "string"
      }
     },
     {
      "name": "status",
      "in": "query",
      "schema": {
       "type": "string",
       "enum": [
        "ad",
        "sl"
       ]
      }
     },
     {
      "name": "line",
      "in": "query",
      "schema": {
       "type": "string"
      }
     }
    ],
    "responses": {
     "200": {
      "description": "Companies"
     }
    }
   }
  },
  "/api/directory/state/{state}/{line}": {
   "get": {
    "operationId": "directoryStateLine",
    "summary": "Who writes a line in a state, ranked by premium where the regulator publishes every company.",
    "parameters": [
     {
      "name": "state",
      "in": "path",
      "required": true,
      "schema": {
       "type": "string"
      }
     },
     {
      "name": "line",
      "in": "path",
      "required": true,
      "schema": {
       "type": "string"
      }
     }
    ],
    "responses": {
     "200": {
      "description": "Companies"
     }
    }
   }
  },
  "/api/directory": {
   "get": {
    "operationId": "directoryAbout",
    "summary": "What the insurance company directory holds: counts, states loaded, line keys, downloads.",
    "responses": {
     "200": {
      "description": "Index"
     }
    }
   }
  }
 },
 "components": {
  "schemas": {
   "Application": {
    "type": "object",
    "properties": {
     "application_id": {
      "type": "string"
     },
     "coverage": {
      "type": "string"
     },
     "status": {
      "type": "string",
      "enum": [
       "needs_information",
       "ready_to_submit",
       "complete"
      ]
     },
     "missing_required": {
      "type": "array",
      "items": {
       "type": "string"
      }
     },
     "fields": {
      "type": "array",
      "items": {
       "type": "object",
       "properties": {
        "name": {
         "type": "string"
        },
        "label": {
         "type": "string"
        },
        "type": {
         "type": "string"
        },
        "choices": {
         "type": "array",
         "items": {
          "type": "string"
         }
        },
        "required": {
         "type": "boolean"
        },
        "value": {
         "type": [
          "string",
          "null"
         ]
        },
        "group": {
         "type": "string"
        }
       }
      }
     },
     "how_to_complete": {
      "type": "object"
     },
     "rules": {
      "type": "array",
      "items": {
       "type": "string"
      }
     },
     "saved": {
      "type": "array",
      "items": {
       "type": "string"
      }
     },
     "rejected": {
      "type": "array",
      "items": {
       "type": "object",
       "properties": {
        "field": {
         "type": "string"
        },
        "error": {
         "type": "string"
        },
        "choices": {
         "type": "array",
         "items": {
          "type": "string"
         }
        }
       }
      }
     },
     "message": {
      "type": "string"
     }
    }
   }
  }
 }
}