The Relm Report.

Developer platform

The Relm API

A REST API for commercial real estate: search any US property, run multi-agent Deep Search, build 10-year pro-formas, and read your portfolios — 27 endpoints, every finding traceable to a source.

https://api.relm.ai/v1

Base URL & authentication

All requests go to https://api.relm.ai/v1 over HTTPS and authenticate with an API key you create on the API keys page. Pass it as a bearer token:

Authorization: Bearer relm_sk_...

Each key has a scope: read (all GET endpoints) or full (adds POST/PUT/DELETE — triggering runs and edits). Keys only authenticate for organizations on a paid plan.

Quickstart

Verify your key by fetching your account:

curl https://api.relm.ai/v1/me \
  -H "Authorization: Bearer relm_sk_..."

Search a property, then start a Deep Search run and poll it — pick your language (the choice applies to every example on this page):

# 1. Search
curl "https://api.relm.ai/v1/search?q=40+Main+St" \
  -H "Authorization: Bearer relm_sk_..."

# 2. Start Deep Search (returns { run_id })
curl -X POST https://api.relm.ai/v1/deep-research \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{"portfolio_id":"...","property_id":"..."}'

# 3. Poll status
curl https://api.relm.ai/v1/deep-research/RUN_ID \
  -H "Authorization: Bearer relm_sk_..."

API reference

27 endpoints, grouped below. Full request/response schemas are in the /v1/openapi.json spec. List endpoints accept limit / offset and return a total. Path placeholders like PROP_ID are shown in UPPERCASE in the examples.

Account

Identify the key and read your organization’s wallet.

GET/v1/me

Returns the user, organization, role, and scope the API key resolves to. Use it to verify a key works and which org it acts in.

curl https://api.relm.ai/v1/me \
  -H "Authorization: Bearer relm_sk_..."
GET/v1/credits

The org’s credit balance, plan, and whether new deep-search / pro-forma runs can start right now.

curl https://api.relm.ai/v1/credits \
  -H "Authorization: Bearer relm_sk_..."

Search & preview

Find properties and pull instant preview data by address.

GET/v1/search

Search the org’s properties, portfolios, and uploaded documents. Returns matches with the portfolio_id / property_id you can pass to other endpoints.

Parameters

  • q query · required Search text — an address fragment, portfolio name, or document keywords.
curl "https://api.relm.ai/v1/search?q=40+Main+St" \
  -H "Authorization: Bearer relm_sk_..."
POST/v1/properties/preview

Fetch (or serve cached) preview data — basic info, taxes, area stats — for a US address. Synchronous; 10–30s for a cold address. An address must be previewed before it can be added to a portfolio.

Parameters

  • address body · required Full street address.
  • force_refresh body Bypass the 30-day cache and re-fetch (default false).
curl -X POST https://api.relm.ai/v1/properties/preview \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{"address":"40 Main St, Brooklyn, NY 11201"}'
GET/v1/properties/preview/progress

Real-time progress steps for an in-flight preview. Poll it alongside the preview call; returns an empty list when nothing is running for the address.

Parameters

  • address query · required The same address string passed to the preview call.
curl "https://api.relm.ai/v1/properties/preview/progress?address=40+Main+St,+Brooklyn,+NY+11201" \
  -H "Authorization: Bearer relm_sk_..."

Portfolios

Group properties into portfolios and manage membership.

GET/v1/portfolios

Every portfolio in the org, newest first. Paginated; the response includes count, total, limit, and offset.

Parameters

  • limit query Max to return (1–200, default 50).
  • offset query Rows to skip (default 0).
curl "https://api.relm.ai/v1/portfolios?limit=50&offset=0" \
  -H "Authorization: Bearer relm_sk_..."
POST/v1/portfolios

Creates a new portfolio in the org and returns it (201).

Parameters

  • name body · required Display name (1–200 chars).
curl -X POST https://api.relm.ai/v1/portfolios \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{"name":"Brooklyn Multifamily 2026"}'
GET/v1/portfolios/{portfolio_id}

One portfolio’s metadata (name, property count, created date). 404 for unknown or cross-org ids.

Parameters

  • portfolio_id path · required Portfolio id.
curl https://api.relm.ai/v1/portfolios/PORTFOLIO_ID \
  -H "Authorization: Bearer relm_sk_..."
GET/v1/portfolios/{portfolio_id}/properties

Summary rows (id, address, section-completion) for the properties in one portfolio. Paginated.

Parameters

  • portfolio_id path · required Portfolio id.
  • limit query Max to return (1–200, default 50).
  • offset query Rows to skip (default 0).
curl "https://api.relm.ai/v1/portfolios/PORTFOLIO_ID/properties?limit=50&offset=0" \
  -H "Authorization: Bearer relm_sk_..."
