Connect MCP
Configure the HTTP endpoint and key in a compatible MCP client. Example for Claude Code:
claude mcp add --transport http cotacaoia https://cotacaoia-a1.netlify.app/api/mcp \
--header "Authorization: Bearer cot_live_SUA_CHAVE"Reference under review. Examples and identifiers retain the original contract data; verify availability and format before integrating.
Tools
Reference for the implemented server, reviewed on 2026-09-10. The connection lets an agent operate the business in A1 Quote; it does not configure the internal extraction AI. Email, WhatsApp, search and extraction availability depends on the instance providers.
There are 29 tools. The client discovers complete schemas through tools/list. Results use content, usually accompanied by structuredContent; tool failures can use isError: true. There is no single { ok, data } envelope for every response.
Each key grants access to the entire business, without per-tool scopes or automatic expiration. Keys can be revoked in Settings → API keys. Interface cookies do not authenticate MCP. OAuth is not implemented yet.
Keys with the cot_test_ prefix are rejected in production, including key creation. In development, the prefix does not create a sandbox or prevent real sends: use an isolated instance, fictitious data and test providers.
Recipients must be approved before the quotation is sent, but the agent itself can call approve_recipients. The server does not require a separate human confirmation. Configure which tools the client may run and which require confirmation, especially approvals, sends, resends and orders.
Current definitions do not publish readOnlyHint, destructiveHint or openWorldHint. Configure permissions by tool name without relying on these hints.
| Tool | What it does | Endpoint REST |
|---|---|---|
create_project |
Creates a project | POST /projects |
list_projects |
Lists projects with an optional status filter | GET /projects |
create_quotation |
Creates a draft request | POST /projects/{id}/quotations |
get_quotation |
Reads a quotation and its items | GET /quotations/{id} |
update_quotation |
Updates permitted fields; providing status returns an error | PATCH /quotations/{id} |
list_suppliers |
Lists business suppliers | GET /suppliers |
add_supplier |
Creates a supplier; additional fields below | POST /suppliers |
search_suppliers |
Finds candidates without saving them; requires a configured provider | POST /suppliers/search |
attach_suppliers_to_quotation |
Attaches saved suppliers as pending recipients | POST /quotations/{id}/suppliers |
approve_recipients |
Approves explicit IDs and records the agent as the actor | POST /quotations/{id}/suppliers/approve |
list_recipients |
Lists pending and approved recipients | GET /quotations/{id}/suppliers |
send_rfq |
Requests sending to approved recipients; monitor invitations | POST /quotations/{id}/send |
get_invitations |
Reads invitation status | GET /quotations/{id}/invitations |
resend_invitation |
Requests a resend subject to invitation rules | POST /invitations/{id}/resend |
get_quotes |
Lists received quotes with items | GET /quotations/{id}/quotes |
close_quotation |
Closes a sent or collecting quotation | POST /quotations/{id}/close |
get_whatsapp_status |
Reads channel connection and pause status without returning its token | GET /whatsapp/status |
compare_quotes |
Compares confirmed quotes and identifies pending confirmations | GET /quotations/{id}/compare |
generate_order |
Creates orders and requests sending by default; see limitations below | POST /quotations/{id}/orders + POST /quotations/{id}/orders/send |
get_orders |
Lists orders for a quotation | GET /quotations/{id}/orders |
list_orders |
Lists business orders and a summary of results | — |
list_templates |
Lists active templates with an optional sector filter | GET /templates |
create_quotation_from_template |
Creates a quotation from a template | POST /quotations/from-template |
confirm_quote |
Confirms a quote after review | POST /quotes/{id}/confirm |
patch_quote |
Corrects quote fields; additional fields below | PATCH /quotes/{id} |
list_unconfirmed_quotes |
Lists extracted quotes awaiting confirmation | — |
extract_quote_from_text |
Queues text extraction; requires configured AI | POST /quotations/{id}/extract |
get_usage |
Aggregates usage; without dates, queries the entire history | GET /usage |
get_billing_status |
Reads plan and credits; may create the initial trial record | GET /billing |
The names and formats above are registered by the server. Not every interface operation has a tool; for example, supplier updates and attachment uploads have no dedicated MCP tool.
Inputs and outputs
What each tool receives and returns.
create_project
entrada { name: string }
saída Project
list_projects
entrada { status?: "active" | "archived" }
saída { projects }
create_quotation
entrada { project_id: string, title: string, deadline_at?: string, content?: Block[], items?: Item[] }
saída Quotation
get_quotation
entrada { quotation_id: string }
saída Quotation
update_quotation
entrada { quotation_id: string, title?: string, deadline_at?: string | null, content?: Block[], items?: Item[] }
saída Quotation
list_suppliers
entrada { search?: string, origin?: "manual" | "import" | "search", limit?: int(1..500) }
saída { suppliers }
add_supplier
entrada { name: string, email?: string | null, phone?: string | null, communication_locale?: "pt-BR" | "en" | "es", ... }
saída Supplier
search_suppliers
entrada { query: string, location?: string, limit?: int(1..50) }
saída { candidates, provider, cost_usd }
attach_suppliers_to_quotation
entrada { quotation_id: string, supplier_ids: string[] }
saída { recipients }
approve_recipients
entrada { quotation_id: string, supplier_ids: string[] }
saída { recipients }
list_recipients
entrada { quotation_id: string }
saída { recipients }
send_rfq
entrada { quotation_id: string, channels?: ("email" | "whatsapp")[] }
saída { job_id, invitations }
get_invitations
entrada { quotation_id: string }
saída { invitations }
resend_invitation
entrada { invitation_id: string }
saída { resent: true }
get_quotes
entrada { quotation_id: string }
saída { quotes }
close_quotation
entrada { quotation_id: string }
saída { quotation }
get_whatsapp_status
entrada {}
saída { connected, phone, quality_rating, paused_at, pause_reason }
compare_quotes
entrada { quotation_id: string }
saída Comparison
generate_order
entrada { quotation_id: string, selection: { supplier_id: string } | { by_item: Record<quotation_item_id, supplier_id> }, dry_run?: boolean (default false), notes?: string }
saída { dry_run, orders, warnings? }
get_orders
entrada { quotation_id: string }
saída { orders }
list_orders
entrada { status?: ("draft" | "sent" | "confirmed" | "rejected" | "cancelled")[], limit?: int(1..500) }
saída { orders, summary }
list_templates
entrada { sector?: string }
saída { templates }
create_quotation_from_template
entrada { template_id: string, project_id: string, title?: string }
saída Quotation
confirm_quote
entrada { quote_id: string }
saída { confirmed: true, quote_id }
patch_quote
entrada { quote_id: string, lead_time_days?: int, payment_terms?: string, freight?: "included" | "separate" | "pickup", valid_until?: string, notes?: string, items?: QuoteItem[] }
saída { patched: true, quote_id }
list_unconfirmed_quotes
entrada { quotation_id: string }
saída { quotes }
extract_quote_from_text
entrada { quotation_id: string, text: string, supplier_id?: string, invitation_id?: string }
saída { job_id }
get_usage
entrada { from?: string, to?: string, kind?: string }
saída { usage }
get_billing_status
entrada {}
saída BillingStatusAdditional schemas
Additional optional fields for add_supplier; omitting the language uses pt-BR. Creating a supplier does not prove consent: record only WhatsApp permission that actually exists.
type SupplierFields = {
website?: string | null; cnpj?: string | null; cnae?: string | null;
origin?: "manual" | "import" | "search"; google_place_id?: string | null;
contact_source?: "buyer_provided" | "website" | "rfb" | "places" | null;
consent_basis?: "existing_relationship" | "legitimate_interest";
whatsapp_opt_in_at?: string | null; notes?: string | null;
};
type Block =
| { type: "items_table"; columns: { key: string; label: string; kind: "text" | "number" }[] }
| { type: "text"; markdown: string }
| { type: "image"; storage_path: string; caption?: string };
type Item = {
description: string; quantity?: number | null; unit?: string | null;
brand?: string | null; extra?: Record<string, string | number | null>;
};
type QuoteItem = {
quotation_item_id: string; unit_price: number;
available_quantity?: number | null; brand?: string | null; notes?: string | null;
};Approval, orders and processing
For generate_order, omitting dry_run means false: the tool creates orders and requests sending. There is no send: false parameter to save only a draft.
With dry_run: true, the tool calculates a preview of the supplied selection, including items, totals and warnings, with the same validations as order creation. Amounts use the quotation currency: BRL, USD or EUR, without conversion. No order is created or sent.
A result with job_id confirms a processing request, not delivery to the supplier. Use get_invitations, get_quotes and get_orders to monitor progress. There is no MCP subscription for completion events. Do not assume generic support for Idempotency-Key; each service applies its own retry rules.
Recommended flow: find or create suppliers; create the project and quotation; attach saved IDs; review recipients and content in the client; approve and send only with authorization; monitor replies; compare; review the selection and authorize the order. The read-tool list in the configuration below blocks write tools in that client but does not reduce the key authority on the server.
Connect Claude Code and Codex
Create a key in Settings → API keys and make it available to the client through the COTACAOIA_API_KEYenvironment variable. This is a A1 Quote key, not an OpenAI or Anthropic key. The examples use placeholders and must not contain secrets in versioned files.
Claude Code, PowerShell example with the variable already set:
claude mcp add --transport http cotacaoia https://cotacaoia-a1.netlify.app/api/mcp --header "Authorization: Bearer $env:COTACAOIA_API_KEY"Check the connection with /mcp and configure Claude Code permissions before enabling write tools. Official reference.
Codex: add this to the client configuration file. The example starts with five query tools; expand the list deliberately when you need other operations. Official reference.
[mcp_servers.cotacaoia]
url = "https://cotacaoia-a1.netlify.app/api/mcp"
bearer_token_env_var = "COTACAOIA_API_KEY"
enabled_tools = ["list_projects", "list_suppliers", "get_quotation", "compare_quotes", "get_orders"]
default_tools_approval_mode = "prompt"Claude Code and Codex accept this transport with Bearer authentication. Configuration must be checked against the deployed instance; an endpoint and local tests do not prove a real connection in these clients.
Agent APIs and chat interfaces
OpenAI Responses API accepts a remote MCP server with a URL, authentication headers, an allowed-tool list and an approval policy. Use the A1 Quote key in the Bearer header and keep approval for write actions. The OpenAI API call is configured and billed separately. Official guide.
Claude Messages API offers a remote MCP connector with authorization_token; its documentation describes an OAuth token. Using the opaque A1 Quote key in that field needs an interoperability test before it can be advertised as validated. Official guide.
In Claude web/Desktop, static headers for remote connectors are in beta for some organizations. When available, use Authentication: None and an authorization header with the value Bearer <chave>. This credential is shared by the organization; it is not individual account linking. Availability and configuration.
For an authenticated connection directly in ChatGPT web, the documented path requires OAuth, which A1 Quote does not yet implement. This account-linking flow is outside the current MVP. It does not prevent key-based connections in Codex or Claude Code. ChatGPT authentication.
Supplier communication language
POST /api/v1/suppliers, PATCH /api/v1/suppliers/{id} and the add_supplier MCP tool accept the optional communication_locale field. Valid values: pt-BR, en or es. New suppliers default to pt-BR when the field is omitted; an update without this field preserves the existing preference.
The preference selects the language of request and order emails and configured WhatsApp templates. It does not change currency, country, time zone or original item and terms content. WhatsApp still requires recorded permission and an appropriate approved template. A language without a configured template is not silently replaced with Portuguese.
Authentication
Authorization: Bearer cot_live_<key> on every call. Each key belongs to one business and is subject to access rules. Use a test environment for development.