API reference

Base URL: https://commonelements.com/api/v1

Find the right endpoint

You are starting fromUse
A name from your own system to reconcile/associations/match
A property address/associations/by-address
Browsing or filtering a state/associations/lookup
Watching for changes/changes
Pulling a whole dataset (Growth and above)/export/{resource}

Authentication

All API requests must include an Authorization header with a bearer token. Generate an API key from your account settings.

Authorization: Bearer ce_live_your_key_here

Keys are prefixed with ce_live_ for production and ce_test_ for sandbox environments. Never expose keys in client-side code or commit them to version control.

Spec, sandbox and status

Four endpoints exist so you never have to take this page’s word for anything. None of them consumes quota, and the first three need no key at all.

OpenAPI 3.1 document

Generated from the same definitions this page renders, so it cannot drift from the reference. Import it into Postman or an API gateway, or generate a client from it. Add ?format=yaml for YAML.

Sandbox

A published test key and a small fixed dataset at /api/v1/meta/sandbox. Build and test a client before you buy anything, and provoke a 429 or a 403 on demand to check your retry path.

Status, versioning and deprecation

Live availability at /api/v1/meta/status, plus the written compatibility and deprecation commitments procurement asks for.

Data dictionary

Every resource and every field: type, source, how often it is actually populated, how many rows stand behind it, and the refresh cadence of the feed. Measured at request time, never typed into a page.

# Import the spec, then hit the sandbox with the published test key.
curl https://commonelements.com/api/v1/openapi -o common-elements.json

curl "https://commonelements.com/api/v1/meta/sandbox/associations" \
  -H "Authorization: Bearer ce_test_sandbox"

Rate limits

Limits are enforced per API key against a calendar month, UTC: the counter resets on the first request on or after the first of the next month, not on a rolling window from when the key was created. When you exceed your limit, requests return 429 Too Many Requests with quota_exceeded until the reset. There is no overage charge and no automatic top-up.

TierRequests/month
Free250
Builder10,000
Growth50,000
Scale250,000
EnterpriseUnlimited

Track your remaining quota on the API keys settings page; a request over quota returns 429 with { "error": "quota_exceeded" }.

Monitoring your usage

Your API keys settings page is the self-serve way to see where you stand. Every key you hold shows its current usage as a running count, for example 742 / 10,000 requests this month, next to its tier and status. Check it before a scheduled job or bulk import to confirm you have room, rather than finding out from a 429.

Your integration can ask the same question itself. GET /api/v1/meta/usage returns requests used and remaining, the reset date, a per-day and per-endpoint breakdown, and your most recent errors — and it does not consume quota, so it still answers when the key is already over its limit. That is the call to make before starting a batch.

curl "https://commonelements.com/api/v1/meta/usage?days=7" \
  -H "Authorization: Bearer ce_live_your_key_here"

It also reports the plan your organization’s subscription entitles you to, resolved from billing at request time, next to the plan the key was created at. If those two ever disagree, plan.mismatch says so and what to do about it.

A quota-exhausted request returns a 429 with this body:

{
  "ok": false,
  "error": "quota_exceeded",
  "message": "Monthly request quota exceeded."
}

Monthly quota resets at the start of the next calendar month; there is no partial reset and no automatic overage charge. If you are building an integration that calls the API on a schedule, check your usage on the API keys page before a large batch, and back off with an increasing delay after a 429 rather than retrying immediately in a tight loop.

Endpoints

Every endpoint below is live, and this list is the same one /api/v1/openapi is generated from — a reader and a generated client cannot see different APIs. A test walks app/api/v1 on every run and fails when a route exists that this page does not describe, so nothing ships here undocumented. If something below does not match what the API returns, the API is right and this page is a bug worth reporting.

Dataset catalog

What the platform holds, and what it holds for one association. Start here: the catalog names every resource, the plan it needs, and the caveat that stops an unmatched jurisdiction reading as a clean record.

GET/api/v1/datasets

The resource catalog: every published resource and every source behind it, with display name, buyer summary, provenance, state footprint, coverage basis and caveat, the plan each needs, and whether your key can read it. Resources above your plan are listed deliberately — an absence you cannot see is indistinguishable from a clean record.

Scope: associations

Response fields

ParameterTypeDescription
resource_keystringStable key. The `source` and path segment both derive from it.
display_namestringResource name, for display.
buyer_summarystringWhat this resource gives you, in one sentence.
provenance_labelstringWhere the underlying records come from.
min_tierstringPlan required to read rows from this resource.
has_accessbooleanWhether the key on this request can read its rows.
coverage_basisstringWhat kind of coverage number this resource may be described with.
coverage_notestringThe caveat that says whether a zero means 'nothing happened' or 'not matched yet'.

Example request

curl "https://commonelements.com/api/v1/datasets" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "resource_key": "permits",
      "display_name": "Building permits",
      "buyer_summary": "Municipal permits recorded against the association.",
      "provenance_label": "Municipal permit systems",
      "min_tier": "builder",
      "has_access": true,
      "coverage_basis": "association_share",
      "coverage_note": "Matched in the jurisdictions listed; a zero outside them means not matched, not none."
    }
  ]
}

GET/api/v1/associations/{id}/datasets

What the platform holds for one association across every resource, in one round trip: record counts, how many of each resource's sources could be measured, whether your key can read them, and the coverage caveat. The call to make before deciding which resource endpoints are worth a request.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Response fields

ParameterTypeDescription
resource_keystringResource this row describes.
record_countnumberRecords held for this association in this resource.
sources_measurednumberHow many of the resource's sources could be counted.
has_accessbooleanWhether your key can read the rows behind the count.
coverage_notestringWhether a zero here means 'nothing happened' or 'this jurisdiction is not matched yet'.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/datasets" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    { "resource_key": "permits", "record_count": 14, "sources_measured": 1, "has_access": true, "coverage_note": "…" },
    { "resource_key": "violations", "record_count": 0, "sources_measured": 1, "has_access": false, "coverage_note": "…" }
  ]
}
  • Counts are returned for resources above your plan on purpose. The size of what is behind the gate is the offer.

Change feed

What changed, and when. The rest of the API describes the association graph as it stands today; this describes it moving.

GET/api/v1/changes

The trigger-event feed: board turnover, president changes, management-company moves, self-managed transitions, registration status and name changes, and license events across the association graph. This is the programmatic form of the change feed on data.commonelements.com, and the endpoint to poll when you want to act on a community the week something changed rather than re-download a static list.

Scope: changes or associationsYour plan sets the row cap, and a maximum lookback window (table below). Free keys: up to 10 rows per request; paid tiers raise the cap.

PlanRows per requestMaximum lookback
Free5030 days
Builder1,000180 days
Growth5,000365 days
Scale25,0003 years
Enterprise100,00010 years

Change history records differences observed in public records. An observation date may differ from the date a change took effect. Available history varies by source. Your plan's lookback window limits the recorded events you can access; it does not guarantee that much history is available.

Query parameters

ParameterTypeDescription
kindstringComma-separated list of change kinds to include. Any of: board_turnover, board_president_changed, officer_added, officer_removed, officer_title_changed, management_company_changed, management_company_added, management_company_removed, self_managed_transition, entity_status_changed, entity_name_changed, license_added, license_lapsed. Omit for all kinds.
statestringComma-separated two-letter state codes, e.g. "FL" or "FL,GA,TX". Case-insensitive.
countystringSingle county name, matched exactly as stored (e.g. "Miami-Dade").
subtypestringOne of "hoa", "condo", "coop".
sincestringEarliest observation date, YYYY-MM-DD. Clamped to your plan lookback window; an earlier date does not widen it. Available change history varies by source. Observation dates may differ from when changes took effect, and your plan's lookback window does not guarantee that much history.
untilstringLatest observation date, YYYY-MM-DD.
min_unitsnumberOnly associations with at least this many units.
max_unitsnumberOnly associations with at most this many units.
min_magnitudenumberMinimum change magnitude, 0 to 1. Higher means a larger share of the board or record changed at once.
limitnumberRows to return, 1 to 1000 (default 100). Clamped to your plan row cap.
offsetnumberPagination offset (default 0).

Response fields

ParameterTypeDescription
iduuidStable id for this change event.
organization_iduuidThe association the change was observed on.
organization_namestringAssociation legal name.
directory_slugstring | nullKebab-case slug for the public directory page.
subtypestring | null"hoa", "condo", or "coop".
citystring | nullCity on the association record.
countystring | nullCounty on the association record.
statestring | nullTwo-letter state code.
unit_countnumber | nullUnits or lots in the community, where known.
change_kindstringOne of the 13 kinds listed above.
observed_ondateDate the change was observed in the source record.
magnitudenumber | nullRelative size of the change, 0 to 1.
detailobjectPerson-free summary of what changed. Null keys are stripped, so a given event carries only the relevant subset of: seats_affected, titles_affected, board_size, previous_manager, new_manager, previous_status, new_status, previous_name, new_name.

Example request

curl "https://commonelements.com/api/v1/changes?kind=management_company_changed,board_turnover&state=FL&since=2026-06-01&min_units=100&limit=50" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "3f6b1c2e-7a41-4d0b-9f52-8c1e0a4d7b93",
      "organization_id": "0b9d4f21-3c88-4a17-b5e2-6d7f109c4a55",
      "organization_name": "PELICAN BAY COMMUNITY ASSOCIATION, INC.",
      "directory_slug": "pelican-bay-community-association",
      "subtype": "hoa",
      "city": "Naples",
      "county": "Collier",
      "state": "FL",
      "unit_count": 742,
      "change_kind": "management_company_changed",
      "observed_on": "2026-07-18",
      "magnitude": 0.8,
      "detail": {
        "previous_manager": "GULF COAST PROPERTY MANAGEMENT, INC.",
        "new_manager": "SUNSTATE ASSOCIATION MANAGEMENT, LLC"
      }
    },
    {
      "id": "b1244a90-55f7-4e6c-8d31-2a0f7c93e118",
      "organization_id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af",
      "organization_name": "HARBOUR RIDGE CONDOMINIUM ASSOCIATION, INC.",
      "directory_slug": "harbour-ridge-condominium-association",
      "subtype": "condo",
      "city": "Fort Lauderdale",
      "county": "Broward",
      "state": "FL",
      "unit_count": 214,
      "change_kind": "board_turnover",
      "observed_on": "2026-07-02",
      "magnitude": 0.6,
      "detail": {
        "seats_affected": 3,
        "board_size": 5,
        "titles_affected": ["president", "director"]
      }
    }
  ],
  "pagination": {
    "total": 1284,
    "limit": 50,
    "offset": 0,
    "returned": 50
  },
  "note": "Row cap and lookback window are set by your plan tier. Person-level identity is never included; officer changes are reported as counts and titles."
}
  • No officer names, ever. The feed reads a person-stripped view by construction: officer changes come back as counts and canonical titles, and management changes as firm names. There is no parameter that widens this.
  • "total" in the pagination block is the count of matching rows inside your plan window, not the count in the whole dataset.
  • Two caps stack and the tighter one wins: the per-request free-plan row cap of 10, and your plan row cap in the table above. A free key therefore receives up to 10 rows per request within a 30-day window. When a response was shortened by the free cap it also carries a "row_cap" field in the envelope.

GET/api/v1/changes/summary