POST/v1/portfolios/{portfolio_id}/properties

Adds a previously-previewed address to the portfolio and returns the new property_id. 404 if the address was never previewed.

Parameters

  • portfolio_id path · required Target portfolio id.
  • address body · required The exact address that was previewed.
curl -X POST https://api.relm.ai/v1/portfolios/PORTFOLIO_ID/properties \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{"address":"40 Main St, Brooklyn, NY 11201"}'
GET/v1/portfolios/{portfolio_id}/properties/{prop_id}

The full, normalized property data document as it sits in that portfolio.

Parameters

  • portfolio_id path · required Portfolio id.
  • prop_id path · required Property id.
curl https://api.relm.ai/v1/portfolios/PORTFOLIO_ID/properties/PROP_ID \
  -H "Authorization: Bearer relm_sk_..."
DELETE/v1/portfolios/{portfolio_id}/properties/{prop_id}

Removes a property from a portfolio (org-scoped). 404 if it isn’t in that portfolio.

Parameters

  • portfolio_id path · required Portfolio id.
  • prop_id path · required Property id.
curl -X DELETE https://api.relm.ai/v1/portfolios/PORTFOLIO_ID/properties/PROP_ID \
  -H "Authorization: Bearer relm_sk_..."

Properties

Read properties org-wide or by id, without walking portfolios.

GET/v1/properties

Every property in the org (one row per portfolio membership), newest first. Paginated; optionally scoped to a portfolio.

Parameters

  • portfolio_id query Restrict to a single portfolio.
  • limit query Max to return (1–200, default 50).
  • offset query Rows to skip (default 0).
curl "https://api.relm.ai/v1/properties?limit=50&offset=0" \
  -H "Authorization: Bearer relm_sk_..."
GET/v1/properties/{prop_id}

The full property data document by property id alone (any portfolio in the org). 404 if not in your org.

Parameters

  • prop_id path · required Property id.
curl https://api.relm.ai/v1/properties/PROP_ID \
  -H "Authorization: Bearer relm_sk_..."

Deep research

Kick off multi-agent research and follow it to completion.

POST/v1/deep-research

Starts (or queues) a deep-research run. A full run (services omitted or ["all"]) researches basics, units, comps, taxes, POIs, area stats, and a summary — and consumes one credit. Returns a run_id (202); 402 if out of credits.

Parameters

  • portfolio_id body · required Portfolio containing the property.
  • property_id body · required Property to research.
  • services body Sections to run; omit for a full run. e.g. ["comps","taxes"].
  • auto_run_financials body Start the pro-forma automatically on completion (default false).
curl -X POST https://api.relm.ai/v1/deep-research \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{"portfolio_id":"PORTFOLIO_ID","property_id":"PROP_ID"}'
GET/v1/deep-research/{run_id}

Per-section statuses plus a rollup: processing | complete | error | stopped. Works for deep-search and pro-forma runs. Status expires ~24h after completion.

Parameters

  • run_id path · required run_id returned when the run started.
curl https://api.relm.ai/v1/deep-research/RUN_ID \
  -H "Authorization: Bearer relm_sk_..."
GET/v1/runs/{run_id}/steps

The run’s thinking steps (the live activity trace). Pass the returned next_cursor back to receive only new steps. Steps expire ~1h after the run ends.

Parameters

  • run_id path · required Run to inspect.
  • cursor query Opaque cursor from a previous response.
curl "https://api.relm.ai/v1/runs/RUN_ID/steps" \
  -H "Authorization: Bearer relm_sk_..."
GET/v1/runs/{run_id}/steps/stream

The same steps as a Server-Sent Events stream. Emits a final run_complete event when the run reaches a terminal state; capped per key. Reconnect or fall back to polling on idle/timeout.

Parameters

  • run_id path · required Run to stream.
curl -N https://api.relm.ai/v1/runs/RUN_ID/steps/stream \
  -H "Authorization: Bearer relm_sk_..."

Pro forma

Build, read, edit, and export the 10-year financial model.

POST/v1/properties/{prop_id}/proforma

Starts the financial pro-forma run (~18 line-item agents; 10–30 min). Returns a run_id (202); 402 without an active subscription. Deep search should have completed first.

Parameters

  • prop_id path · required Property to underwrite.
  • portfolio_id body · required Portfolio containing the property.
curl -X POST https://api.relm.ai/v1/properties/PROP_ID/proforma \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{"portfolio_id":"PORTFOLIO_ID"}'
GET/v1/properties/{prop_id}/proforma

The transformed pro-forma: Year-1 summary, 10-year projections, and line items. Each line item carries key / label / category / year1_value / per_unit / per_sqft / ten_year_values.

