{
 "openapi": "3.1.0",
 "info": {
  "title": "Mend API",
  "version": "1.0.0",
  "description": "Mend repairs broken JSON (trailing commas, single quotes, comments, Python literals, code fences, truncated output), tells you exactly where invalid JSON breaks, and outlines or queries big payloads. Runs in your browser, no account. Public, no API key. Rate limited.",
  "contact": {
   "name": "Clawhard Studio",
   "url": "https://clawhard.com",
   "email": "support@clawhard.com"
  }
 },
 "servers": [
  {
   "url": "https://mend.clawhard.com"
  }
 ],
 "paths": {
  "/api/v1/repair_json": {
   "post": {
    "operationId": "repair_json",
    "summary": "Repair broken or LLM-generated JSON",
    "description": "Use when JSON from an LLM, API, log, config or copy-paste fails to parse (JSON.parse error, \"Unexpected token\", \"Expecting property name\"), or the user pastes JSON with trailing commas, single quotes, unquoted keys, comments, Python True/False/None, NaN, missing commas or brackets, a ```json…",
    "x-full-description": "Use when JSON from an LLM, API, log, config or copy-paste fails to parse (JSON.parse error, \"Unexpected token\", \"Expecting property name\"), or the user pastes JSON with trailing commas, single quotes, unquoted keys, comments, Python True/False/None, NaN, missing commas or brackets, a ```json fence, text around it, or output that was cut off. Deterministic repair: returns valid, formatted JSON plus a list of every fix with line and column. Values are never rewritten, so big numbers, number formatting and key order stay exactly as written (re-asking a model to \"fix the JSON\" changes data and costs tokens). If the text is already valid it says so. Up to 100,000 characters. Returns: {summary, ok, repaired, was_already_valid, fix_count, fixes:[{type, message, line, col}], warnings, json, type, depth, values, keys, chars_in, chars_out, open_url}",
    "x-openai-isConsequential": false,
    "responses": {
     "200": {
      "description": "Result. Always has \"ok\": true.",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          }
         },
         "additionalProperties": true
        }
       }
      }
     },
     "400": {
      "description": "Bad input. {\"ok\":false,\"error\":\"...\"}"
     },
     "429": {
      "description": "Rate limited. Retry after the Retry-After header."
     }
    },
    "requestBody": {
     "required": true,
     "content": {
      "application/json": {
       "schema": {
        "type": "object",
        "properties": {
         "text": {
          "type": "string",
          "minLength": 1,
          "maxLength": 100000,
          "description": "The broken JSON, or any text that contains JSON (a chat reply, a log line, a code block)."
         },
         "indent": {
          "type": "integer",
          "minimum": 0,
          "maximum": 8,
          "description": "Spaces per indent level in the output. Default 2. Use 0 for one minified line."
         },
         "sort_keys": {
          "type": "boolean",
          "description": "Sort object keys alphabetically. Default false (keep the original order)."
         }
        },
        "required": [
         "text"
        ]
       }
      }
     }
    }
   }
  },
  "/api/v1/check_json": {
   "post": {
    "operationId": "check_json",
    "summary": "Validate JSON and locate the exact error",
    "description": "Use when you need to know whether text is strictly valid JSON, and if not, exactly where it breaks. Strict RFC 8259 check (the same accept/reject as JSON.parse). Returns line, column, the offending line with a caret and whether Mend can repair it. Use mend_repair_json to fix it.",
    "x-full-description": "Use when you need to know whether text is strictly valid JSON, and if not, exactly where it breaks. Strict RFC 8259 check (the same accept/reject as JSON.parse). Returns line, column, the offending line with a caret and whether Mend can repair it. Use mend_repair_json to fix it. Up to 100,000 characters. Returns: {summary, valid, type, depth, values, keys, top_level, warnings, chars} or {summary, valid:false, error:{message, position, line, column, line_text, caret}, repairable, fixes_needed}",
    "x-openai-isConsequential": false,
    "responses": {
     "200": {
      "description": "Result. Always has \"ok\": true.",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          }
         },
         "additionalProperties": true
        }
       }
      }
     },
     "400": {
      "description": "Bad input. {\"ok\":false,\"error\":\"...\"}"
     },
     "429": {
      "description": "Rate limited. Retry after the Retry-After header."
     }
    },
    "requestBody": {
     "required": true,
     "content": {
      "application/json": {
       "schema": {
        "type": "object",
        "properties": {
         "text": {
          "type": "string",
          "minLength": 1,
          "maxLength": 100000,
          "description": "The text to validate."
         }
        },
        "required": [
         "text"
        ]
       }
      }
     }
    }
   }
  },
  "/api/v1/outline_json": {
   "post": {
    "operationId": "outline_json",
    "summary": "Outline the structure of a large JSON payload",
    "description": "Use before reading a big JSON response, log or export into context: returns a compact outline of the structure (keys, types, array lengths, one example per repeated shape) so you can plan a query without spending tokens on the whole document. Repairs the JSON first if needed.",
    "x-full-description": "Use before reading a big JSON response, log or export into context: returns a compact outline of the structure (keys, types, array lengths, one example per repeated shape) so you can plan a query without spending tokens on the whole document. Repairs the JSON first if needed. Follow with mend_query_json to pull only the values you need. Up to 100,000 characters. Returns: {summary, type, depth, values, keys, top_level, outline, lines, chars_in, repaired_input, open_url}",
    "x-openai-isConsequential": false,
    "responses": {
     "200": {
      "description": "Result. Always has \"ok\": true.",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          }
         },
         "additionalProperties": true
        }
       }
      }
     },
     "400": {
      "description": "Bad input. {\"ok\":false,\"error\":\"...\"}"
     },
     "429": {
      "description": "Rate limited. Retry after the Retry-After header."
     }
    },
    "requestBody": {
     "required": true,
     "content": {
      "application/json": {
       "schema": {
        "type": "object",
        "properties": {
         "text": {
          "type": "string",
          "minLength": 1,
          "maxLength": 100000,
          "description": "The JSON (or JSON-ish text)."
         },
         "max_depth": {
          "type": "integer",
          "minimum": 1,
          "maximum": 10,
          "description": "How many levels to expand. Default 4."
         },
         "max_items": {
          "type": "integer",
          "minimum": 1,
          "maximum": 20,
          "description": "How many array items to show when items differ. Default 6."
         }
        },
        "required": [
         "text"
        ]
       }
      }
     }
    }
   }
  },
  "/api/v1/query_json": {
   "post": {
    "operationId": "query_json",
    "summary": "Extract values from JSON by path",
    "description": "Use when you need specific fields from a JSON document without reading all of it: $.users[0].name, $.items[*].id, $.a.b[-1], $.list[1:3], $..email (recursive). Returns each match with its exact path, type and value. Repairs the JSON first if needed, so broken input still works.",
    "x-full-description": "Use when you need specific fields from a JSON document without reading all of it: $.users[0].name, $.items[*].id, $.a.b[-1], $.list[1:3], $..email (recursive). Returns each match with its exact path, type and value. Repairs the JSON first if needed, so broken input still works. Up to 100,000 characters. Returns: {summary, path, count, returned, truncated, matches:[{path, type, value}], repaired_input}",
    "x-openai-isConsequential": false,
    "responses": {
     "200": {
      "description": "Result. Always has \"ok\": true.",
      "content": {
       "application/json": {
        "schema": {
         "type": "object",
         "properties": {
          "ok": {
           "type": "boolean"
          }
         },
         "additionalProperties": true
        }
       }
      }
     },
     "400": {
      "description": "Bad input. {\"ok\":false,\"error\":\"...\"}"
     },
     "429": {
      "description": "Rate limited. Retry after the Retry-After header."
     }
    },
    "requestBody": {
     "required": true,
     "content": {
      "application/json": {
       "schema": {
        "type": "object",
        "properties": {
         "text": {
          "type": "string",
          "minLength": 1,
          "maxLength": 100000,
          "description": "The JSON (or JSON-ish text)."
         },
         "path": {
          "type": "string",
          "minLength": 1,
          "maxLength": 300,
          "description": "Path such as $.users[*].email, data.items[0], $..id, $.list[-1], $.list[1:3]."
         },
         "max": {
          "type": "integer",
          "minimum": 1,
          "maximum": 200,
          "description": "Maximum matches to return. Default 50."
         }
        },
        "required": [
         "text",
         "path"
        ]
       }
      }
     }
    }
   }
  }
 },
 "externalDocs": {
  "description": "llms.txt",
  "url": "https://mend.clawhard.com/llms.txt"
 }
}