Counts by change kind over your window: how many events, across how many distinct associations, in how many states. The cheap call for a dashboard tile or a scheduled digest, and the one to run first when you are sizing the dataset before committing to a plan.

Scope: changes or associationsAvailable on every plan, uncapped: this returns one aggregate row per change kind, not a row listing. The lookback window is set by your plan, the same window /api/v1/changes uses.

Query parameters

ParameterTypeDescription
sincestringEarliest observation date, YYYY-MM-DD. Clamped to your plan lookback window. Available change history varies by source. Observation dates may differ from when changes took effect, and your plan's lookback window does not guarantee that much history.
statestringComma-separated two-letter state codes. Omit for all states.

Response fields

ParameterTypeDescription
change_kindstringOne of the 13 change kinds.
event_countnumberEvents of this kind in the window.
org_countnumberDistinct associations with at least one such event.
states_coverednumberDistinct states represented.

Example request

curl "https://commonelements.com/api/v1/changes/summary?state=FL&since=2026-05-01" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "change_kind": "board_turnover",
      "event_count": 4182,
      "org_count": 3907,
      "states_covered": 1
    },
    {
      "change_kind": "management_company_changed",
      "event_count": 611,
      "org_count": 598,
      "states_covered": 1
    }
  ]
}

Associations

GET/api/v1/associations/lookup

Browse and filter community associations by state, county, subtype or registration number. For a name, `q` is a literal SUBSTRING filter: it matches only when your text appears verbatim in the filed corporate name, so "SUNSET RIDGE CONDO ASSN" will not find "Sunset Ridge Condominium Association, Inc.". If you are reconciling names from your own system, use /api/v1/associations/match instead. If `q` is a street address, the request is resolved against linked parcels (same path as /associations/by-address) rather than as a name substring. Use lookup when you hold an exact key: a registration number, or a real substring of the filed name.

Scope: associationsFree keys: up to 10 rows per request; paid tiers raise the cap.

Query parameters

ParameterTypeDescription
qstringExact substring of the filed corporate name, case-insensitive. Not fuzzy; for messy names use /associations/match. A street address (with ZIP) is resolved as an address, not as a name.
statestringTwo-letter state filter, e.g. "FL".
subtypestringOne of "hoa", "condo", "coop".
countystringCounty filter, case-insensitive, e.g. "Broward" or "Pima".
registration_numberstringExact state registry corp/document number (Sunbiz document number, ACC entity id, ...), case-insensitive. Returned as external_document_number.
limitnumberMax results to return (default 20, max 100; free tier is clamped lower).
offsetnumberPagination offset (default 0).

Example request

curl "https://commonelements.com/api/v1/associations/lookup?q=Pelican+Bay&state=FL" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "0d3f6c2e-...",
      "name": "PELICAN BAY COMMUNITY ASSOCIATION, INC.",
      "display_name": "Pelican Bay Community Association",
      "state": "FL",
      "subtype": "hoa",
      "unit_count": 742,
      "address": "801 Laurel Oak Dr",
      "city": "Naples",
      "zip": "34108",
      "external_document_number": "N04000001234",
      "is_claimed": false,
      "created_at": "2026-05-02T14:11:09.000Z"
    }
  ],
  "total": 3,
  "limit": 20,
  "offset": 0
}

GET/api/v1/associations/match

Fuzzy name matching for entity resolution: given a messy association name from your own system, get back the best-matching Common Elements records with a similarity score. Use this to reconcile a book of business against the directory, where an exact-string lookup would miss "Pelican Bay Comm. Assn." against "PELICAN BAY COMMUNITY ASSOCIATION, INC.". If `q` is a street address (house number, city, state, ZIP), the request is resolved against linked parcels instead of names, the same path as /associations/by-address. Name-scoring an address attaches the wrong community.

Scope: associations

Query parameters

ParameterTypeDescription
q*stringThe name to match, minimum 3 characters. A street address (with ZIP) is resolved as an address, not as a name.
state*stringTwo-letter state code. Required; matching is scoped per state.
countystringOptional county filter, case-insensitive.
min_similaritynumberTrigram similarity floor, 0.1 to 0.99 (default 0.25). Raise it for stricter matches.
limitnumberMax candidates to return, 1 to 10 (default 5).

Response fields

ParameterTypeDescription
iduuidCommon Elements id for the matched record.
canonical_namestringNormalized association name.
simnumberTrigram similarity against your query, 0 to 1. Rows come back ranked. Parcel hits use 1 (exact) or 0.99 (building) so a client that thresholds on sim still keeps a real address match.
resolved_via"name" | "address" | "legal_description"How this request was resolved. Address-shaped q never falls through to name matching.
matched_address / match_confidencestring | nullPresent when resolved_via is address: the indexed parcel and exact or building.
unit_countnumber | nullPresent when resolved_via is address. Units in the association, where known and above our confidence floor; null does not mean zero.
county / statestring | nullLocation on the matched record.
sunbiz_corp_idstring | nullState corporate registry id, where known.
registration_statusstring | nullRegistry status on the record.
registered_at / last_filing_attimestamp | nullRegistry formation and most recent filing timestamps.
cam_firm_namestring | nullManagement firm of record, where known.
cam_license_number / cam_license_statusstring | nullLicense of the management firm of record.
association_typestring | nullAssociation type on the record.
sb_4d_applicableboolean | nullWhether Florida SB 4-D structural requirements are recorded as applicable.
sb_4d_inspection_status / sb_4d_last_inspection_atstring | timestamp | nullRecorded SB 4-D inspection state.
data_provenanceobject | nullPer-field source attribution for the record.
last_refreshed_attimestamp | nullWhen the record was last refreshed from source.
ai_summary / ai_summary_generated_atstring | timestamp | nullGenerated plain-language summary, where one exists.

Example request

curl "https://commonelements.com/api/v1/associations/match?q=Pelican%20Bay%20Comm%20Assn&state=FL&min_similarity=0.3" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "0b9d4f21-3c88-4a17-b5e2-6d7f109c4a55",
      "canonical_name": "PELICAN BAY COMMUNITY ASSOCIATION, INC.",
      "county": "Collier",
      "state": "FL",
      "sunbiz_corp_id": "N04000001234",
      "registration_status": "ACTIVE",
      "cam_firm_name": "GULF COAST PROPERTY MANAGEMENT, INC.",
      "association_type": "hoa",
      "sim": 0.62
    }
  ],
  "query": "Pelican Bay Comm Assn",
  "state": "FL",
  "county": null
}
  • Similarity is trigram-based, so word order matters less than shared character runs. A score above roughly 0.45 is usually a confident match; between 0.25 and 0.45, review before merging.
  • If q looks like a street address, the response includes resolved_via: "address" and match_confidence of exact or building. Those rows are parcel links, not name guesses. An empty list means we do not have that address linked yet. Address-shaped q never falls through to name matching.

GET/api/v1/associations/by-address

Resolve a property address to the association that governs it. Dedicated parcel-backed contract for a book of property addresses. /associations/match and /lookup also route a street-shaped q through this same resolve path so an address is never scored as a name.

Scope: associations

Query parameters

ParameterTypeDescription
address*stringStreet address, minimum 3 characters. Unit numbers are fine — see match_confidence below.
zip*string5-digit ZIP or ZIP+4. A 4-digit ZIP (leading zero dropped by Excel) is padded. Matching is scoped to the ZIP.
limitnumberMax candidates to return, 1 to 5 (default 3).

Response fields

ParameterTypeDescription
organization_iduuidCommon Elements id for the matched association.
association_namestringName of the matched association.
matched_addressstringThe indexed parcel address this query matched, for your own audit trail.
zip5 / statestringLocation on the matched record.
source_tablestringWhich parcel source produced the link (internal provenance, not stable API surface).
match_confidence"exact" | "building""exact" is a normalized address match. "building" means your address included a unit and the indexed parcel is the building it sits in — the common shape for a condo, where our source data is building-level.
unit_countnumber | nullUnits in the association, where known and above our confidence floor. Null does not mean zero — it means we do not have a trustworthy count for this one yet.

Example request

curl "https://commonelements.com/api/v1/associations/by-address?address=2290%20SE%205th%20Court%2C%20Unit%204&zip=33033" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "organization_id": "0572f345-0763-4eed-810e-72a25aea4a50",
      "association_name": "KEYS GATE CONDO NO. 2",
      "matched_address": "2290 SE 5 CT",
      "zip5": "33033",
      "state": "FL",
      "source_table": "association_parcels",
      "match_confidence": "building",
      "unit_count": 42
    }
  ]
}
  • Coverage is real but not complete everywhere: this only returns a hit where a parcel has already been deterministically linked to an association. An empty result includes a hint pointing at /associations/match as a name-based fallback. It does not mean the property has no association, only that we do not have the link yet.
  • Nothing here is a guess made at request time. A result is always a parcel a matcher already linked to an organization, never a fuzzy score computed on the fly — which is what makes /match the wrong tool for this and this the wrong tool for a bare name.

GET/api/v1/associations/nearby

Find associations within a radius of a coordinate, sorted nearest first. Built for "what communities are around this property" workflows: territory planning, route density for a service vendor, or comparable-community selection.

Scope: associationsFree keys: up to 10 rows per request; paid tiers raise the cap.

Query parameters

ParameterTypeDescription
lat*numberLatitude, -90 to 90.
lng*numberLongitude, -180 to 180.
radius_kmnumberSearch radius in kilometres, 0.1 to 50 (default 2).
subtypestringOne of "hoa", "condo", "coop".
limitnumberMax results, 1 to 50 (default 20).

Response fields

ParameterTypeDescription
iduuidAssociation id.
namestringAssociation legal name.
subtypestring | null"hoa", "condo", or "coop".
city / county / state / zipstring | nullLocation on the association record.
lat / lngnumberCoordinates the distance was computed from.
unit_countnumber | nullUnits or lots, where known.
external_document_numberstring | nullState registration document number.
distance_mnumberDistance from your centre point in metres, rounded.

Example request

curl "https://commonelements.com/api/v1/associations/nearby?lat=26.2379&lng=-81.8095&radius_km=5&subtype=condo&limit=10" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af",
      "name": "HARBOUR RIDGE CONDOMINIUM ASSOCIATION, INC.",
      "subtype": "condo",
      "city": "Naples",
      "county": "Collier",
      "state": "FL",
      "zip": "34108",
      "lat": 26.2401,
      "lng": -81.8062,
      "unit_count": 214,
      "external_document_number": "N04000001234",
      "distance_m": 412
    }
  ],
  "center": { "lat": 26.2379, "lng": -81.8095 },
  "radius_km": 5
}
  • Only associations with recorded coordinates are searchable here. Coverage of geocoded records varies by state, so an empty result is not proof no association exists at that location.

GET/api/v1/associations/{id}/risk

Retrieve flood zone, reserve-study health, and geographic risk signals for a specific association. Useful for underwriting, due diligence, and loan origination workflows.

Scope: risk

Path parameters

ParameterTypeDescription
id*stringAssociation ID from the lookup endpoint.

Example request

curl "https://commonelements.com/api/v1/associations/0b9d4f21-3c88-4a17-b5e2-6d7f109c4a55/risk" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "association_id": "0b9d4f21-3c88-4a17-b5e2-6d7f109c4a55",
  "flood_zone": "AE",
  "fema_firm_panel": "12021C0454H",
  "reserve_health": {
    "funded_percent": 62,
    "study_year": 2023,
    "next_study_due": 2028
  },
  "risk_signals": [
    { "type": "coastal_proximity", "value": "0.8mi", "severity": "medium" }
  ],
  "data_as_of": "2026-01-15"
}