Parameters

  • prop_id path · required Property id.
curl https://api.relm.ai/v1/properties/PROP_ID/proforma \
  -H "Authorization: Bearer relm_sk_..."
GET/v1/properties/{prop_id}/proforma/export

Download the pro-forma as an Excel model (formulas), a formatted PDF report, or raw JSON.

Parameters

  • prop_id path · required Property id.
  • format query xlsx (default) | pdf | json.
curl "https://api.relm.ai/v1/properties/PROP_ID/proforma/export?format=xlsx" \
  -H "Authorization: Bearer relm_sk_..." \
  -o proforma.xlsx
PUT/v1/properties/{prop_id}/financials

Save an edited pro-forma: the full line-item array (same shape GET .../proforma returns) plus optional financing assumptions. Edits are recorded as source="api". Expenses/losses are stored as negative numbers.

Parameters

  • prop_id path · required Property id.
  • portfolio_id body · required Portfolio containing the property.
  • line_items body · required Full FinancialLineItem array.
  • financing body purchase_price, down_payment_pct, interest_rate, loan_term_years, closing_costs_pct.
curl -X PUT https://api.relm.ai/v1/properties/PROP_ID/financials \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{"portfolio_id":"PORTFOLIO_ID","line_items":[{"key":"gross_potential_income","year1_value":250000}]}'

Sections

Read (and, where allowed, write) one section of a property.

GET/v1/properties/{prop_id}/sections/{section}

One data section of a property. Readable: basic_info, taxes, comps, units, summary, area_stats, pois, market, neighborhood_news. (Financials live under the /proforma endpoints.)

Parameters

  • prop_id path · required Property id.
  • section path · required Section name (see list above).
curl https://api.relm.ai/v1/properties/PROP_ID/sections/taxes \
  -H "Authorization: Bearer relm_sk_..."
PUT/v1/properties/{prop_id}/sections/{section}

Save one section (schema-validated). Writable sections: basic_info, taxes, comps, units, summary, area_stats, pois. 409 if another editor holds the lock; 422 on schema failure. (market and neighborhood_news are read-only.)

Parameters

  • prop_id path · required Property id.
  • section path · required Writable section name.
  • (body) body · required The section payload (shape matches what GET returns).
curl -X PUT https://api.relm.ai/v1/properties/PROP_ID/sections/summary \
  -H "Authorization: Bearer relm_sk_..." \
  -H "Content-Type: application/json" \
  -d '{ "...section fields..." }'

Documents

Attach deal documents and make them searchable.

POST/v1/properties/{prop_id}/documents

Upload one or more files (multipart/form-data field "files"). Allowed: pdf, csv, tsv, xlsx, xls, html, json, txt, md, doc, docx, and common images. 50MB per file; per-file failures are reported without failing the batch.

Parameters

  • prop_id path · required Property to attach to.
  • files body · required Multipart form field; repeat for multiple files.
curl -X POST https://api.relm.ai/v1/properties/PROP_ID/documents \
  -H "Authorization: Bearer relm_sk_..." \
  -F "files=@rent_roll.pdf"
POST/v1/properties/{prop_id}/documents/{document_id}/index

Start vector indexing so a document becomes searchable / citable in chat and deep research (async, 202). Returns an upload_id to poll.

Parameters

  • prop_id path · required Property id.
  • document_id path · required Document id from the upload response.
curl -X POST https://api.relm.ai/v1/properties/PROP_ID/documents/DOCUMENT_ID/index \
  -H "Authorization: Bearer relm_sk_..."
GET/v1/properties/{prop_id}/documents/indexing-status/{upload_id}

Status of an indexing job: pending, in_progress, failed, or complete.

Parameters

  • prop_id path · required Property id.
  • upload_id path · required upload_id from the index call.
curl https://api.relm.ai/v1/properties/PROP_ID/documents/indexing-status/UPLOAD_ID \
  -H "Authorization: Bearer relm_sk_..."

Errors & rate limits

Errors use a consistent envelope (5xx responses stay generic):

{ "detail": { "error": "invalid_scope", "message": "..." } }

Common statuses: 401 (bad/expired key), 402 (out of credits / no subscription), 403 (read key on a write), 404 (not found / not in your org), 422 (validation). Requests are rate limited per key and per org; over the limit you get 429 with a Retry-After header.

MCP server

Prefer to drive the API from an AI agent? Connect the Relm MCP server (https://api.relm.ai/mcp/) to Cursor, Claude, or any MCP client. The MCP guide has the setup config and a description of every tool.

Keys are scoped and revocable, calls are rate limited and isolated to your organization, and every research finding is traceable to its source. Your data is never used to train models.

Build on Relm

Start a subscription, mint an API key, and make your first request in minutes.

Get an API key