# REST API Endpoints Complete reference for WP Agentic Writer REST API endpoints. **Base URL:** `/wp-json/wp-agentic-writer/v1` **Authentication:** All endpoints require WordPress authentication via `cookie` or application password. Permission checks vary by endpoint (see below). **Rate Limiting:** Most endpoints are rate-limited. See [Rate Limits](#rate-limits) below. --- ## Rate Limits | Endpoint | Limit | Window | Notes | |----------|-------|--------|-------| | `POST /chat` | 30/min | 60s | | | `POST /chat_stream` | 30/min | 60s | Streaming variant | | `POST /search` | 20/min | 60s | Brave Search | | `POST /fetch-content` | 10/min | 60s | Web content fetch | | All others | — | — | No rate limiting | --- ## Models ### `GET /models` List available AI models from OpenRouter. **Handler:** `Controller_Models::handle_get_models()` **Permission:** `check_permissions` (authenticated user) **Response:** Array of model objects from OpenRouter cache. --- ### `POST /models/refresh` Force-refresh the model cache. **Handler:** `Controller_Models::handle_refresh_models()` **Permission:** `check_permissions` **Response:** ```json { "models": [...], "message": "Models refreshed successfully." } ``` --- ## Chat ### `POST /chat` Send a chat message (non-streaming). **Handler:** `Controller_Chat::handle_chat_request()` **Permission:** `check_permissions` + post edit (if `postId` provided) **Rate Limit:** 30 requests/minute **Request Body:** ```json { "messages": [...], "postId": 123, "sessionId": "uuid", "type": "planning|writing|revising", "stream": false } ``` **Response:** Full JSON response with assistant message. --- ### `POST /chat` (streaming variant) Same endpoint with `"stream": true` in request body. Uses Server-Sent Events. **Rate Limit:** 30 requests/minute (same as non-streaming) **Response:** `text/event-stream` with chunks. --- ### `POST /clear-context` Clear the chat context for a post. **Handler:** `Controller_Chat::handle_clear_context()` **Permission:** `check_permissions` + post edit **Request Body:** ```json { "postId": 123, "sessionId": "uuid" } ``` --- ### `GET /chat-history/(?P\d+)` Get legacy chat history from post meta. **Deprecated** — use `/conversations` instead. **Handler:** `Gutenberg_Sidebar::handle_get_chat_history()` **Permission:** `check_permissions` + post edit --- ## Conversations ### `GET /conversation/(?P\d+)` Get canonical conversation for chat hydration. **Handler:** `Gutenberg_Sidebar::handle_get_conversation()` **Permission:** `check_permissions` + post edit --- ### `GET /conversations` List all conversations for the current user. **Handler:** `Gutenberg_Sidebar::handle_get_conversations()` **Permission:** `check_permissions` --- ### `GET /conversations/post/(?P\d+)` List conversations linked to a specific post. **Handler:** `Gutenberg_Sidebar::handle_get_conversations()` **Permission:** `check_permissions` --- ### `POST /conversations` Create a new conversation. **Handler:** `Gutenberg_Sidebar::handle_create_conversation()` **Permission:** `check_permissions` --- ### `GET /conversations/(?P[a-zA-Z0-9]+)` Get a specific conversation. **Handler:** `Gutenberg_Sidebar::handle_get_conversation()` **Permission:** `check_permissions` --- ### `PUT /conversations/(?P[a-zA-Z0-9]+)` Update conversation metadata. **Handler:** `Gutenberg_Sidebar::handle_update_conversation()` **Permission:** `check_permissions` --- ### `DELETE /conversations/(?P[a-zA-Z0-9]+)` Delete a conversation. **Handler:** `Gutenberg_Sidebar::handle_delete_conversation()` **Permission:** `check_permissions` --- ### `POST|PUT /conversations/(?P[a-zA-Z0-9]+)/messages` Add or update messages in a conversation. **Handler:** `Gutenberg_Sidebar::handle_update_conversation_messages()` **Permission:** `check_permissions` --- ### `POST /conversations/(?P[a-zA-Z0-9]+)/link-post` Link a conversation to a post. **Handler:** `Gutenberg_Sidebar::handle_link_conversation_to_post()` **Permission:** `check_permissions` --- ### `POST /conversations/(?P[a-zA-Z0-9]+)/lock` Acquire or refresh session lock (heartbeat). **Handler:** `Controller_Session::handle_session_lock()` **Permission:** `check_permissions` + conversation access **Request Body:** ```json { "tab_id": "uuid", "force": false } ``` **Response:** ```json { "acquired": true, "expires_at": 1234567890, "tab_id": "uuid" } ``` --- ### `DELETE /conversations/(?P[a-zA-Z0-9]+)/lock` Release session lock. **Handler:** `Controller_Session::handle_session_unlock()` **Permission:** `check_permissions` + conversation access --- ## Planning & Writing ### `GET|POST /post-config/(?P\d+)` Get or save post configuration (focus keyword, language, article type). **Handler:** `Gutenberg_Sidebar::handle_get_post_config()` / `handle_save_post_config()` **Permission:** `check_permissions` + post edit --- ### `POST /generate-plan` Generate article outline/plan. **Handler:** `Gutenberg_Sidebar::handle_generate_plan()` **Permission:** `check_permissions` + post edit --- ### `POST /revise-plan` Revise an existing plan. **Handler:** `Gutenberg_Sidebar::handle_revise_plan()` **Permission:** `check_permissions` + post edit --- ### `POST /execute-article` Execute article generation from plan. **Handler:** `Gutenberg_Sidebar::handle_execute_article()` **Permission:** `check_permissions` + post edit --- ### `POST /reformat-blocks` Reformat blocks (e.g., convert to different structure). **Handler:** `Gutenberg_Sidebar::handle_reformat_blocks()` **Permission:** `check_permissions` + post edit --- ### `POST /regenerate-block` Regenerate a single block. **Handler:** `Gutenberg_Sidebar::handle_regenerate_block()` **Permission:** `check_permissions` + post edit --- ### `POST /refine-block` Refine a block with instructions. **Handler:** `Gutenberg_Sidebar::handle_block_refine()` **Permission:** `check_permissions` + post edit --- ### `POST /refine-from-chat` Refine blocks based on chat conversation. **Handler:** `Gutenberg_Sidebar::handle_refine_from_chat()` **Permission:** `check_permissions` + post edit --- ### `POST /refine-multi-pass` Multi-pass block refinement. **Handler:** `Gutenberg_Sidebar::handle_refine_multi_pass()` **Permission:** `check_permissions` + post edit --- ### `POST /refine-article` Article-wide refinement. **Handler:** `Gutenberg_Sidebar::handle_refine_article()` **Permission:** `check_permissions` + post edit --- ### `POST /summarize-context` Summarize context to stay within token limits. **Handler:** `Gutenberg_Sidebar::handle_summarize_context()` **Permission:** `check_permissions` + post edit --- ## Content Quality ### `POST /check-clarity` Check content clarity. **Handler:** `Gutenberg_Sidebar::handle_check_clarity()` **Permission:** `check_permissions` + post edit --- ### `POST /detect-intent` Detect user intent from message. **Handler:** `Gutenberg_Sidebar::handle_detect_intent()` **Permission:** `check_permissions` --- ### `POST /suggest-improvements` Proactive improvement suggestions (idle analysis). **Handler:** `Gutenberg_Sidebar::handle_suggest_improvements()` **Permission:** `check_permissions` + post edit --- ## SEO ### `GET /seo-audit/(?P\d+)` Run SEO audit for a post. **Handler:** `Gutenberg_Sidebar::handle_seo_audit()` **Permission:** `check_permissions` + post edit --- ### `POST /generate-meta` Generate meta description. **Handler:** `Gutenberg_Sidebar::handle_generate_meta()` **Permission:** `check_permissions` + post edit --- ### `POST /suggest-keywords` Suggest keywords for a post. **Handler:** `Gutenberg_Sidebar::handle_suggest_keywords()` **Permission:** `check_permissions` + post edit --- ### `GET /geo-score/(?P\d+)` Get GEO scoring for a post. **Handler:** `Gutenberg_Sidebar::handle_geo_score()` **Permission:** `check_permissions` + post edit --- ## Title & Excerpt ### `POST /generate-title` Generate post title (uses WP 7.0 AI Client when available). **Handler:** `Gutenberg_Sidebar::handle_generate_title()` **Permission:** `check_permissions` + post edit --- ### `POST /refine-title` Refine title with instructions. **Handler:** `Gutenberg_Sidebar::handle_refine_title()` **Permission:** `check_permissions` + post edit --- ### `POST /generate-excerpt` Generate post excerpt (uses WP 7.0 AI Client when available). **Handler:** `Gutenberg_Sidebar::handle_generate_excerpt()` **Permission:** `check_permissions` + post edit --- ## Images ### `GET /image-recommendations/(?P\d+)` Get image recommendations for a post. **Handler:** `Gutenberg_Sidebar::handle_get_image_recommendations()` **Permission:** `check_permissions` + post edit --- ### `POST /generate-image` Generate an image. **Handler:** `Gutenberg_Sidebar::handle_generate_image()` **Permission:** `check_permissions` + post edit --- ### `POST /commit-image` Commit/save generated image. **Handler:** `Gutenberg_Sidebar::handle_commit_image()` **Permission:** `check_permissions` + post edit --- ## Writing State ### `GET /writing-state/(?P\d+)` Get writing state for a post. **Handler:** `Gutenberg_Sidebar::handle_get_writing_state()` **Permission:** `check_permissions` + post edit --- ### `POST /writing-state/(?P\d+)` Save writing state. **Handler:** `Gutenberg_Sidebar::handle_save_writing_state()` **Permission:** `check_permissions` + post edit --- ## Section Blocks ### `POST /section-blocks` Save section block mapping. **Handler:** `Gutenberg_Sidebar::handle_save_section_blocks()` **Permission:** `check_permissions` --- ### `GET /section-blocks/(?P\d+)` Get section blocks for a post. **Handler:** `Gutenberg_Sidebar::handle_get_section_blocks()` **Permission:** `check_permissions` + post edit --- ## Cost Tracking ### `GET /cost-tracking/(?P\d+)` Get cost tracking data. **Handler:** `Controller_Cost::handle_get_cost_tracking()` **Permission:** `check_permissions` + post edit (if `post_id` > 0) --- ## AI Capabilities ### `GET /ai-capabilities` Get AI capabilities status. **Handler:** `Gutenberg_Sidebar::handle_get_ai_capabilities()` **Permission:** `check_permissions` --- ## Research ### `POST /search` Search the web (Brave Search). **Handler:** `Controller_Chat::handle_search()` **Permission:** `check_permissions` **Rate Limit:** 20 requests/minute --- ### `POST /fetch-content` Fetch web page content. **Handler:** `Controller_Chat::handle_fetch_content()` **Permission:** `check_permissions` **Rate Limit:** 10 requests/minute --- ### `POST /research-summary` Generate research summary. **Handler:** `Controller_Chat::handle_research_summary()` **Permission:** `check_permissions` --- ## MEMANTO (Memory) ### `GET /memanto/status` Get MEMANTO service status. **Handler:** `Gutenberg_Sidebar::handle_memanto_status()` **Permission:** `check_permissions` --- ### `GET /memanto/recall` Recall recent memories for a post. **Handler:** `Gutenberg_Sidebar::handle_memanto_recall()` **Permission:** `check_permissions` --- ### `GET /memanto/restore` Restore session for cross-session continuity. **Handler:** `Gutenberg_Sidebar::handle_memanto_restore()` **Permission:** `check_permissions` --- ### `GET /memanto/preferences` Get user preferences for new post carry-over. **Handler:** `Gutenberg_Sidebar::handle_memanto_preferences()` **Permission:** `check_permissions` --- ## User Preferences ### `GET /user-preferences` Get user preferences (public — no auth required). **Handler:** `Gutenberg_Sidebar::handle_get_user_preferences()` **Permission:** `__return_true` (public) --- ### `POST /user-preferences` Save user preferences. **Handler:** `Gutenberg_Sidebar::handle_save_user_preferences()` **Permission:** `check_permissions` --- ## Migration ### `POST /migrate-chat-history/(?P\d+)` Migrate legacy post meta chat history to conversations table. **Handler:** `Gutenberg_Sidebar::handle_migrate_chat_history()` **Permission:** `check_permissions` + post edit --- ## Error Codes | Code | HTTP Status | Description | |------|-------------|-------------| | `forbidden` | 403 | User lacks permission for this action | | `invalid_post` | 400 | Invalid or missing post ID | | `rate_limit_exceeded` | 429 | Too many requests | | `missing_tab_id` | 400 | Session lock requires tab_id | | Various WP_Error codes | varies | Provider-specific errors | --- ## Response Format All responses are JSON. Successful responses: ```json { "status": "success", "data": { ... } } ``` Or directly the resource data: ```json { "key": "value" } ``` Error responses: ```json { "code": "error_code", "message": "Human-readable message", "data": { "status": 400 } } ```