GET/api/v1/associations/{id}/building-safety

Everything on public record about an association’s physical buildings, joined into one call: Florida SIRS filings, county milestone/recertification rolls, elevator certificates, pool inspections, parcel building characteristics, and HUD FHA condo approval. The structural sibling of the risk endpoint, which reports county-level FEMA hazard instead.

Scope: risk

Path parameters

ParameterTypeDescription
id*stringAssociation UUID.

Response fields

ParameterTypeDescription
sirsobjectStructural Integrity Reserve Study filings: on_file, project_count, and the projects array.
milestoneobjectCounty recertification roll: status and due of the record with the latest due date, record_count, and every records row so you can apply your own rule.
elevatorsobjectcount, delinquent, delinquent_count, earliest_expiry, max_landings, and the certificates array from the FL DBPR elevator safety roll.
poolsobjectinspection_count, last_inspection_date, last_result, last_violations, and the inspections array from FL DOH.
structureobjectmax_stories, max_building_height_ft, earliest_year_built, three_plus_story_building (null when no characteristics row exists, not false), and the buildings array.
fhaobjectproject_count, status, status_date, expiration_date, approval_method, and the projects array.
layer_countsobjectRow count per layer: sirs, recertifications, elevators, pool_inspections, characteristics, fha_projects.
has_databooleanFalse when every layer is empty for this association.
sourcestringThe public-record sources behind this response.

Example request

curl "https://commonelements.com/api/v1/associations/c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af/building-safety" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "organization_id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af",
    "name": "HARBOUR RIDGE CONDOMINIUM ASSOCIATION, INC.",
    "state": "FL",
    "county": "Broward",
    "city": "Fort Lauderdale",
    "zip": "33301",
    "subtype": "condo",
    "unit_count": 214,
    "sirs": { "on_file": true, "project_count": 1, "projects": [] },
    "milestone": {
      "status": "Due",
      "due": "2027-12-31",
      "record_count": 2,
      "records": []
    },
    "elevators": {
      "count": 4,
      "delinquent": false,
      "delinquent_count": 0,
      "earliest_expiry": "2027-03-31",
      "max_landings": 12,
      "certificates": []
    },
    "pools": {
      "inspection_count": 6,
      "last_inspection_date": "2026-05-14",
      "last_result": "Satisfactory",
      "last_violations": 0,
      "inspections": []
    },
    "structure": {
      "max_stories": 12,
      "max_building_height_ft": 128,
      "earliest_year_built": 1979,
      "three_plus_story_building": true,
      "buildings": []
    },
    "fha": {
      "project_count": 1,
      "status": "Approved",
      "status_date": "2025-08-01",
      "expiration_date": "2028-08-01",
      "approval_method": "HRAP",
      "projects": []
    },
    "layer_counts": {
      "sirs": 1,
      "recertifications": 2,
      "elevators": 4,
      "pool_inspections": 6,
      "characteristics": 3,
      "fha_projects": 1
    },
    "has_data": true,
    "source": "FL DBPR (SIRS, elevator safety), county recertification rolls (Miami-Dade RER, Broward BORA), FL DOH pool inspections, county property appraiser building characteristics, HUD FHA condo approvals",
    "note": "Public-record data linked to the association by Common Elements entity resolution. Reference-only; not a structural determination. Coverage varies by county and layer — read layer_counts before treating an absent record as compliance."
  }
}
  • Coverage is uneven by design: county recertification rolls are Miami-Dade and Broward only, SIRS is Florida condo, HUD FHA is national. Branch on has_data and layer_counts. An absent record means nothing was filed with a source we ingest, not that the association is compliant.
  • Arrays are truncated at 500 rows per layer. The example above shows the arrays empty for brevity; live responses carry the rows.
  • Reference data only, not a structural determination. Confirm anything load-bearing with a licensed engineer.

GET/api/v1/associations/{id}/vendors

The vendors and service providers an association is on record working with, from confirmed relationship edges in the Common Elements graph. Answers "who already services this community" before you bid against them or refer into them.

Scope: associations

Path parameters

ParameterTypeDescription
id*stringAssociation UUID.

Response fields

ParameterTypeDescription
iduuidVendor organization id.
namestringVendor legal name.
subtypestring | nullVendor subtype.
city / statestring | nullVendor location.
websitestring | nullVendor website.
verification_statusstring | nullWhether the vendor org is verified on the platform.
directory_slugstring | nullSlug for the public vendor directory page.
review_count / review_avg_ratingnumber | nullPlatform review volume and average rating.
relationship_typestring | null"under_contract" or "represented_by". This is the edge type behind the row.
relationship_statusstring | nullEdge status; only active edges are returned.
start_date / end_datedate | nullContract window, where recorded.
contract_valuenumber | nullContract value, where recorded.

Example request

curl "https://commonelements.com/api/v1/associations/c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af/vendors" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604",
      "name": "COASTAL LANDSCAPE SERVICES, LLC",
      "subtype": "landscaping",
      "city": "Fort Lauderdale",
      "state": "FL",
      "website": "https://example.com",
      "verification_status": "verified",
      "directory_slug": "coastal-landscape-services",
      "review_count": 12,
      "review_avg_rating": 4.6,
      "relationship_type": "under_contract",
      "relationship_status": "active",
      "start_date": "2025-01-01",
      "end_date": null,
      "contract_value": 84000
    }
  ],
  "association_id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af"
}
  • Only confirmed, active relationships appear. An empty array means no vendor edge is recorded, not that the association self-performs the work.

GET/api/v1/associations/{id}

The core record for one association: identity, location, registration status, and management-firm-of-record, in one call. The starting point once you have an id from lookup, match, or nearby.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Response fields

ParameterTypeDescription
iduuidAssociation id.
namestringLegal name.
state / county / city / zipstring | nullLocation on the record.
subtypestring | null"hoa", "condo", or "coop".
unit_countnumber | nullUnits or lots, where known.
addressstring | nullStreet address.
lat / lngnumber | nullCoordinates, where geocoded.
website / phonestring | nullPublic contact info on the record, where present.
is_claimedbooleanWhether a board member or manager has claimed this record on the platform.
registration_statusstring | nullState corporate registry status (e.g. "ACTIVE").
external_document_numberstring | nullState registration document number.
management_firmstring | nullManagement company of record, where known.
created_at / updated_attimestampRecord lifecycle timestamps.

Example request

curl "https://commonelements.com/api/v1/associations/c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af",
    "name": "HARBOUR RIDGE CONDOMINIUM ASSOCIATION, INC.",
    "state": "FL",
    "county": "Broward",
    "subtype": "condo",
    "unit_count": 214,
    "address": "1500 Harbour Ridge Blvd",
    "city": "Fort Lauderdale",
    "zip": "33301",
    "lat": 26.2401,
    "lng": -81.8062,
    "website": null,
    "phone": null,
    "is_claimed": true,
    "registration_status": "ACTIVE",
    "external_document_number": "N04000001234",
    "management_firm": "SUNSTATE ASSOCIATION MANAGEMENT, LLC",
    "created_at": "2025-02-11T14:03:00Z",
    "updated_at": "2026-07-18T09:22:00Z"
  }
}

GET/api/v1/associations/{id}/officers

The current board/officer roster on file for an association, from state officer filings. Coverage is strongest in the eight states with published officer rolls. Board-turnover events on the change feed come from diffing successive snapshots of this roster, so they currently exist only for the states that have had more than one snapshot.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Response fields

ParameterTypeDescription
officer_titlestringTitle as filed (e.g. "President", "Director").
first_name / last_namestringOfficer name as filed.
middle_initial / suffixstring | nullAdditional name parts, where present.
city / county / statestring | nullLocation on the filing, not necessarily the officer's residence.
directory_sourcestringThe state filing source this row came from.
source_snapshot_labelstringWhich ingested snapshot this row belongs to.
is_resolvedbooleanWhether this filing row has been matched to a canonical person record.

Example request

curl "https://commonelements.com/api/v1/associations/c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af/officers" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "officer_title": "President",
      "first_name": "JANE",
      "middle_initial": null,
      "last_name": "MARTINEZ",
      "suffix": null,
      "city": "Fort Lauderdale",
      "county": "Broward",
      "state": "FL",
      "directory_source": "fl_sunbiz",
      "source_snapshot_label": "2026-07-15",
      "is_resolved": true
    }
  ],
  "association_id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af"
}
  • This is the current roster only. For board history over time (who served when, and each turnover as an event), use data.commonelements.com or the change feed's board_turnover / officer_* events.
  • An empty array means no officer filing is on record for this association, not necessarily that the board has vacancies.

GET/api/v1/associations/{id}/management

Who manages this association, from two independent sources: the manager-association graph built from state CAM/registration filings (ranked by source priority), and any confirmed management relationship recorded on the platform itself.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Response fields

ParameterTypeDescription
managersarrayRows from state filings: manager_name, source, priority, and provenance, ranked highest-priority first.
confirmed_relationshipsarrayPlatform-confirmed management edges: to_org_id (the management company's org id), relationship_type ("managed_by"), status, start_date, end_date, contract_value.

Example request

curl "https://commonelements.com/api/v1/associations/c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af/management" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "managers": [
      {
        "manager_name": "SUNSTATE ASSOCIATION MANAGEMENT, LLC",
        "source": "fl_dbpr_cam",
        "priority": 3,
        "provenance": "DBPR licensee-of-record filing"
      }
    ],
    "confirmed_relationships": []
  },
  "association_id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af"
}
  • The two arrays can disagree, and that is meaningful: managers reflects the state filing, confirmed_relationships reflects what the platform's own users have confirmed. Treat managers as the source of record when they differ; confirmed_relationships is corroborating, not authoritative.
  • Both empty means no manager is on record at all, which for a professionally-managed association usually means self-managed or an unfiled change.

GET/api/v1/associations/{id}/buildings

Building footprint, roof/facade area estimates, floor count, and recorded structural facts (measured stories, year built, FL Ch. 553 milestone relevance) for an association, derived from mapped building outlines and county parcel rolls.

Scope: valuations

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Response fields

ParameterTypeDescription
building_countnumberMapped buildings for this association.
total_footprint_sqft / total_footprint_sqmnumber | nullSummed footprint area across mapped buildings.
primary_building_sqft / avg_footprint_sqmnumber | nullLargest building's footprint, and the average across all of them.
roof_area_sqft_estimatenumber | nullEstimated from footprint; add a pitch multiplier for sloped roofs.
facade_area_sqft_estimatenumber | nullPerimeter x height estimate. A starting point for painting/waterproofing scope.
floors_estimatenumber | nullRough estimate from measured height only. Not a milestone determination.
max_height_mnumber | nullMeasured height, capped ~34m by the underlying source; null when unmeasured. Never a hard stories count.
height_confidencestring | nullConfidence label for the height figure.
storiesnumber | nullRecorded stories from the county parcel roll (FL only currently) — measured, not estimated.
year_builtnumber | nullEarliest recorded year built across the association's buildings.
milestone_inspection_relevantboolean | nullTrue when a recorded building has 3+ stories — the real FL Ch. 553 signal. Reference-only.
structural_source / source / attributionstring | nullWhere each figure came from.

