{
  "openapi": "3.1.0",
  "info": {
    "title": "MemoryPlugin",
    "version": "1.0.0",
    "description": "API for managing and querying user memories"
  },
  "servers": [
    {
      "url": "https://www.memoryplugin.com"
    }
  ],
  "paths": {
    "/api/memory": {
      "post": {
        "summary": "Store a new memory",
        "operationId": "AddNewMemory",
        "x-openai-isConsequential": false,
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/MemoryInput"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Memory stored successfully",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/SuccessResponse"
                }
              }
            }
          },
          "400": {
            "description": "Bad request",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      },
      "get": {
        "summary": "Query or retrieve memories.",
        "operationId": "GetMemories",
        "parameters": [
          {
            "name": "query",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Search query for memories. You will receive the 5 most relevant memories."
          },
          {
            "name": "all",
            "in": "query",
            "schema": {
              "type": "boolean"
            },
            "description": "Fetch all memories"
          },
          {
            "name": "latest",
            "in": "query",
            "schema": {
              "type": "boolean"
            },
            "description": "Fetch latest memories"
          },
          {
            "name": "count",
            "in": "query",
            "schema": {
              "type": "integer",
              "default": 10
            },
            "description": "Number of memories to retrieve, use with latest=true to limit the number of memories retrieved"
          },
          {
            "name": "v",
            "in": "query",
            "schema": {
              "type": "number",
              "default": 2
            },
            "description": "API version - current is 2"
          },
          {
            "name": "source",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Client source identifier (e.g., 'chatgpt' for ChatGPT requests)"
          },
          {
            "name": "skip",
            "in": "query",
            "schema": {
              "type": "integer",
              "default": 0,
              "minimum": 0
            },
            "description": "Number of memories to skip for pagination. Zero-indexed: skip=0 starts from first memory, skip=10 skips first 10 memories and starts from 11th. Used primarily with token limiting to load additional memories beyond the initial response."
          }
        ],
        "responses": {
          "200": {
            "description": "Successful response",
            "content": {
              "application/json": {
                "schema": {
                  "oneOf": [
                    {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    },
                    {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Memory"
                      }
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "description": "Bad request",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/Memory"
                  }
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/buckets": {
      "get": {
        "summary": "List all memory buckets",
        "operationId": "ListBuckets",
        "parameters": [
          {
            "name": "v",
            "in": "query",
            "schema": {
              "type": "number",
              "default": 2
            },
            "description": "API version - current is 2"
          },
          {
            "name": "source",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Client source identifier (e.g., 'chatgpt' for ChatGPT requests)"
          }
        ],
        "responses": {
          "200": {
            "description": "List of memory buckets",
            "content": {
              "application/json": {
                "schema": {
                  "type": "array",
                  "items": {
                    "$ref": "#/components/schemas/Bucket"
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      },
      "post": {
        "summary": "Create a new bucket",
        "operationId": "CreateBucket",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "name": {
                    "type": "string",
                    "description": "Name of the bucket to create"
                  },
                  "source": {
                    "type": "string",
                    "description": "Client source identifier (e.g., 'chatgpt' for ChatGPT requests)"
                  }
                },
                "required": ["name"]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Bucket created successfully",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "enum": ["Bucket created successfully"]
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/v2/memory/update": {
      "post": {
        "summary": "Edit a memory's text or move memories between buckets",
        "operationId": "UpdateOrMoveMemories",
        "x-openai-isConsequential": true,
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "oneOf": [
                  { "$ref": "#/components/schemas/SingleMemoryUpdate" },
                  { "$ref": "#/components/schemas/BulkMemoryMove" }
                ]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Memory updated or moved successfully",
            "content": {
              "application/json": {
                "schema": {
                  "oneOf": [
                    { "$ref": "#/components/schemas/SingleUpdateResponse" },
                    { "$ref": "#/components/schemas/BulkMoveResponse" }
                  ]
                }
              }
            }
          },
          "400": {
            "description": "Bad request",
            "content": {
              "application/json": {
                "schema": { "$ref": "#/components/schemas/ErrorResponse" }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": { "$ref": "#/components/schemas/ErrorResponse" }
              }
            }
          },
          "404": {
            "description": "Memory or bucket not found",
            "content": {
              "application/json": {
                "schema": { "$ref": "#/components/schemas/ErrorResponse" }
              }
            }
          }
        },
        "security": [
          { "bearerAuth": [] }
        ]
      }
    },
    "/api/v2/memory": {
      "get": {
        "summary": "Get memories and buckets in a single request",
        "operationId": "GetMemoriesAndBuckets",
        "parameters": [
          {
            "name": "bucketId",
            "in": "query",
            "schema": {
              "type": "integer"
            },
            "description": "Optional bucket ID to filter memories"
          },
          {
            "name": "count",
            "in": "query",
            "schema": {
              "type": "integer",
              "default": 10
            },
            "description": "Number of memories to retrieve"
          },
          {
            "name": "all",
            "in": "query",
            "schema": {
              "type": "boolean"
            },
            "description": "Fetch all memories"
          },
          {
            "name": "latest",
            "in": "query",
            "schema": {
              "type": "boolean"
            },
            "description": "Fetch latest memories"
          },
          {
            "name": "query",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Search query for memories"
          },
          {
            "name": "source",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Client source identifier (e.g., 'chatgpt' for ChatGPT requests)"
          },
          {
            "name": "skip",
            "in": "query",
            "schema": {
              "type": "integer",
              "default": 0,
              "minimum": 0
            },
            "description": "Number of memories to skip for pagination. Zero-indexed: skip=0 starts from first memory, skip=10 skips first 10 memories and starts from 11th. Used primarily with token limiting to load additional memories beyond the initial response."
          },
          {
            "name": "includeIds",
            "in": "query",
            "schema": {
              "type": "boolean",
              "default": false
            },
            "description": "When true, text memories are returned as objects with `id` and `text` fields instead of plain strings. Useful for clients that need to reference specific memories for edit or delete operations."
          },
          {
            "name": "contentType",
            "in": "query",
            "schema": {
              "type": "string",
              "enum": ["text", "image"]
            },
            "description": "Filter memories by content type. Use `text` for text-only memories, `image` for image-only memories. Omit to return all memories."
          }
        ],
        "responses": {
          "200": {
            "description": "Successful response with memories and buckets",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "memories": {
                      "type": "array",
                      "description": "Array of memories. Text memories are returned as plain strings (or `{id, text}` objects when `includeIds=true`). Image memories are always returned as objects with `content_type`, `image_url`, and `image_description` fields.",
                      "items": {
                        "oneOf": [
                          {
                            "type": "string",
                            "description": "Text memory (plain string format)"
                          },
                          {
                            "type": "object",
                            "description": "Text memory with ID (when includeIds=true) or image memory",
                            "properties": {
                              "id": {
                                "type": "string",
                                "description": "Memory ID (present when includeIds=true or for image memories)"
                              },
                              "text": {
                                "type": "string",
                                "description": "Memory text content. For image memories, this contains the AI-generated description."
                              },
                              "content_type": {
                                "type": "string",
                                "enum": ["text", "image"],
                                "description": "Memory type. Omitted for text memories in plain string format."
                              },
                              "image_url": {
                                "type": "string",
                                "format": "uri",
                                "description": "Signed URL to view the image. Only present for image memories. Expires after 4 hours."
                              },
                              "image_description": {
                                "type": "string",
                                "description": "AI-generated description of the image. Only present for image memories."
                              },
                              "metadata": {
                                "type": "object",
                                "properties": {
                                  "text": {
                                    "type": "string"
                                  },
                                  "createdAt": {
                                    "type": "string",
                                    "format": "date-time"
                                  },
                                  "bucketId": {
                                    "type": "integer"
                                  },
                                  "bucketName": {
                                    "type": "string"
                                  }
                                }
                              }
                            }
                          }
                        ]
                      }
                    },
                    "buckets": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/Bucket"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/chat-history/ingest/custom-online": {
      "post": {
        "summary": "Upload chat history",
        "operationId": "UploadChatHistory",
        "description": "Upload a single conversation from any platform. Supports upsert semantics — re-sending a conversation with the same ID will update it with new messages. The conversation is processed asynchronously (chunked, embedded, and indexed for search).",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CustomChatHistoryInput"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Conversation queued for processing",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ChatHistoryIngestResponse"
                }
              }
            }
          },
          "400": {
            "description": "Validation error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Internal server error",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/chat-history/inject": {
      "post": {
        "summary": "Recall chat history",
        "operationId": "RecallChatHistory",
        "description": "Search and synthesize context from the user's past AI conversations. This is the primary recall endpoint — it performs semantic search, then uses AI to synthesize matching results into a coherent summary with source citations. This is the same function powering the `recall_chat_history` tool in the MCP server.\n\nSupports parallel queries for complex topics that benefit from multiple search angles (e.g., timeline, decisions, people).",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ChatHistoryInjectInput"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Synthesized context from chat history",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ChatHistoryInjectResponse"
                }
              }
            }
          },
          "400": {
            "description": "Invalid parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/chat-history/search": {
      "post": {
        "summary": "Search chat history (raw)",
        "operationId": "SearchChatHistory",
        "description": "Perform raw semantic search across all imported chat conversations. Returns matched chunks with scores and surrounding context. For most use cases, use the Recall endpoint (`POST /api/chat-history/inject`) instead — it performs search and AI synthesis in one step.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ChatHistorySearchInput"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Search results",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ChatHistorySearchResponse"
                }
              }
            }
          },
          "400": {
            "description": "Invalid parameters",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/chat-history/chats": {
      "get": {
        "summary": "List conversations",
        "operationId": "ListConversations",
        "description": "List imported chat conversations with pagination and filtering.",
        "parameters": [
          {
            "name": "page",
            "in": "query",
            "schema": { "type": "integer", "default": 1 },
            "description": "Page number (1-indexed)."
          },
          {
            "name": "pageSize",
            "in": "query",
            "schema": { "type": "integer", "default": 25, "maximum": 100 },
            "description": "Results per page."
          },
          {
            "name": "provider",
            "in": "query",
            "schema": { "type": "string", "default": "all" },
            "description": "Filter by platform. Use 'all' for all platforms, or a specific platform ID (e.g., 'chatgpt', 'claude', 'custom')."
          },
          {
            "name": "title",
            "in": "query",
            "schema": { "type": "string" },
            "description": "Filter by conversation title (partial match)."
          },
          {
            "name": "dateFrom",
            "in": "query",
            "schema": { "type": "string", "format": "date" },
            "description": "Filter conversations created on or after this date (ISO 8601)."
          },
          {
            "name": "dateTo",
            "in": "query",
            "schema": { "type": "string", "format": "date" },
            "description": "Filter conversations created on or before this date (ISO 8601)."
          },
          {
            "name": "pinnedOnly",
            "in": "query",
            "schema": { "type": "boolean", "default": false },
            "description": "Only return pinned conversations."
          },
          {
            "name": "importId",
            "in": "query",
            "schema": { "type": "string" },
            "description": "Filter by import ID."
          }
        ],
        "responses": {
          "200": {
            "description": "Paginated conversation list",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ConversationListResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      },
      "delete": {
        "summary": "Delete conversations",
        "operationId": "DeleteConversations",
        "description": "Delete one or more conversations and their associated data (messages, chunks, vectors).",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "ids": {
                    "type": "array",
                    "items": { "type": "string" },
                    "description": "Array of conversation IDs to delete."
                  }
                },
                "required": ["ids"]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Conversations deleted",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "deleted": {
                      "type": "array",
                      "items": { "type": "string" },
                      "description": "IDs of successfully deleted conversations."
                    },
                    "count": {
                      "type": "integer",
                      "description": "Number of conversations deleted."
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/chat-history/conversation": {
      "get": {
        "summary": "Get conversation",
        "operationId": "GetConversation",
        "description": "Retrieve a specific conversation with all its messages.",
        "parameters": [
          {
            "name": "conversationId",
            "in": "query",
            "required": true,
            "schema": { "type": "string" },
            "description": "The internal conversation ID (returned from list or search endpoints)."
          }
        ],
        "responses": {
          "200": {
            "description": "Conversation with messages",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ConversationDetailResponse"
                }
              }
            }
          },
          "404": {
            "description": "Conversation not found",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/chat-history/count": {
      "get": {
        "summary": "Get conversation count",
        "operationId": "GetConversationCount",
        "description": "Returns the total count of imported conversations (excluding excluded and quota-blocked ones).",
        "responses": {
          "200": {
            "description": "Conversation count",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "count": {
                      "type": "integer",
                      "description": "Total number of active imported conversations."
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/memories/{memoryId}": {
      "delete": {
        "summary": "Delete a memory",
        "operationId": "DeleteMemory",
        "description": "Delete a single memory by its ID. Removes the memory from the database and vector store.",
        "parameters": [
          {
            "name": "memoryId",
            "in": "path",
            "required": true,
            "schema": { "type": "string" },
            "description": "The memory ID to delete."
          }
        ],
        "responses": {
          "200": {
            "description": "Memory deleted",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "enum": ["Memory deleted"]
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Memory ID is required",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    },
    "/api/memories/bulk-delete": {
      "post": {
        "summary": "Bulk delete memories",
        "operationId": "BulkDeleteMemories",
        "description": "Delete multiple memories in a single request.",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "memoryIds": {
                    "type": "array",
                    "items": { "type": "string" },
                    "description": "Array of memory IDs to delete."
                  }
                },
                "required": ["memoryIds"]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Memories deleted",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": ["message", "deletedCount", "errors"],
                  "properties": {
                    "message": { "type": "string", "description": "Always \"Memories deleted\"." },
                    "deletedCount": { "type": "integer", "description": "Number of memory rows deleted from the database. Unresolvable IDs are skipped, so this can be lower than the number of memoryIds submitted." },
                    "errors": {
                      "type": "array",
                      "description": "Per-failure details; empty on full success. A partial failure still returns 200.",
                      "items": {
                        "type": "object",
                        "required": ["memoryId", "error"],
                        "properties": {
                          "memoryId": { "type": "string", "description": "The memory ID that failed, or a batch identifier (\"zilliz_bulk\", \"supabase_bulk\") when a whole batch fails and individual IDs cannot be attributed." },
                          "error": { "type": "string", "description": "Failure reason." }
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Invalid request",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        },
        "security": [
          {
            "bearerAuth": []
          }
        ]
      }
    }
  },
  "components": {
    "schemas": {
      "MemoryInput": {
        "type": "object",
        "properties": {
          "text": {
            "type": "string",
            "description": "The memory to be added. Always prepend with current date in YYYY-MM-DD format in the users timezone if you know it, UTC otherwise."
          },
          "bucketId": {
            "type": "integer",
            "description": "The id of the bucket to add the memory to. If not provided, the memory will be added to the default bucket."
          },
          "source": {
            "type": "string",
            "description": "Client source identifier (e.g., 'chatgpt' for ChatGPT requests)"
          }
        },
        "required": ["text"]
      },
      "Memory": {
        "type": "object",
        "properties": {
          "text": {
            "type": "string"
          },
          "score": {
            "type": "number"
          },
          "metadata": {
            "type": "object",
            "properties": {
              "bucketId": {
                "type": "integer",
                "description": "Numeric ID of the bucket"
              }
            }
          }
        }
      },
      "ErrorResponse": {
        "type": "object",
        "properties": {
          "error": {
            "type": "string"
          },
          "text": {
            "type": "string"
          },
          "score": {
            "type": "number"
          }
        }
      },
      "SuccessResponse": {
        "type": "object",
        "properties": {
          "done": {
            "type": "string",
            "enum": ["ok"]
          },
          "memoryId": {
            "type": "string",
            "description": "Encoded identifier for the created memory"
          }
        }
      },
      "SingleMemoryUpdate": {
        "type": "object",
        "properties": {
          "memoryId": {
            "type": "string",
            "description": "Encoded memory ID to update"
          },
          "text": {
            "type": "string",
            "description": "New text content for the memory"
          },
          "bucketId": {
            "type": "integer",
            "description": "Target bucket ID to move the memory to"
          },
          "bucketName": {
            "type": "string",
            "description": "Target bucket name (auto-creates if it does not exist)"
          }
        },
        "required": ["memoryId"]
      },
      "BulkMemoryMove": {
        "type": "object",
        "properties": {
          "memoryIds": {
            "type": "array",
            "items": { "type": "string" },
            "maxItems": 100,
            "description": "Array of encoded memory IDs to move (max 100)"
          },
          "bucketId": {
            "type": "integer",
            "description": "Target bucket ID"
          },
          "bucketName": {
            "type": "string",
            "description": "Target bucket name (auto-creates if it does not exist)"
          }
        },
        "required": ["memoryIds"]
      },
      "SingleUpdateResponse": {
        "type": "object",
        "properties": {
          "success": { "type": "boolean" },
          "memory": {
            "type": "object",
            "properties": {
              "id": { "type": "string", "description": "Encoded memory ID" },
              "text": { "type": "string" },
              "bucketId": { "type": "integer" },
              "version": { "type": "integer" },
              "updatedAt": { "type": "string", "format": "date-time" },
              "createdAt": { "type": "string", "format": "date-time" }
            }
          }
        }
      },
      "BulkMoveResponse": {
        "type": "object",
        "properties": {
          "success": { "type": "boolean" },
          "updated": { "type": "integer", "description": "Number of memories moved" },
          "bucketId": { "type": "integer", "description": "Target bucket ID" }
        }
      },
      "Bucket": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Unique identifier for the bucket"
          },
          "name": {
            "type": "string",
            "description": "Display name of the bucket"
          },
          "description": {
            "type": "string",
            "description": "Optional description of the bucket"
          },
          "memoryCount": {
            "type": "integer",
            "description": "Number of memories in this bucket"
          }
        },
        "required": ["id", "name", "memoryCount"]
      },
      "CustomChatHistoryInput": {
        "type": "object",
        "properties": {
          "platform": {
            "type": "string",
            "description": "Platform identifier for your integration (e.g., 'my-slack-bot', 'internal-tool'). Alphanumeric, hyphens, underscores, dots. Max 100 chars. Defaults to 'custom' if omitted.",
            "pattern": "^[a-zA-Z0-9\\-_.]{1,100}$",
            "example": "my-custom-app"
          },
          "platformDisplayName": {
            "type": "string",
            "description": "Human-readable display name for the platform shown in the UI. Max 200 chars. Overwrites previous value if supplied again for the same platform.",
            "maxLength": 200,
            "example": "My Custom App"
          },
          "conversation": {
            "type": "object",
            "description": "The conversation to upload.",
            "properties": {
              "id": {
                "type": "string",
                "description": "Your unique identifier for this conversation. Used for upsert deduplication — sending the same ID again updates the existing conversation.",
                "maxLength": 500,
                "example": "conv-abc-123"
              },
              "title": {
                "type": "string",
                "description": "Display title of the conversation.",
                "example": "Discussion about API design"
              },
              "createdAt": {
                "type": "string",
                "format": "date-time",
                "description": "When the conversation was created (ISO 8601).",
                "example": "2026-04-27T10:00:00Z"
              },
              "updatedAt": {
                "type": "string",
                "format": "date-time",
                "description": "When the conversation was last updated (ISO 8601). Defaults to createdAt if omitted.",
                "example": "2026-04-27T11:30:00Z"
              },
              "messages": {
                "type": "array",
                "description": "The messages in the conversation. Must contain at least one message.",
                "minItems": 1,
                "items": {
                  "type": "object",
                  "properties": {
                    "id": {
                      "type": "string",
                      "description": "Your unique identifier for this message. Used for deduplication on re-upload.",
                      "example": "msg-001"
                    },
                    "role": {
                      "type": "string",
                      "enum": ["human", "assistant"],
                      "description": "Who sent this message."
                    },
                    "content": {
                      "type": "string",
                      "description": "The message text content.",
                      "example": "How should we structure the API?"
                    },
                    "createdAt": {
                      "type": "string",
                      "format": "date-time",
                      "description": "When this message was sent (ISO 8601). Optional but recommended for correct ordering.",
                      "example": "2026-04-27T10:00:00Z"
                    }
                  },
                  "required": ["id", "role", "content"]
                }
              }
            },
            "required": ["id", "title", "createdAt", "messages"]
          }
        },
        "required": ["conversation"]
      },
      "ChatHistoryIngestResponse": {
        "type": "object",
        "properties": {
          "queued": {
            "type": "boolean",
            "description": "Whether the conversation was accepted for processing."
          },
          "importId": {
            "type": "string",
            "description": "The import record ID for this platform."
          },
          "conversationId": {
            "type": "string",
            "description": "The internal conversation ID assigned by MemoryPlugin."
          },
          "platform": {
            "type": "string",
            "description": "The resolved platform identifier."
          },
          "conversation": {
            "type": "object",
            "description": "Conversation details after upsert.",
            "properties": {
              "id": {
                "type": "string",
                "description": "Internal conversation ID."
              },
              "platformConversationId": {
                "type": "string",
                "description": "Your supplied conversation ID."
              },
              "title": {
                "type": "string"
              },
              "updatedAt": {
                "type": "string",
                "format": "date-time"
              },
              "messageCount": {
                "type": "integer"
              },
              "status": {
                "type": "string",
                "enum": ["queued"],
                "description": "Processing status. 'queued' means the conversation is stored and background processing (chunking, embedding) is in progress."
              }
            }
          }
        }
      },
      "ChatHistoryInjectInput": {
        "type": "object",
        "properties": {
          "query": {
            "type": "string",
            "description": "Natural-language description of what you're looking for in the user's chat history.",
            "example": "What decisions did I make about the database schema?"
          },
          "maxTokens": {
            "type": "integer",
            "default": 600,
            "maximum": 2000,
            "description": "Maximum tokens to allocate for the synthesized context. More tokens = richer detail but larger response."
          },
          "platform": {
            "type": "string",
            "enum": ["claude", "chatgpt", "typingmind"],
            "description": "Optional hint about the downstream chat platform to influence formatting."
          },
          "conversationContext": {
            "type": "string",
            "description": "Short plaintext summary of the current conversation to ground retrieval."
          },
          "conversationHistory": {
            "type": "array",
            "description": "Recent dialogue turns to help ground the search.",
            "items": {
              "type": "object",
              "properties": {
                "role": {
                  "type": "string",
                  "enum": ["user", "assistant"]
                },
                "content": {
                  "type": "string"
                }
              },
              "required": ["role", "content"]
            }
          },
          "queries": {
            "type": "array",
            "description": "Array of parallel queries for complex topics (max 15). Each query is searched and synthesized independently. Use when a topic benefits from multiple search angles.",
            "maxItems": 15,
            "items": {
              "type": "object",
              "properties": {
                "query": {
                  "type": "string",
                  "description": "The search query for this parallel request."
                },
                "maxTokens": {
                  "type": "integer",
                  "description": "Maximum tokens for this query (defaults to 600)."
                }
              },
              "required": ["query"]
            }
          }
        }
      },
      "ChatHistoryInjectResponse": {
        "type": "object",
        "properties": {
          "content": {
            "type": "string",
            "description": "AI-synthesized summary of relevant chat history. Ready to inject into a conversation as context."
          },
          "sources": {
            "type": "array",
            "description": "Source conversations that contributed to the synthesized content.",
            "items": {
              "type": "object",
              "properties": {
                "conversationId": {
                  "type": "string",
                  "description": "Internal conversation ID. Use with the Get Conversation or Get Conversation Summary endpoints to dive deeper."
                },
                "conversationTitle": {
                  "type": "string"
                },
                "messageId": {
                  "type": "string"
                },
                "date": {
                  "type": "string"
                },
                "relevanceScore": {
                  "type": "number"
                }
              }
            }
          },
          "tokenCount": {
            "type": "integer",
            "description": "Actual token count of the synthesized content."
          },
          "processingTime": {
            "type": "string",
            "description": "Total processing time (e.g., '342ms')."
          },
          "model": {
            "type": "string",
            "description": "AI model used for synthesis."
          }
        }
      },
      "ChatHistorySearchInput": {
        "type": "object",
        "properties": {
          "query": {
            "type": "string",
            "description": "The search query. Semantic search is performed across all imported conversations.",
            "example": "how to set up authentication"
          },
          "limit": {
            "type": "integer",
            "default": 20,
            "minimum": 1,
            "maximum": 100,
            "description": "Maximum number of results to return."
          },
          "provider": {
            "type": "string",
            "default": "all",
            "description": "Filter results by platform. 'all' searches everything, or specify a platform ID (e.g., 'chatgpt', 'claude', 'custom')."
          },
          "contextChunks": {
            "type": "integer",
            "default": 4,
            "description": "Number of surrounding message chunks to include for context around each result."
          },
          "skipRerank": {
            "type": "boolean",
            "default": false,
            "description": "Skip the AI reranking step. Faster but potentially less relevant ordering."
          }
        },
        "required": ["query"]
      },
      "ChatHistorySearchResponse": {
        "type": "object",
        "properties": {
          "results": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "conversationId": {
                  "type": "string",
                  "description": "Internal conversation ID."
                },
                "title": {
                  "type": "string",
                  "description": "Conversation title."
                },
                "text": {
                  "type": "string",
                  "description": "The matched text chunk."
                },
                "score": {
                  "type": "number",
                  "description": "Relevance score."
                },
                "timestamp": {
                  "type": "string",
                  "format": "date-time",
                  "description": "When the matched message was sent."
                },
                "sender": {
                  "type": "string",
                  "enum": ["human", "assistant"],
                  "description": "Who sent the matched message."
                },
                "context": {
                  "type": "array",
                  "items": {
                    "type": "object",
                    "properties": {
                      "text": { "type": "string" },
                      "sender": { "type": "string" },
                      "timestamp": { "type": "string" }
                    }
                  },
                  "description": "Surrounding messages for context."
                }
              }
            }
          },
          "totalResults": {
            "type": "integer",
            "description": "Total number of results found."
          },
          "query": {
            "type": "string",
            "description": "The original query."
          },
          "provider": {
            "type": "string",
            "description": "Platform filter applied."
          },
          "processingTime": {
            "type": "integer",
            "description": "Time taken in milliseconds."
          }
        }
      },
      "ConversationListResponse": {
        "type": "object",
        "properties": {
          "items": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "id": {
                  "type": "string",
                  "description": "Internal conversation ID."
                },
                "title": {
                  "type": "string",
                  "description": "Conversation title."
                },
                "platform": {
                  "type": "string",
                  "description": "Source platform (e.g., 'chatgpt', 'claude', 'custom')."
                },
                "messageCount": {
                  "type": "integer",
                  "description": "Number of messages in the conversation."
                },
                "tokenCount": {
                  "type": "integer",
                  "description": "Total tokens in the conversation."
                },
                "createdAt": {
                  "type": "string",
                  "format": "date-time"
                },
                "updatedAt": {
                  "type": "string",
                  "format": "date-time"
                },
                "pinned": {
                  "type": "boolean"
                }
              }
            }
          },
          "page": {
            "type": "integer",
            "description": "Current page number."
          },
          "pageSize": {
            "type": "integer",
            "description": "Results per page."
          },
          "total": {
            "type": "integer",
            "description": "Total number of conversations matching the filter."
          },
          "totalPages": {
            "type": "integer",
            "description": "Total number of pages."
          }
        }
      },
      "ConversationDetailResponse": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Internal conversation ID."
          },
          "title": {
            "type": "string",
            "description": "Conversation title."
          },
          "messages": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "message_index": {
                  "type": "integer",
                  "description": "Position in the conversation (0-indexed)."
                },
                "sender": {
                  "type": "string",
                  "enum": ["human", "assistant"],
                  "description": "Who sent the message."
                },
                "text": {
                  "type": "string",
                  "description": "Message content."
                },
                "timestamp": {
                  "type": "string",
                  "format": "date-time",
                  "description": "When the message was sent."
                }
              }
            }
          },
          "total": {
            "type": "integer",
            "description": "Total number of messages."
          },
          "platformConversationId": {
            "type": "string",
            "description": "The original platform conversation ID."
          },
          "sourceId": {
            "type": "string",
            "description": "Platform identifier."
          },
          "tokenCount": {
            "type": "integer",
            "description": "Total tokens in the conversation."
          }
        }
      }
    },
    "securitySchemes": {
      "bearerAuth": {
        "type": "http",
        "scheme": "bearer"
      }
    }
  }
}
