API Report Card · Phone · Methodology v1.1
Quo
Where the points came from.
Five categories, each worth a fixed share of the 100 points. A category earns the fraction of its checks it passes, times its maximum.
Functional Coverage
Design & Reliability
Access Control
Docs & AI-Ready
Access & Cost
Letter grades are absolute, never curved.
The same numeric bands apply to every platform. Nothing here is scored relative to the rest of the board.
What this means for you.
One paragraph per category, in plain language.
1 · Functional Coverage
For its domain, business phone and SMS, this API is genuinely complete. You can sync tenant, owner and vendor contacts both ways, send and receive texts, pull call logs with AI transcripts and summaries, manage conversations and tasks, and get real-time events. Contact and task writes were exercised live, created and then deleted, with cleanup verified. The main gaps are richness rather than reach: no outbound call initiation through the API, and no MMS in the current version.
2 · Design & Reliability
A modern, well-instrumented API that code and AI agents can run in production: predictable types, actionable errors carrying a trace id you can quote to support, real rate-limit headers, clean cursor pagination, a genuine versioning contract with a retirement window, and strong webhook security with HMAC signatures and a documented eight-attempt retry schedule. Two things to engineer around. There is no idempotency key, and the vendor's own error guide warns that a retried message send can repeat its effect, so you must dedupe consequential retries yourself. And there is no bulk export path, with message and call lists scoped to a single conversation rather than the whole dataset.
3 · Access Control
The weakest area by a distance. Every key is an admin-equivalent, full-access credential, described in the vendor's own documentation as having the same reach as an admin. You cannot mint a read-only key or scope one to particular resources or actions, which matters a great deal if you are handing a key to an AI agent or an outside tool. Your only real controls are issuing a separate key per integration and revoking fast, both of which are self-serve and take effect immediately. Treat every key like an admin password.
4 · Docs & AI-Ready
Full marks, and about as good as this gets for building, including with AI. The public reference is complete and needs no reverse-engineering, there are published OpenAPI 3.1 specs for both versions, an official MCP server, an llms.txt and llms-full.txt plus per-endpoint markdown and a downloadable docs bundle, and a dated changelog running through September 2026 with an RSS feed. Hand a coding agent the spec and the llms file and it can build against this correctly.
5 · Access & Cost
You can get in the door on the cheapest paid plan and turn the API on yourself in about a minute, with no sales call, ticket or approval step. The core API and the MCP connector are included on all three plans. Two things to budget for: SMS is billed per segment from a prepaid credit balance, and AI call summaries and transcripts require a Business or Scale plan. An active paid subscription is required for any API access at all.
Every check, and why it scored that way.
The same 27 checks are applied to every platform. What changes is which are N-A and what the core objects mean for that kind of software. Each mark below is quoted from the run's own report.
Category 1 · Functional Coverage
15 / 15Object coverage
weighted coverage = 98% (21.5/22; no critical object absent). Contacts [v1 /v1/contacts GET/POST/PATCH/DELETE; 2026-03-30 /contacts], messages [v1 /v1/messages GET/POST, /v1/messages/{id}], calls + media [v1 /v1/calls, /v1/call-recordings|summaries|transcripts|voicemails/{id}], conversations [v1 /v1/conversations + /conversations/{id}/mark-as-], phone numbers [v1 /v1/phone-numbers], tasks [/v1/tasks], users [/users], webhooks [/webhooks*], organization [GET /organization], contact custom fields [/v1/contact-custom-fields]. Live-confirmed reads 2026-09-08 on users, contacts, conversations, phone numbers (4), organization.
Core operational actions
weighted coverage = 100% (no critical write absent). Observed live 2026-09-08: contact create (POST /v1/contacts → 201) and update (PATCH /v1/contacts/{id} → 200, company changed); task create (POST /v1/tasks → 201) and update (PUT /v1/tasks/{id} → 200). Message send [POST /v1/messages] and conversation-state writes [/conversations/{id}/mark-as-*] and webhook create/update [POST/PATCH /webhooks] present; message send is documentation-graded (hard-excluded from live test as external communication).
Delete or lifecycle actions
weighted coverage = 100% (no critical lifecycle absent). Observed live: contact delete (DELETE /v1/contacts/{id} → 204, then 404); task complete (/complete → 200), reopen (/reopen → 200), delete (→ 204, then 404). Also documented: conversation mark done/open, message retry, webhook delete + POST /webhooks/{id}/rotate.
Change notification
webhooks cover message (received/delivered/failed/undelivered), the full call lifecycle (incl. call.completed, call.summary.completed, call.transcript.completed, call.menu.selected), contact.updated/deleted, and 12 task.* events [docs/2026-03-30/webhooks-overview; changelog 2026-06-18/07-09/08-25]; incremental polling (updatedAfter/since/createdAfter) is available as a backup and was honored live on conversations.
Category 2 · Design & Reliability
7.9 / 10Modern API conventions
resource-oriented REST, JSON in/out, standard verbs (GET/POST/PATCH/PUT/DELETE) observed live [OpenAPI paths; docs/2026-03-30/requests].
Consistent typing
OpenAPI 3.1 with explicit types, anyOf+{type:null} nullability, format/pattern constraints; live GET /users and GET /contacts payloads matched documented types exactly (2026-09-08).
Structured errors
(reconciled: R1 yes → resolved partial with R2/R3) — structured envelope with correct HTTP status semantics, human-readable message, field-level errors[].path/value/schema, and a trace id, all observed live (live/e_ver.json, e_lim.json, e_auth.json, e_404.json). Limitation — error shapes vary across endpoints: the flagship 2026-03-30 core-resource errors (users/contacts/tasks) carry no stable top-level machine code, whereas v1 and webhook-family errors do (e.g. live/msg.json code:"0100400"; spec consts 0300401/0301500). No single populated stable machine code across the surface → partial.
Duplicate prevention
no idempotency mechanism is documented in either spec (0 occurrences of idempotency/Idempotency-Key), and the errors guide explicitly warns that a retried POST such as a message send "can repeat its effect" [docs/2026-03-30/errors → "Retrying"]. Consequential creates/sends are unprotected. (Not N-A: the API has consequential writes.)
Graceful handling under load
documented 429 at 10 req/s/key plus machine-readable ratelimit and ratelimit-policy response headers observed live ("per-second"; q=10; w=1, r=9; t=1) and explicit exponential-backoff-with-jitter guidance [docs/2026-03-30/rate-limits; live headers 2026-09-08].
Pagination for large collections
cursor pagination (limit 1–50 default 10, after, nextCursor) in 2026-03-30; v1 adds totalItems + nextPageToken. Live multi-page traversal returned distinct, stable pages [docs/2026-03-30/requests; live 2026-09-08].
Bulk or incremental export
incremental sync is possible on list endpoints (since/createdAfter/updatedAfter + pagination; updatedAfter honored live on conversations), but there is no dedicated bulk/export path (no async export jobs or bulk endpoints), messages/calls lists require phoneNumberId+participants (per-conversation scope, not a whole-dataset pull — confirmed live via a 400), and contacts have no updated-since filter.
Webhook security and delivery reliability
(documentation-graded)** — HMAC-SHA256 signatures (webhook-signature, svix-compatible, whsec_ secret), a documented 8-attempt retry schedule (~27h), consumer idempotency via webhook-id, replay protection, and delivery inspection/retry endpoints [docs/2026-03-30/webhooks-overview, webhooks-signature-validation]. Management endpoints exist and are in-spec; end-to-end delivery was not live-observed (no operator-controlled endpoint; out of authorized write scope).
Concurrency and conflict control
documented 409 Conflict on all contact writes [v1 /v1/contacts*] and a revision version field on tasks (observed incrementing on update, 2026-09-08), but no documented optimistic-concurrency mechanism (no If-Match/ETag write path — the response etag is a generic weak validator — and no way to submit an expected revision) and no documented concurrency behavior.
Versioning and backward compatibility
required dated Quo-Api-Version header, an explicit breaking-vs-non-breaking policy, and a retirement/migration-window commitment [docs/2026-03-30/versioning; changelog 2026-03-30].
Request traceability
(reconciled: R1/R2 yes, R3 partial → resolved yes) — a documented trace id explicitly usable with support ("we can pull up the exact request") satisfies the yes clause "an equivalent documented trace mechanism"; an x-correlation-id is additionally present on every response observed live [docs/2026-03-30/errors → "The trace id"; live/headers_users.txt].
Service availability and status transparency
(reconciled: R1 yes, R2/R3 no due to a packet-completeness gap, now fixed → resolved yes) — public first-party status page status.quo.com (statuspage.io) with a Quo API component, per-service uptime (API 99.997%) and a Jun–Sep 2026 incident-history calendar; persisted to the packet as live/status_page.html + live/status_summary.json ("All Systems Operational", 0 active incidents).
Category 3 · Access Control
2.5 / 5Read-only credentials
keys are full workspace access; no read-only credential option ("each key has full access to your workspace's API"; "the same reach as an admin") [docs/2026-03-30/authentication].
Scoped credentials
a key cannot be restricted to specific resources/actions/roles; it is a single all-powerful credential [same citation].
Multiple keys
multiple named keys, one per integration, are supported and encouraged [docs/2026-03-30/authentication → "one key per integration"].
Rotation and revocation
self-serve generate/delete in Workspace Settings → API; "access ends immediately" [docs/2026-03-30/authentication → "Revoke a key"].
Test and production isolation
no sandbox/separate test environment is documented.
Category 4 · Docs & AI-Ready
5 / 5Complete self-serve reference
complete public reference with auth, per-endpoint params, and worked request/response examples; usable without reverse-engineering (verified across many pages, 2026-09-08).
Reliable machine-consumable path
published, complete OpenAPI 3.1 specs (v1 and 2026-03-30) plus an official MCP server; the docs name the spec the "ground truth" [docs/2026-03-30/ai-agents].
AI-readable documentation
llms.txt, llms-full.txt, per-endpoint .md, and a downloadable docs-bundle zip [docs/2026-03-30/ai-agents; docs/llms.txt].
Kept current
a detailed, dated changelog through September 2026 with RSS, plus versioning/deprecation guidance [docs/2026-03-30/changelog].
Category 5 · Access & Cost
11.3 / 15Self-serve API key
an owner/admin generates a key in Workspace Settings → API with no sales call, ticket, or approval step [docs/2026-03-30/authentication].
Not commercially gated
the core API (messaging, contacts, calls metadata, conversations, tasks, webhooks, users) and the MCP connector are included on all three plans, including entry-level Starter ($15/user/mo annual) [quo.com/pricing]; but two meaningful capabilities — AI call summaries and transcripts — require Business/Scale plans [docs/mdx/api-reference/calls/get-a-summary-for-a-call, .../get-a-transcription-for-a-call], and an active paid subscription is required for any API access [pricing-overview → "Requirements & limitations"].
What works
- Complete coverage of its own domain: contacts, messages, calls, conversations, tasks, webhooks
- Contact and task writes exercised live, created then deleted, with cleanup verified
- Webhooks with HMAC signatures, a documented 8-attempt retry schedule and replay protection
- A real versioning contract: dated version header, breaking-change policy, retirement window
- Published OpenAPI 3.1 specs, an official MCP server, llms.txt and a downloadable docs bundle
- Rate limiting that tells you where you stand, with machine-readable headers verified live
- A trace id on errors that the documentation says support can look up directly
- Self-serve keys on the entry-level paid plan, with revocation that takes effect immediately
What to watch
- Every key is full workspace access: no read-only option and no scoping of any kind
- No idempotency key, and the vendor's own guide warns a retried send can repeat its effect
- No bulk export, and message and call lists are scoped to one conversation at a time
- Contacts have no updated-since filter, so incremental sync does not reach them
- No optimistic concurrency: tasks carry a revision field but nothing accepts it on write
- Error codes vary across endpoints, so there is no single stable machine code to match on
- AI call summaries and transcripts need a Business or Scale plan
- An active paid subscription is required before any API access at all
- No sandbox or separate test environment
- No outbound call initiation and no MMS in the current version
The bottom line for a property manager
Quo, formerly OpenPhone, is a general-purpose business phone system with an unusually good, modern API. It is not a property management platform, not a bank, and it holds no funds. Today you can build a lot on it: two-way contact sync for tenants, owners and vendors, automated SMS with receipt through signed webhooks, call logs with AI transcripts and summaries, conversation triage, and task tracking. All of that was verified live here except message send, which was excluded from testing because it would text real people. The API's real strengths are developer and agent readiness: clean REST, strong typing, actionable errors with trace ids, real versioning, first-class webhooks, and an OpenAPI spec alongside an MCP server. Its real weaknesses are access control, where every key is full-access with no read-only or scoped option, which matters if you hand a key to an AI agent, and the absence of both idempotency keys and a bulk export path. Read the score for what it measures. This grades the API, not the product. As a tool, Quo is the communications layer of a property management stack, and you would still run a separate PMS, accounting system and trust accounting alongside it.
Check it yourself.
Both files behind this page, in full.
Quo’s full report
The complete markdown report this page is built from, including the evidence packet, the run metadata and every check in full.
Download the Quo reportThe grading file
The exact rubric behind every score on this page. Same file, every platform. Run it yourself and compare.
Download the methodologyFound a factual error in your grade?
Tell us and we will fix it. Every mark on this page traces to a specific piece of first-party evidence or a live API call, and the full report is published so you can see exactly what was checked and what it was checked against.
Confirmed factual errors are corrected immediately.
Everything else waits. We do not rescore piecemeal on request, because a board where some vendors have been re-run and others have not is not a fair comparison. Shipped improvements, changed documentation and disagreements about judgement all go into the next full rerun.
Contact us with a factual errorMethodology inspired by SaaStr’s AI Agent API Report Card. Sponsored by Column.