Example request

curl "https://commonelements.com/api/v1/associations/c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af/buildings" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "organization_id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af",
    "name": "HARBOUR RIDGE CONDOMINIUM ASSOCIATION, INC.",
    "state": "FL",
    "unit_count": 214,
    "building_count": 3,
    "total_footprint_sqft": 48210,
    "roof_area_sqft_estimate": 48210,
    "facade_area_sqft_estimate": 61500,
    "floors_estimate": 11,
    "max_height_m": 34.5,
    "height_confidence": "medium",
    "stories": 12,
    "year_built": 1979,
    "milestone_inspection_relevant": true,
    "structural_source": "FL DOR parcel roll (fl_association_characteristics)",
    "source": "overture_maps",
    "attribution": "Overture Maps building footprints",
    "note": "Building footprint data derived from mapped outlines (Overture Maps). Reference-only; not a survey or underwriting-grade valuation."
  }
}
  • Requires the "valuations" scope, not "associations" — the one endpoint in this group that does.
  • Footprint coverage is uneven outside FL/NC/MA/NY/WI; a low building_count can mean sparse mapping, not a small property. Recorded structural facts (stories, year_built, milestone_inspection_relevant) are Florida-only today.
  • Reference data only. Confirm anything load-bearing with a licensed engineer.

Statutes

Full-text search across the community-association statute corpus, ranked by relevance. The endpoint behind the statute search on commonelements.com, available programmatically.

Scope: statutes or associationsFree keys: up to 10 rows per request; paid tiers raise the cap.

Query parameters

ParameterTypeDescription
q*stringSearch text, minimum 2 characters.
statestringTwo-letter state code to scope results to one jurisdiction. Omit to search every jurisdiction.
limitnumberMax results, 1 to 25 (default 10).
offsetnumberPagination offset (default 0).

Response fields

ParameterTypeDescription
section_iduuidStatute section id, for use with /v1/statutes/sections/{id}.
chapter_slug / chapter_short_title / chapter_jurisdiction / chapter_numberstringThe chapter this section belongs to.
section_number / subsectionstring | nullSection numbering as published.
section_slugstringSlug for the public statute page.
title / summarystring | nullSection title and plain-language summary.
snippetstring | nullSearch-result highlight from the matched text.
ranknumberRelevance score. Results are pre-sorted by this, highest first.

Example request

curl "https://commonelements.com/api/v1/statutes/search?q=reserve+study&state=FL" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "query": "reserve study",
  "state": "FL",
  "data": [
    {
      "section_id": "8a3f0c1e-2b4d-4e9a-9f0c-1e2b4d4e9a9f",
      "chapter_id": "chp_...",
      "chapter_slug": "florida-718",
      "chapter_short_title": "Condominium Act",
      "chapter_jurisdiction": "FL",
      "chapter_number": "718",
      "section_number": "718.112",
      "subsection": "2",
      "section_slug": "718-112-bylaws",
      "title": "Bylaws; reserve accounts",
      "summary": "Requires reserve accounts for capital expenditures and deferred maintenance...",
      "snippet": "...the association shall include reserve accounts for capital expenditures and deferred maintenance...",
      "rank": 0.87
    }
  ],
  "count": 1
}

GET/api/v1/statutes/by-state

Browse/enumerate every statute section on file for a state, grouped by chapter — the companion to statutes/search for "show me everything" rather than a keyword match. Filter to one chapter or a tagged topic.

Scope: statutes or associationsFree keys: up to 10 rows per request; paid tiers raise the cap.

Query parameters

ParameterTypeDescription
state*stringTwo-letter state code.
chapterstringLimit to one chapter number.
topicstringLimit to sections tagged with this topic.
limitnumberMax results, 1 to 200 (default 100).
offsetnumberPagination offset (default 0).

Response fields

ParameterTypeDescription
iduuidStatute section id.
chapter_number / chapter_titlestring | nullThe chapter this section belongs to.
section_number / subsectionstring | nullSection numbering as published.
slugstringSlug for the public statute page.
title / summarystring | nullSection title and plain-language summary.
topicsstring[]Tagged topics for this section.
citationstring | nullFormatted legal citation, e.g. "Fla. Stat. § 718.112".
effective_datedate | nullWhen this version took effect.
source_urlstring | nullLink to the official published text.

Example request

curl "https://commonelements.com/api/v1/statutes/by-state?state=FL&chapter=718" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "8a3f0c1e-2b4d-4e9a-9f0c-1e2b4d4e9a9f",
      "chapter_number": "718",
      "chapter_title": "Condominium Act",
      "section_number": "718.112",
      "subsection": "2",
      "slug": "718-112-bylaws",
      "title": "Bylaws; reserve accounts",
      "summary": "Requires reserve accounts for capital expenditures and deferred maintenance...",
      "topics": ["reserves", "bylaws"],
      "citation": "Fla. Stat. § 718.112",
      "effective_date": "2026-07-01",
      "source_url": "https://www.leg.state.fl.us/..."
    }
  ],
  "state": "FL",
  "pagination": { "total": 214, "limit": 100, "offset": 0 }
}

GET/api/v1/statutes/sections/{id}

The full text and metadata for one statute section, including its parent chapter and formatted citation. Follow-up call after search or by-state to read the section in full.

Scope: statutes or associations

Path parameters

ParameterTypeDescription
id*uuidSection id from search or by-state.

Response fields

ParameterTypeDescription
section_iduuidStatute section id.
section_number / subsectionstring | nullSection numbering as published.
title / summarystring | nullSection title and plain-language summary.
body_textstringFull text of the section.
topicsstring[]Tagged topics for this section.
effective_date / source_urldate | string | nullEffective date and link to the official published text.
chapterobjectid, slug, jurisdiction, chapter_number, short_title, citation_format for the parent chapter.
citationstringFormatted legal citation for this exact section.

Example request

curl "https://commonelements.com/api/v1/statutes/sections/8a3f0c1e-2b4d-4e9a-9f0c-1e2b4d4e9a9f" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "section_id": "8a3f0c1e-2b4d-4e9a-9f0c-1e2b4d4e9a9f",
    "section_number": "718.112",
    "subsection": "2",
    "title": "Bylaws; reserve accounts",
    "summary": "Requires reserve accounts for capital expenditures and deferred maintenance...",
    "body_text": "(2) BYLAWS. (a) The original bylaws of the association...",
    "topics": ["reserves", "bylaws"],
    "effective_date": "2026-07-01",
    "source_url": "https://www.leg.state.fl.us/...",
    "chapter": {
      "id": "chp_...",
      "slug": "florida-718",
      "jurisdiction": "FL",
      "chapter_number": "718",
      "short_title": "Condominium Act",
      "citation_format": "Fla. Stat. § {section}"
    },
    "citation": "Fla. Stat. § 718.112(2)"
  }
}

Vendors

GET/api/v1/vendors

Search the public vendor directory: verified vendors only, ranked by review rating. Filter by name/description text, state (home or served), or service category.

Scope: vendors.readFree keys: up to 10 rows per request; paid tiers raise the cap.

Query parameters

ParameterTypeDescription
qstringFree-text search over name and description.
statestringTwo-letter state code. Matches either the vendor's home state or a state it serves.
categorystringA vendor-category slug, matched against the vendor's self-tagged service categories.
limitnumberMax results per page. Free keys are capped at 10; paid tiers get a higher cap.
offsetnumberPagination offset (default 0).

Response fields

ParameterTypeDescription
iduuidVendor organization id.
namestringVendor legal name.
subtypestring | nullVendor category subtype.
city / state / zipstring | nullVendor location.
websitestring | nullVendor website.
service_statesstring[]States the vendor reports serving.
directory_slugstring | nullSlug for the public vendor directory page.
review_count / review_avg_ratingnumber | nullPlatform review volume and average rating. Results are sorted by rating, highest first.
descriptionstring | nullVendor-authored description.
service_categories / service_countiesstring[]Vendor-self-asserted service scope.
license_number / insurance_carrierstring | nullVendor-self-asserted credentials. Not independently verified at this endpoint — see /v1/vendors/{id} for the verified trust profile.

Example request

curl "https://commonelements.com/api/v1/vendors?state=FL&category=roofing" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604",
      "name": "COASTAL ROOFING SOLUTIONS, LLC",
      "subtype": "roofing",
      "city": "Fort Lauderdale",
      "state": "FL",
      "zip": "33301",
      "website": "https://example.com",
      "service_states": ["FL"],
      "directory_slug": "coastal-roofing-solutions",
      "review_count": 24,
      "review_avg_rating": 4.8,
      "description": "Licensed commercial and residential roofing serving South Florida HOAs and condos.",
      "service_categories": ["roofing"],
      "service_counties": ["Broward", "Miami-Dade"],
      "license_number": "CCC1234567",
      "insurance_carrier": null
    }
  ],
  "total": 1,
  "limit": 10,
  "offset": 0
}
  • Only verified vendors are listed. Coverage grows as vendors complete verification — see the note this endpoint returns on an empty result for the current count.

GET/api/v1/vendors/{id}

The full public profile for one verified vendor: identity, self-reported service offerings, review summary, and the neutral, independently-sourced trust profile (workers' comp status, professional licenses, enforcement history) pulled from public records.

Scope: vendors.read

Path parameters

ParameterTypeDescription
id*uuidVendor organization id.

Response fields

ParameterTypeDescription
id / name / subtype / city / state / zip / websitestring | nullVendor identity and location.
verification_statusstringAlways "verified" for a row this endpoint returns.
service_statesstring[]States the vendor reports serving.
review_count / review_avg_ratingnumber | nullPlatform review summary.
description / license_number / insurance_carrier / team_size / booth_taglinestring | nullVendor-self-asserted display fields.
services_offered / certifications / service_categories / service_countiesstring[]Vendor-self-asserted service scope and credentials.
service_offeringsarrayPublished offering posts: id, title, body, category_slugs, service_states, service_counties, pinned, published_at.
trust_profileobject | nullIndependently-sourced, public-record credential facts (FL workers'-comp status, professional licenses, enforcement count). Null when the vendor has no confirmed public-record match — this is the verified boundary, distinct from the self-asserted fields above.
created_attimestampWhen the vendor record was created.

Example request

curl "https://commonelements.com/api/v1/vendors/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "id": "9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604",
    "name": "COASTAL ROOFING SOLUTIONS, LLC",
    "subtype": "roofing",
    "city": "Fort Lauderdale",
    "state": "FL",
    "zip": "33301",
    "website": "https://example.com",
    "verification_status": "verified",
    "service_states": ["FL"],
    "directory_slug": "coastal-roofing-solutions",
    "review_count": 24,
    "review_avg_rating": 4.8,
    "follower_count": 6,
    "description": "Licensed commercial and residential roofing serving South Florida HOAs and condos.",
    "service_categories": ["roofing"],
    "service_counties": ["Broward", "Miami-Dade"],
    "license_number": "CCC1234567",
    "insurance_carrier": null,
    "year_established": 2011,
    "team_size": "11-50",
    "booth_tagline": "24/7 emergency roof response for South Florida associations.",
    "services_offered": ["Roof replacement", "Storm damage repair"],
    "certifications": ["GAF Master Elite"],
    "service_offerings": [],
    "trust_profile": {
      "workers_comp_status": "active",
      "licenses": [{ "type": "CCC", "number": "CCC1234567", "status": "active" }],
      "enforcement_count": 0
    },
    "created_at": "2025-06-01T00:00:00Z"
  }
}
  • Never returns private contact data, street address lines, phone, or email. That data does not exist on this endpoint at all, not merely hidden.
  • Distinguish self-asserted from verified: description/services_offered/certifications/license_number are what the vendor states about itself; trust_profile is what public records independently confirm.

GET/api/v1/vendors/{id}/reviews

Published reviews for a vendor, newest first. Every review is tied to a completed RFP or proposal, so each one is a verified-buyer review, not an open review anyone can post.

Scope: vendors

Path parameters

ParameterTypeDescription
id*uuidVendor organization id.

Query parameters

ParameterTypeDescription
limitnumberMax results, 1 to 100 (default 25).
offsetnumberPagination offset (default 0).

Response fields

ParameterTypeDescription
iduuidReview id.
ratingnumber1 to 5.
bodystringReview text.
created_at / updated_attimestampReview lifecycle timestamps.

Example request

curl "https://commonelements.com/api/v1/vendors/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/reviews" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "f1a2b3c4-5d6e-4f70-8a91-2b3c4d5e6f70",
      "rating": 5,
      "body": "Responsive and finished ahead of schedule after the storm.",
      "created_at": "2026-06-02T00:00:00Z",
      "updated_at": "2026-06-02T00:00:00Z"
    }
  ],
  "vendor_id": "9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604",
  "total": 1,
  "limit": 25,
  "offset": 0
}
  • Reviewer identity is never included, by design — the reviewing association is withheld to keep the projection neutral.

Professionals and licenses

GET/api/v1/licenses/verify

Verify a professional license against the state board roll by license number, or by name when you do not have the number. Returns the raw status and expiry plus two derived flags, because a status that reads "current" can still be past its expiry date.

Scope: licenses

Query parameters

ParameterTypeDescription
license_numberstringExact license number. Provide this or name.
namestringLicensee name, substring match. Provide this or license_number.
state*stringTwo-letter state code.
license_typestringSubstring filter on license type, e.g. "CAM".
limitnumberMax results, 1 to 25 (default 10).

Response fields

ParameterTypeDescription
license_numberstringLicense number as issued.
license_type / license_type_descstring | nullLicense class and its description.
name / dbastring | nullLicensee name and trade name.
statusstring | nullBoard status verbatim from the source roll.
issue_date / expiry_datedate | nullLicense dates verbatim from the source roll.
city / countystring | nullAddress of record.
boardstring | nullIssuing board.
organization_iduuid | nullLinked Common Elements org, when the licensee resolves to one.
is_expiredbooleanTrue when expiry_date is in the past.
is_activebooleanThe trust signal to branch on: status reads current/active/valid/clear AND the license is not past expiry.

Example request

curl "https://commonelements.com/api/v1/licenses/verify?license_number=CAM12345&state=FL" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "license_number": "CAM12345",
      "license_type": "CAM",
      "license_type_desc": "Community Association Manager",
      "name": "SAMPLE LICENSEE",
      "dba": null,
      "status": "Current",
      "issue_date": "2019-04-02",
      "expiry_date": "2027-09-30",
      "city": "Naples",
      "county": "Collier",
      "board": "Regulatory Council of Community Association Managers",
      "organization_id": null,
      "is_expired": false,
      "is_active": true
    }
  ],
  "state": "FL"
}
  • Branch on is_active, not on status. A board roll can carry a "Current" status on a license whose expiry date has already passed.

Search the licensed professional graph: community association managers, contractors, engineers, and the firms they work under, from state licensing board rolls. Filter by name, state, license type, board, or status.

Scope: professionalsFree keys: up to 10 rows per request; paid tiers raise the cap.

Query parameters

ParameterTypeDescription
qstringLicensee name, substring match. Minimum 2 characters.
statestringTwo-letter state code.
license_typestringExact license type, e.g. "CAM".
boardstringExact issuing board name.
statusstringExact board status.
limitnumberRows to return, 1 to 100 (default 25).
offsetnumberPagination offset (default 0).

Response fields

ParameterTypeDescription
iduuidLicense record id. Pass this to the detail endpoints below.
state / boardstringIssuing jurisdiction and board.
license_number / license_type / license_type_descstring | nullLicense identity.
name / dbastring | nullLicensee name and trade name.
statusstring | nullBoard status verbatim.
issue_date / expiry_datedate | nullLicense dates verbatim.
is_expiredbooleanTrue when expiry_date is in the past.
city / county / zipstring | nullAddress of record.
organization_iduuid | nullLinked Common Elements org, when one is resolved.

Example request

curl "https://commonelements.com/api/v1/professionals/search?state=FL&license_type=CAM&q=coastal&limit=25" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "5e3b8c17-2af9-4d60-9a11-77c04e5b8d32",
      "state": "FL",
      "board": "Regulatory Council of Community Association Managers",
      "license_number": "CAM12345",
      "license_type": "CAM",
      "license_type_desc": "Community Association Manager",
      "name": "COASTAL ASSOCIATION MANAGEMENT, LLC",
      "dba": null,
      "status": "Current",
      "issue_date": "2019-04-02",
      "expiry_date": "2027-09-30",
      "is_expired": false,
      "city": "Naples",
      "county": "Collier",
      "zip": "34108",
      "organization_id": "7d1e2a90-6b4c-4f31-a8d5-9c0f3e7b1246"
    }
  ],
  "total": 37,
  "limit": 25,
  "offset": 0
}
  • At least one of q, state, license_type, or board is required. The roll is multi-million rows and cannot be paged unfiltered. Omitting all four returns a 400.

GET/api/v1/professionals/{id}

The full single-record projection for one licensed professional or firm, including the city/county/zip of record and the linked Common Elements organization. The street address is not returned: a licence with no firm and no d/b/a is an individual, and that address is overwhelmingly a home.

Scope: professionals

Path parameters

ParameterTypeDescription
id*stringLicense record UUID, from the search endpoint.

Response fields

ParameterTypeDescription
iduuidLicense record id.
state / boardstringIssuing jurisdiction and board.
license_number / license_type / license_type_descstring | nullLicense identity.
name / dbastring | nullLicensee name and trade name.
statusstring | nullBoard status verbatim.
issue_date / expiry_datedate | nullLicense dates verbatim.
is_expiredbooleanTrue when expiry_date is in the past.
city / county / zipstring | nullAddress of record, to locality level. The street line is never returned.
organization_iduuid | nullLinked Common Elements org, when one is resolved.
created_attimestampWhen the record entered Common Elements.

Example request

curl "https://commonelements.com/api/v1/professionals/5e3b8c17-2af9-4d60-9a11-77c04e5b8d32" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "id": "5e3b8c17-2af9-4d60-9a11-77c04e5b8d32",
    "state": "FL",
    "board": "Regulatory Council of Community Association Managers",
    "license_number": "CAM12345",
    "license_type": "CAM",
    "license_type_desc": "Community Association Manager",
    "name": "COASTAL ASSOCIATION MANAGEMENT, LLC",
    "dba": null,
    "status": "Current",
    "issue_date": "2019-04-02",
    "expiry_date": "2027-09-30",
    "is_expired": false,
    "city": "Naples",
    "county": "Collier",
    "zip": "34108",
    "organization_id": "7d1e2a90-6b4c-4f31-a8d5-9c0f3e7b1246",
    "created_at": "2026-06-06T08:00:00.000Z"
  }
}
  • Business address of record only. No personal email or phone is returned by any Common Elements endpoint.

GET/api/v1/professionals/{id}/associations

The communities a professional or firm is on record serving: the manager-to-portfolio view. Merges confirmed relationship edges with name-matched rows from the public management registry, de-duplicated, with the provenance of each row.

Scope: professionals

Path parameters

ParameterTypeDescription
id*stringLicense record UUID, from the search endpoint.

Response fields

ParameterTypeDescription
iduuidAssociation organization id.
namestringAssociation legal name.
subtypestring | null"hoa", "condo", or "coop".
city / statestring | nullAssociation location.
directory_slugstring | nullSlug for the public directory page.
sourcestringHow this row was resolved: "relationship:<type>" for a confirmed graph edge (managed_by, under_contract, represented_by), or "manager_view:<source>" for a name match against the public management registry.

Example request

curl "https://commonelements.com/api/v1/professionals/5e3b8c17-2af9-4d60-9a11-77c04e5b8d32/associations" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "c4d0a7e5-91b3-4f28-8a6d-0e51937bb2af",
      "name": "HARBOUR RIDGE CONDOMINIUM ASSOCIATION, INC.",
      "subtype": "condo",
      "city": "Fort Lauderdale",
      "state": "FL",
      "directory_slug": "harbour-ridge-condominium-association",
      "source": "relationship:managed_by"
    },
    {
      "id": "0b9d4f21-3c88-4a17-b5e2-6d7f109c4a55",
      "name": "PELICAN BAY COMMUNITY ASSOCIATION, INC.",
      "subtype": "hoa",
      "city": "Naples",
      "state": "FL",
      "directory_slug": "pelican-bay-community-association",
      "source": "manager_view:dbpr_condo"
    }
  ],
  "professional_id": "5e3b8c17-2af9-4d60-9a11-77c04e5b8d32",
  "linked_org_id": "7d1e2a90-6b4c-4f31-a8d5-9c0f3e7b1246"
}
  • Read the source field before treating a row as confirmed. A "relationship:" row is a confirmed edge in the graph; a "manager_view:" row is a name match against a public registry and carries the ambiguity of name matching.
  • When the license has no linked organization (linked_org_id is null), only name-matched rows are returned.

Aggregates and compliance

GET/api/v1/geo/state-summary

Per-state rollup of the dataset: association counts broken out by subtype, plus insurance licensee counts. The market-sizing call: how much of a state the data covers before you build against it.

Scope: associationsAvailable on every plan, uncapped: this returns one row per state, not a row listing.

Query parameters

ParameterTypeDescription
statestringTwo-letter state code. Omit for every state, ranked by association count.

Response fields

ParameterTypeDescription
statestringTwo-letter state code.
association_countnumberAssociations in the state, summed across subtypes.
by_subtypeobjectSubtype to count, e.g. { "hoa": 51204, "condo": 27810 }.
insurance_licensee_countnumberInsurance licensees recorded in the state.
insurance_active_countnumberOf those, the ones recorded as active.

Example request

curl "https://commonelements.com/api/v1/geo/state-summary?state=FL" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "state": "FL",
      "association_count": 79014,
      "by_subtype": { "hoa": 51204, "condo": 27810 },
      "insurance_licensee_count": 43638,
      "insurance_active_count": 39120
    }
  ],
  "total": 1
}
  • Aggregate counts only. No per-association rows, no personal data. Counts move as ingestion runs, so treat them as current rather than fixed.

POST/api/v1/compliance/scan

Submit a community association document for automated compliance analysis. Returns a structured assessment against Florida and multi-state statutory requirements, plus best-practice governance rules.

Scope: compliance

Request body

ParameterTypeDescription
text*stringThe full text of the governing document to analyze.
state*stringTwo-letter state code (e.g. "FL", "GA").
doc_typestringOptional. One of: "governing_document" (default), "cc_and_rs", "bylaws", "articles", "rules_and_regulations".

Example request

curl -X POST https://commonelements.com/api/v1/compliance/scan \
  -H "Authorization: Bearer ce_live_your_key_here" \
  -H "Content-Type: application/json" \
  -d '{
    "text": "Article I. Name. The name of this Association...",
    "state": "FL",
    "doc_type": "cc_and_rs"
  }'

Example response

{
  "ok": true,
  "score": {
    "score": 88,
    "grade": "B",
    "label": "1 item to review with counsel"
  },
  "findings": [
    {
      "ruleId": "fl-solar-preemption",
      "title": "Solar-energy-device restriction (statewide preemption)",
      "category": "preemption",
      "severity": "flag",
      "statute": "Fla. Stat. § 163.04",
      "guidance": "Florida § 163.04 voids most prohibitions on solar-energy devices...",
      "excerpt": "...no solar panels or collectors shall be installed on any roof surface...",
      "corpusVerified": false,
      "matchQuality": "restrictive"
    }
  ],
  "total_findings": 1,
  "total_applicable_rules": 17,
  "state": "FL",
  "engine": "statute_scan_v1"
}

Bulk export

Stream a full dataset as CSV or JSON. Growth plan or higher.

GET/api/v1/export/{resource}

Stream a full dataset as CSV or JSON, one request against your monthly quota regardless of row count. `resource` is one of associations, vendors, statutes, building-safety, or report-card. Each resource has its own filter parameters (narrow the export the same way you would narrow the matching list endpoint) and a public-safe column allowlist. report-card streams the per-association public-record signal set behind the Explorer — FEMA NRI county risk, SIRS on file, HUD FHA status, elevator certificates, latest pool inspection, 24-month building permits, and IRS Form 990 revenue — keyed by organization id, name, state, and county.

Scope: per-resource: associations scope for associations, vendors.read for vendors, statutes or associations for statutes, risk for building-safety and report-cardGrowth plan or higher. Free and Builder keys receive 403 tier_not_allowed — the per-row endpoints above are included in every plan, but streaming a full dataset is a Growth+ capability. Per-tier row cap on a single export: Growth 50,000 · Scale 250,000 · Enterprise 1,000,000.

Path parameters

ParameterTypeDescription
resource*stringOne of: associations, vendors, statutes, building-safety, report-card.

Query parameters

ParameterTypeDescription
formatstring"csv" (default) or "json".
columnsstringComma-separated column names to narrow the output. An unknown column name 400s and lists the valid set for that resource.
statestringTwo-letter state code. Every resource supports this filter.
qstringFree-text filter, meaning varies by resource (name for associations/vendors, statute text for statutes).
countystringCounty filter. Supported by associations, vendors, and building-safety.
subtypestring"hoa", "condo", or "coop". Supported by associations and building-safety.
categorystringVendor category slug. Vendors only.
unit_min / unit_maxnumberUnit count range. Associations only.
year_min / year_maxnumberYear-built range. Associations only.
is_claimedboolean"true" or "false". Associations only.
mgmtstringManagement firm name filter. Associations only.
chapter / topicstringStatutes only, same meaning as on /v1/statutes/by-state.
sirs_on_file / elevator_delinquentboolean"true" or "false". Building-safety only.
milestone_status / pool_last_resultstringFree-text, matches the source county/agency's own vocabulary. Building-safety only.
has_sirs / has_elevator_certboolean"true" or "false". Report-card only.
fha_statusstringNormalized HUD decision: approved, rejected, withdrawn, expired, or other. Report-card only.
min_risk / max_risknumberFEMA NRI county risk score range. Report-card only.

Example request

curl "https://commonelements.com/api/v1/export/associations?state=FL&subtype=condo&unit_min=100&columns=name,state,unit_count,directory_slug" \
  -H "Authorization: Bearer ce_live_your_key_here" -o fl-condos.csv

Example response

name,state,unit_count,directory_slug
HARBOUR RIDGE CONDOMINIUM ASSOCIATION INC,FL,214,harbour-ridge-condominium-association
PELICAN BAY COMMUNITY ASSOCIATION INC,FL,742,pelican-bay-community-association
...
  • One export = one request against your monthly quota, whatever the row count, up to your plan's row cap.
  • The scope required depends on the resource, not the export capability itself — a key needs both the resource's read scope AND a Growth+ tier.
  • A source guard enforces the same public-record exclusions as every other v1 endpoint; a "columns" value that would expose an excluded field 400s rather than silently dropping it.
  • The first page is validated before the response starts streaming, so a bad filter or column name returns a clean JSON error. A failure mid-stream truncates the file — check row counts on large exports.

GET/api/v1/export/changes

Stream the change feed as CSV or JSON: one row per observed event, with the event date, the association it happened to (id, name, state, county), the event type, the changed field, and person-free old/new value summaries. The bulk form of /api/v1/changes for loading trigger events into a warehouse or CRM instead of polling pages.

Scope: changes or associationsGrowth plan or higher, same as every bulk export, with the same per-tier row caps (Growth 50,000 · Scale 250,000 · Enterprise 1,000,000). Your plan lookback window from the change feed still applies: the exported date range is clamped exactly as /api/v1/changes clamps it.

Query parameters

ParameterTypeDescription
formatstring"csv" (default) or "json".
columnsstringComma-separated column names to narrow the output. An unknown column name 400s and lists the valid set.
kindstringComma-separated change kinds, same vocabulary as /api/v1/changes. Omit for all kinds.
statestringComma-separated two-letter state codes.
countystringSingle county name, case-insensitive exact match.
subtypestringOne of "hoa", "condo", "coop".
sincestringEarliest observation date, YYYY-MM-DD. Clamped to your plan lookback window; an earlier date does not widen it.
untilstringLatest observation date, YYYY-MM-DD.
min_magnitudenumberMinimum change magnitude, 0 to 1.

Response fields

ParameterTypeDescription
iduuidStable id for this change event.
observed_ondateDate the change was observed in the source record.
organization_id / organization_nameuuid / stringThe association the change was observed on.
state / county / subtypestring | nullLocation and type of the association.
event_typestringOne of the 13 change kinds.
fieldstringThe part of the record that moved: board_roster, management_company, entity_status, entity_name, or license.
old_value / new_valuestring | nullPerson-free before/after summaries: firm names for management changes, statuses for registration changes, seat counts and canonical titles for board changes. Never an individual's name.
magnitudenumber | nullRelative size of the change, 0 to 1.

Example request

curl "https://commonelements.com/api/v1/export/changes?kind=management_company_changed,board_turnover&state=FL&since=2026-06-01" \
  -H "Authorization: Bearer ce_live_your_key_here" -o fl-changes.csv

Example response

Event ID,Event date,Organization ID,Organization name,State,County,Subtype,Event type,Changed field,Old value,New value,Magnitude
3f6b1c2e-...,2026-07-18,0b9d4f21-...,PELICAN BAY COMMUNITY ASSOCIATION INC,FL,Collier,hoa,management_company_changed,management_company,GULF COAST PROPERTY MANAGEMENT INC,SUNSTATE ASSOCIATION MANAGEMENT LLC,0.8
b1244a90-...,2026-07-02,c4d0a7e5-...,HARBOUR RIDGE CONDOMINIUM ASSOCIATION INC,FL,Broward,condo,board_turnover,board_roster,,"3 seats affected; titles: president, director; board size 5",0.6
...
  • No officer names, ever. The export reads the same person-stripped view as /api/v1/changes: officer changes come back as seat counts and canonical titles, and management changes as firm names. There is no parameter that widens this.
  • The lookback window is your plan's change-feed window, applied server-side. The row cap is the bulk-export cap for your tier, not the per-request /api/v1/changes cap.
  • One export = one request against your monthly quota, whatever the row count.

Association resources

Public record joined to one association: parcels, structures, permits, code enforcement, hazards, insurance, legal, financials, governance and documents. Same request shape for every one, so a client written against one works against all ten.

GET/api/v1/associations/{id}/parcels

County parcel records matched to the association: the physical footprint behind the corporate record. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: propertyRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/parcels?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "parcels.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/structures

Building footprints and recorded structural characteristics for the association's buildings. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: propertyRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/structures?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "structures.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/permits

Municipal building permits recorded against the association, with work type, value and date. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: permitsRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/permits?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "permits.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/violations

Code enforcement cases recorded against the association by the local jurisdiction. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: enforcementRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/violations?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "violations.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/hazards

Natural-hazard exposure for the association's location: recorded storm events and county-level risk. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: hazardRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/hazards?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "hazards.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/insurance

Insurance-side public record touching the association, including coverage and carrier filings where published. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: insuranceRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/insurance?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "insurance.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

Litigation and legal history recorded against the association, and the counsel of record where published. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: legalRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/legal?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "legal.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/financials

Financial public record for the association, including IRS Form 990 filings where it files one. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: financialsRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/financials?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "financials.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/governance

Governance record for the association: filings, officers over time, and registered agent history. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: governanceRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/governance?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "governance.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/associations/{id}/documents

Governing and recorded documents held for the association, with their source and recording date. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: documentsRow access is plan-gated per source; counts and coverage are returned at every plan so the size of what is behind the gate is visible.

Path parameters

ParameterTypeDescription
id*uuidAssociation id.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/associations/9a71c6b0-4e2f-41d8-8b09-5c3a2d17e604/documents?limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "documents.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

Cross-association collections

The same corpora queried across associations, where the buyer genuinely asks the question that way and an indexed filter exists to answer it.

GET/api/v1/storm-events

NOAA storm events by county and date. The hazard history behind an association's exposure, queryable across the whole corpus. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: hazardRow access is plan-gated per source; counts and coverage are returned at every plan.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).
statestringTwo-letter state code.
county_fipsstringFive-digit county FIPS code.
jurisdictionstringJurisdiction name as published by the source.

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/storm-events?state=FL&limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "storm-events.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • A cross-association collection requires at least one indexed filter. Without one the request is refused with a 400 naming the filters it accepts, rather than starting a sequential scan over millions of rows.
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/insurance/carriers

Carriers writing in the association market, by state, with their filings and market presence. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: insuranceRow access is plan-gated per source; counts and coverage are returned at every plan.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).
statestringTwo-letter state code.
county_fipsstringFive-digit county FIPS code.
jurisdictionstringJurisdiction name as published by the source.

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/insurance/carriers?state=FL&limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "insurance-carriers.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • A cross-association collection requires at least one indexed filter. Without one the request is refused with a 400 naming the filters it accepts, rather than starting a sequential scan over millions of rows.
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/insurance/rate-filings

Insurance rate filings by carrier and state: what carriers asked for, and when. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: insuranceRow access is plan-gated per source; counts and coverage are returned at every plan.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).
statestringTwo-letter state code.
county_fipsstringFive-digit county FIPS code.
jurisdictionstringJurisdiction name as published by the source.

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/insurance/rate-filings?state=FL&limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "rate-filings.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • A cross-association collection requires at least one indexed filter. Without one the request is refused with a 400 naming the filters it accepts, rather than starting a sequential scan over millions of rows.
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

Litigation involving community associations across the corpus, filterable by state and date. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: legalRow access is plan-gated per source; counts and coverage are returned at every plan.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).
statestringTwo-letter state code.
county_fipsstringFive-digit county FIPS code.
jurisdictionstringJurisdiction name as published by the source.

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/legal/cases?state=FL&limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "legal-cases.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • A cross-association collection requires at least one indexed filter. Without one the request is refused with a 400 naming the filters it accepts, rather than starting a sequential scan over millions of rows.
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

GET/api/v1/complaints

CFPB consumer complaints against mortgage servicers, banks and debt collectors, as market context for an association's counterparties. Not a record about the association. Live description, provenance and coverage caveat come from /api/v1/datasets.

Scope: financialsRow access is plan-gated per source; counts and coverage are returned at every plan.

Query parameters

ParameterTypeDescription
limitnumberRows per page, 1-500 (default 50). Your plan's row cap and the source's own page ceiling can only lower this; the response's `meta` block reports what was actually applied.
offsetnumberPagination offset, 0-100000 (default 0).
sourcestringNarrow the read to one physical source behind the resource, e.g. `parcels.fl`. Source keys are listed by /api/v1/datasets.
sincedateOnly records on or after this ISO date (YYYY-MM-DD).
untildateOnly records on or before this ISO date (YYYY-MM-DD).
statestringTwo-letter state code.
county_fipsstringFive-digit county FIPS code.
jurisdictionstringJurisdiction name as published by the source.

Response fields

ParameterTypeDescription
source_keystringWhich physical source the record came from. Provenance travels with every row.
record_idstringThe source's own identifier for the record.
occurred_ondate | nullWhen the recorded event happened, where the source publishes a date.
headlinestring | nullOne-line description of the record, from the source's own headline column.
payloadobject | nullThe record's fields, projected through the source's column allowlist. A column added to a backing table later cannot appear here unless it is added to that allowlist.
pagination.limitnumberRows requested after every server-side cap was applied.
pagination.offsetnumberOffset used.
pagination.totalnumberRows matching the query, before paging.
pagination.has_morebooleanWhether another page exists.

Example request

curl "https://commonelements.com/api/v1/complaints?state=FL&limit=5" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "source_key": "complaints.example",
      "record_id": "SRC-000123",
      "occurred_on": "2026-05-14",
      "headline": "Example record",
      "payload": { "field": "value" }
    }
  ],
  "pagination": { "limit": 5, "offset": 0, "total": 1, "has_more": false },
  "meta": { "coverage": "…", "sources_measured": 1 }
}
  • A cross-association collection requires at least one indexed filter. Without one the request is refused with a 400 naming the filters it accepts, rather than starting a sequential scan over millions of rows.
  • Read `meta.coverage` before treating an empty result as an absence. A resource can return zero rows because nothing happened, or because that jurisdiction is not matched yet, and those are different facts. The coverage caveat says which.

Bulk delivery

Asynchronous exports for datasets larger than one HTTP response. Request, poll, download a durable artifact with a manifest and a column dictionary beside it — or put it on a schedule and stop asking. Growth plan and above.

GET/api/v1/deliveries/datasets

The deliverable catalog and its column dictionary: what can be delivered, in what shape, and — resolved for the key on this request — what your plan allows. Every dataset is listed, each carrying `available_to_you` and the reason when it is false. Add `?dataset=<key>` for one dataset's full column dictionary.

Scope: associations

Query parameters

ParameterTypeDescription
datasetstringNarrow to one dataset and include its full column dictionary. Without it the response carries column counts rather than every column. Current keys: associations, vendors, statutes, building-safety, report-card, changes.

Response fields

ParameterTypeDescription
dataset_keystringStable key to pass as `dataset` when requesting a delivery.
labelstringDataset name, for display.
descriptionstringWhat the dataset contains.
required_scopesstring[]Scopes a key must carry to request it.
required_featurestringPlan feature the dataset sits behind.
supports_snapshotbooleanWhether the dataset can be delivered as a full snapshot.
available_to_youbooleanWhether the key on this request may request it, resolved at request time.

Example request

curl "https://commonelements.com/api/v1/deliveries/datasets" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "dataset_key": "associations",
      "label": "Example dataset",
      "description": "What this dataset contains.",
      "required_scopes": ["associations"],
      "required_feature": "bulk_export",
      "supports_snapshot": true,
      "available_to_you": true
    }
  ]
}
  • The dictionary returned here is the same document shipped inside each delivery, so a schema can be built against this endpoint before the first file arrives, and diffed afterwards.

POST/api/v1/deliveries

Request an asynchronous bulk delivery. Returns immediately with a delivery id; the export runs server-side with keyset pagination and produces a durable artifact with a manifest and a column dictionary beside it. Use this instead of /v1/export when the dataset is larger than one HTTP response can carry.

Scope: associationsBulk delivery is a Growth plan capability, the same line /v1/export draws. Row cap, lookback window, monthly delivery quota and concurrency are all resolved server-side from the key; none of them is a parameter.

Request body

ParameterTypeDescription
dataset*stringDataset key from /v1/deliveries/datasets. Current keys: associations, vendors, statutes, building-safety, report-card, changes.
formatstring`csv` (default) or `jsonl`.
modestring`snapshot` for the dataset as it stands, or `changes` for what moved inside the window your plan allows.
filtersobjectDataset-specific filters, in the same vocabulary as the matching read endpoint.
columnsstring[]Subset of the dataset's column dictionary. Narrowing only; it can never add a column the dictionary does not already publish.
labelstringYour own label for the run, echoed back on status and in the manifest.

Response fields

ParameterTypeDescription
iduuidDelivery id. Poll /v1/deliveries/{id} with it.
statusstringLifecycle state: queued, running, succeeded, failed, or cancelled.
row_capnumberRow ceiling applied to this run, from your plan.
max_lookback_daysnumber | nullLookback window applied in `changes` mode, from your plan.
requested_attimestampWhen the delivery was accepted.

Example request

curl -X POST "https://commonelements.com/api/v1/deliveries" \
  -H "Authorization: Bearer ce_live_your_key_here" \
  -H "Content-Type: application/json" \
  -d '{ "dataset": "associations", "format": "csv", "mode": "snapshot" }'

Example response

{
  "ok": true,
  "data": {
    "id": "1f0a9c4e-2b57-4c1d-9f3a-7b2e5d61c8a4",
    "status": "queued",
    "dataset": "associations",
    "format": "csv",
    "mode": "snapshot",
    "row_cap": 250000,
    "max_lookback_days": 365,
    "requested_at": "2026-08-16T12:00:00.000Z"
  }
}
  • One delivery counts once against your monthly request quota and once against your plan's separate monthly delivery quota. Polling its status costs a request like any other call.
  • A refusal names its reason: `tier_not_allowed` when the plan does not include delivery, `quota_exceeded` when the monthly delivery quota is spent, and 429 again when too many deliveries are already running.

GET/api/v1/deliveries

List this organization's deliveries, most recent first, with their status, row and byte counts, checksum, and download links while they are live.

Scope: associations

Response fields

ParameterTypeDescription
iduuidDelivery id.
statusstringqueued, running, succeeded, failed, or cancelled.
rows_writtennumber | nullRows written once the run has produced output.
truncatedbooleanWhether the run stopped at the plan's row cap.
checksumstring | nullChecksum of the artifact, for verifying a download.
download_expires_attimestamp | nullWhen the download link stops working.

Example request

curl "https://commonelements.com/api/v1/deliveries" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "1f0a9c4e-2b57-4c1d-9f3a-7b2e5d61c8a4",
      "dataset": "associations",
      "status": "succeeded",
      "rows_written": 48210,
      "truncated": false,
      "checksum": "sha256:…",
      "download_expires_at": "2026-08-23T12:00:00.000Z"
    }
  ]
}

GET/api/v1/deliveries/{id}

Status of one delivery: progress while it runs, download links once it succeeds, and — when it fails — a machine-readable `error.code` with a message written for the person who has to decide what to do next.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidDelivery id returned when the delivery was requested.

Response fields

ParameterTypeDescription
statusstringqueued, running, succeeded, failed, or cancelled.
rows_writtennumber | nullRows written so far, or in total once finished.
part_countnumber | nullHow many parts the artifact was split into.
download_urlstring | nullSigned download link, present only while the delivery is downloadable.
error_codestring | nullMachine-readable failure reason. Switch on this, not on the message.

Example request

curl "https://commonelements.com/api/v1/deliveries/1f0a9c4e-2b57-4c1d-9f3a-7b2e5d61c8a4" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "id": "1f0a9c4e-2b57-4c1d-9f3a-7b2e5d61c8a4",
    "status": "succeeded",
    "rows_written": 48210,
    "part_count": 1,
    "download_url": "https://commonelements.com/api/v1/deliveries/…",
    "error_code": null
  }
}

DELETE/api/v1/deliveries/{id}

Cancel a queued or running delivery. Authorization is enforced in SQL from the key's organization rather than asserted by the route, so a delivery belonging to another organization cannot be cancelled even by a caller that skips the check.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidDelivery id.

Example request

curl -X DELETE "https://commonelements.com/api/v1/deliveries/1f0a9c4e-2b57-4c1d-9f3a-7b2e5d61c8a4" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": { "id": "1f0a9c4e-2b57-4c1d-9f3a-7b2e5d61c8a4", "status": "cancelled" }
}

GET/api/v1/deliveries/{id}/download

Stream a delivered artifact, or one of its sidecars. Two doors, one gate: the artifact's own capability token for a pipeline that should not hold an API key, or the organization's API key for anything that already does. Either way the same database function re-checks that the run succeeded, that its retention window is still open, and that the presenter is entitled.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidDelivery id.

Query parameters

ParameterTypeDescription
tokenstringThe artifact's capability token, as returned on the delivery's status. Use this when the consumer should not hold an API key. A token download does not consume your monthly request quota.
partstring`manifest` for the run's manifest or `dictionary` for its column dictionary, fetched through the same authorization. Omit for the data itself.

Example request

curl -L "https://commonelements.com/api/v1/deliveries/1f0a9c4e-2b57-4c1d-9f3a-7b2e5d61c8a4/download?token=…" \
  -o delivery.csv

Example response

# Streams the artifact. Sidecars return JSON:
{
  "dataset": "associations",
  "rows": 48210,
  "checksum": "sha256:…",
  "generated_at": "2026-08-16T12:04:11.000Z"
}
  • The response is the file itself, not a redirect to storage. A signed storage URL would keep working after the artifact expired, after the subscription lapsed and after the key was revoked, with no server left in the path to reconsider.
  • Fetch `?part=dictionary` to build a schema before parsing, and `?part=manifest` to verify the row count and checksum after downloading.

POST/api/v1/deliveries/schedules

Create a recurring delivery: this dataset, these filters, this format, on this cadence, produced whether or not anyone is awake. In `changes` mode each run covers only what was observed after the previous SUCCESSFUL delivery, so a failed run is re-covered on the next one rather than silently skipped.

Scope: associationsGrowth plan and above, the same gate as one-off delivery.

Request body

ParameterTypeDescription
dataset*stringDataset key. Fixed at creation, because it is what entitlement was checked against. Current keys: associations, vendors, statutes, building-safety, report-card, changes.
cadence*string`daily`, `weekly`, or `monthly`.
formatstring`csv` (default) or `jsonl`. Fixed at creation.
modestring`snapshot` or `changes`. Fixed at creation.
filtersobjectDataset-specific filters. Editable later with PATCH.
columnsstring[]Subset of the dataset's column dictionary. Editable later.
targetobjectWhere to deliver. An unimplemented target type is refused with 501 `not_implemented` rather than accepted and silently dropped.

Response fields

ParameterTypeDescription
iduuidSchedule id.
cadencestringHow often it runs.
next_run_attimestamp | nullWhen the next run is due.
paused_attimestamp | nullSet while the schedule is paused.

Example request

curl -X POST "https://commonelements.com/api/v1/deliveries/schedules" \
  -H "Authorization: Bearer ce_live_your_key_here" \
  -H "Content-Type: application/json" \
  -d '{ "dataset": "associations", "cadence": "weekly", "mode": "changes" }'

Example response

{
  "ok": true,
  "data": {
    "id": "6c2b71de-9a44-4d8e-8f31-0c5a9e77b210",
    "dataset": "associations",
    "cadence": "weekly",
    "mode": "changes",
    "next_run_at": "2026-08-23T06:00:00.000Z",
    "paused_at": null
  }
}
  • Dataset, format and mode are fixed at creation. Filters, columns, cadence and pause/resume are editable through PATCH on the schedule.

GET/api/v1/deliveries/schedules

List this organization's recurring deliveries, with their cadence, next run, watermark and paused state.

Scope: associations

Response fields

ParameterTypeDescription
iduuidSchedule id.
datasetstringDataset the schedule delivers.
cadencestringdaily, weekly, or monthly.
next_run_attimestamp | nullWhen the next run is due.
last_success_attimestamp | nullWhen a file last landed. In `changes` mode this is the watermark the next run reads from.

Example request

curl "https://commonelements.com/api/v1/deliveries/schedules" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": [
    {
      "id": "6c2b71de-9a44-4d8e-8f31-0c5a9e77b210",
      "dataset": "associations",
      "cadence": "weekly",
      "next_run_at": "2026-08-23T06:00:00.000Z",
      "last_success_at": "2026-08-16T06:00:12.000Z"
    }
  ]
}

GET/api/v1/deliveries/schedules/{id}

One recurring delivery and its recent runs.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidSchedule id.

Response fields

ParameterTypeDescription
iduuidSchedule id.
cadencestringdaily, weekly, or monthly.
next_run_attimestamp | nullWhen the next run is due. Null while paused.
runsarrayThe schedule's recent runs, each in the same shape as a one-off delivery.

Example request

curl "https://commonelements.com/api/v1/deliveries/schedules/6c2b71de-9a44-4d8e-8f31-0c5a9e77b210" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": {
    "id": "6c2b71de-9a44-4d8e-8f31-0c5a9e77b210",
    "cadence": "weekly",
    "next_run_at": "2026-08-23T06:00:00.000Z",
    "runs": []
  }
}

PATCH/api/v1/deliveries/schedules/{id}

Pause, resume, retime or refilter a recurring delivery. Dataset, format and mode are deliberately not editable: they are what entitlement was checked against at creation, and letting a PATCH swap the dataset would turn one authorized decision into a standing permission for any other. Change them by creating a new schedule.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidSchedule id.

Request body

ParameterTypeDescription
cadencestring`daily`, `weekly`, or `monthly`.
filtersobjectReplacement filters, re-validated against the dataset.
columnsstring[]Replacement column subset, re-validated against the dictionary.
pausedbooleanPause or resume. Resuming recomputes the next run from now, so a schedule paused for a month does not wake and fire a backlog.

Example request

curl -X PATCH "https://commonelements.com/api/v1/deliveries/schedules/6c2b71de-9a44-4d8e-8f31-0c5a9e77b210" \
  -H "Authorization: Bearer ce_live_your_key_here" \
  -H "Content-Type: application/json" \
  -d '{ "paused": true }'

Example response

{
  "ok": true,
  "data": {
    "id": "6c2b71de-9a44-4d8e-8f31-0c5a9e77b210",
    "paused_at": "2026-08-16T12:00:00.000Z",
    "next_run_at": null
  }
}
  • For a `changes` schedule the watermark is untouched by a pause, so the first run after resuming covers everything that happened while it slept — clamped, as always, by your plan's lookback window.

DELETE/api/v1/deliveries/schedules/{id}

Remove a recurring delivery. Artifacts already produced are unaffected and remain downloadable until their retention window closes.

Scope: associations

Path parameters

ParameterTypeDescription
id*uuidSchedule id.

Example request

curl -X DELETE "https://commonelements.com/api/v1/deliveries/schedules/6c2b71de-9a44-4d8e-8f31-0c5a9e77b210" \
  -H "Authorization: Bearer ce_live_your_key_here"

Example response

{
  "ok": true,
  "data": { "id": "6c2b71de-9a44-4d8e-8f31-0c5a9e77b210", "deleted": true }
}

Error codes

All errors return a flat JSON envelope with a machine-readable error string and a human-readable message. Switch on the code; the wording of the message can change, the code will not. Endpoints in the meta namespace add docs_url and next_steps alongside them.

{
  "ok": false,
  "error": "quota_exceeded",
  "message": "Monthly request quota exceeded.",
  "docs_url": "https://commonelements.com/developers/docs#errors",
  "next_steps": "Call /api/v1/meta/usage to see the reset date and how the quota was spent, then either wait for the reset at the start of the next calendar month or upgrade the plan. /api/v1/meta/usage does not itself consume quota."
}
StatusCodeWhat happened, and what to do
400validation_errorInvalid request. A query parameter or body field is missing, malformed, or outside its allowed range. The message names the first parameter that failed.Fix the named parameter and re-send. Every parameter and its accepted values are in the OpenAPI document at /api/v1/openapi; retrying an unchanged request will fail the same way.
401invalid_api_keyKey missing, malformed, or revoked. No Authorization header, a header that is not `Bearer <key>`, or a key that does not resolve to an active record.Send `Authorization: Bearer ce_live_...`. If the header is correct, the key has been revoked or expired — mint a new one at /settings/api-keys. Keys are shown once at creation and stored only as a hash, so a lost key cannot be recovered.
403scope_not_allowedKey lacks the required scope. The key is valid but was created without the scope this endpoint requires. Scopes are set at key creation and are not widened at request time.Create a key carrying the scope named in the message, or use the `all` scope. Each endpoint's required scope is on its OpenAPI operation as `x-ce-scope`.
403tier_not_allowedPlan does not include this endpoint. The key is valid and correctly scoped, but the endpoint is gated to a higher plan. Bulk export is the current case: it is Growth and above.Check your plan and the endpoint's minimum at /api/v1/meta/usage, then upgrade from /settings/api-keys. Per-row endpoints remain available on your current plan.
404not_foundNo such record. The identifier is well-formed but matches nothing this key may see. Records excluded from the public directory read as absent rather than forbidden, deliberately — a 403 would confirm the row exists.Confirm the identifier against a list or search endpoint before fetching it by id. A record that appears in the product but not here is outside the licensed dataset.
429quota_exceededMonthly request quota used up. The key has spent every request included in the current calendar month. There is no overage charge and no automatic top-up.Call /api/v1/meta/usage to see the reset date and how the quota was spent, then either wait for the reset at the start of the next calendar month or upgrade the plan. /api/v1/meta/usage does not itself consume quota.
501not_implementedOption accepted by the schema, not yet built. The request named a documented option that is not live yet — currently, a delivery target type that has no implementation behind it. Refused rather than accepted, because a schedule that silently drops its files is worse than one that never starts.Use one of the target types the catalog reports as implemented, or contact support if you need the one you asked for. This is not a transient failure; retrying will return the same 501.
504search_timeoutSimilarity search exceeded the database time limit. The trigram similarity search behind /associations/match ran past the database's statement timeout. The request itself was well-formed; the search simply took too long under current load.Retry after a few seconds; the Retry-After header says how long. Narrowing with the county parameter reduces the search space. If a specific query times out repeatedly, report it: that is a performance bug on our side, not an error in your request.
500internal_errorUnexpected server error. The request was accepted and failed on our side.Retry with exponential backoff (1s, 2s, 4s, up to about 30s). If it persists past a few minutes, check /api/v1/meta/status and contact support with the time of the request.
503service_unavailableDependency unavailable. A backing dependency is unreachable. Returned by the status endpoint when its own database probe fails, so uptime monitors see a non-200.Treat as transient and retry with backoff. /api/v1/meta/status reports which dependency is failing.

MCP integration

Common Elements runs a hosted MCP (Model Context Protocol) server that lets AI assistants call this API as tools, without writing HTTP client code. It is live today at one endpoint:

https://commonelements.com/api/mcp

Claude and ChatGPT: add that URL as a custom connector and sign in when prompted. The OAuth flow issues the key for you, so there is nothing to copy.

Clients that read a JSON config (Cursor and similar): point at the same URL and send your API key as a bearer header.

{
  "mcpServers": {
    "common-elements": {
      "url": "https://commonelements.com/api/mcp",
      "headers": {
        "Authorization": "Bearer ce_live_your_key_here"
      }
    }
  }
}

Once connected, your agent can call tools like search_associations and scan_compliance conversationally, with structured responses automatically parsed. An npm connector package is planned but not published yet; the hosted endpoint is the supported path today. MCP server documentation and changelog live at commonelements.com/developers/mcp.

Command-line tool

The ce CLI wraps this API for terminal and scripting use, with the same key, scopes, and quota as every other surface. Its npm package is not published yet, so there is no install command to run today; this section will carry one when it ships. Everything the CLI wraps is plain REST, so the same jobs run from curl now:

export CE_API_KEY=ce_live_your_key_here

curl "https://commonelements.com/api/v1/associations/lookup?state=FL&q=sunset&limit=5" \
  -H "Authorization: Bearer $CE_API_KEY"

curl "https://commonelements.com/api/v1/statutes/search?q=reserve%20study&state=FL" \
  -H "Authorization: Bearer $CE_API_KEY"

curl "https://commonelements.com/api/v1/export/associations?state=FL" \
  -H "Authorization: Bearer $CE_API_KEY" -o fl-associations.csv

Full command and option reference lives at commonelements.com/developers/cli.

FAQ

What happens when I get a 429 response?
A 429 means your monthly request quota is used up. The body carries a JSON error envelope with "quota_exceeded" as the error code. Wait for the reset at the start of the next calendar month or upgrade your tier from your API keys settings; there is no automatic overage charge.
How do API keys map to scopes?
Every key carries a list of scopes set when it is created, one per data domain: associations, changes, compliance, risk, licenses, professionals, vendors, valuations, and statutes. A request is only authorized if the key carries the scope the endpoint requires; a key without the "vendors" scope gets a 403 from vendor endpoints even with a valid, unexpired key. The change feed accepts either "changes" or "associations".
What does "read-only" vs "full-access" mean for a scope?
Every scope on a Developer API key is read and analysis access to the public dataset: no Developer API key can write to your account or to anyone else, regardless of scope. The "all" scope is full access, unlocking every endpoint across every domain. Narrower scopes like "associations" or "compliance" unlock only endpoints in that one domain, so a key you hand to a teammate or embed in a single-purpose integration can be scoped down to just what it needs.
Where can I see my usage?
Your API keys settings page shows live usage for every key you hold, as requests used against requests included for the current calendar month. It is the fastest way to check how close a key is to its limit before you hit a 429.

Ready to integrate?

Generate a free API key from your account settings and start building.

Get your API key