Form4API REST API Reference — SEC Form 4, 144 & 13F-HR Data

Get a free API key

500 requests/day, no credit card — your key shows instantly in the dashboard.

Get started free →
Try it: live data, no key needed
GET /v1/transactions?ticker=AAPL&per_page=10
Reproduce with curl
curl "https://api.form4api.com/v1/transactions?ticker=AAPL&per_page=10" \
  -H "X-Api-Key: YOUR_API_KEY"

Get your own free API key → 500 requests/day, no credit card.

// introduction

Introduction

Form4API provides real-time SEC Form 4 insider trading data via a simple REST API. Every time a corporate insider — director, officer, or 10% owner — buys or sells shares, they must file Form 4 with the SEC within two business days. Form4API parses those filings continuously and surfaces the data through clean, developer-friendly endpoints. See the insider trading API overview for a high-level walkthrough of the endpoints and pricing.

Base URL

https://api.form4api.com

A machine-readable OpenAPI 3.x specification is published at api.form4api.com/openapi/v1.json. Use it with Postman, openapi-generator-cli, or any OpenAPI-aware tool to scaffold a client in your language of choice. The spec stays in sync with the live API automatically.

Get started: Create a free account to receive your API key. No credit card required for the Free plan.

// quickstart

Quickstart

Get your first API response in under two minutes.

1

Get your API key

Sign up for a free account — no credit card required. Your API key is shown immediately in the dashboard.

2

Install an SDK (optional)

Official SDKs for JavaScript/TypeScript and Python handle auth, retries, pagination, and type safety for you. Skip this step if you prefer raw HTTP.

npm install form4api
3

Make your first request

Fetch the five most recent insider transactions across all companies. Replace YOUR_API_KEY with your actual key.

curl "https://api.form4api.com/v1/transactions?per_page=5" \
  -H "X-Api-Key: YOUR_API_KEY"

Don't want to set up a key first? Run a live request in the playground above ↑ — real data, no key needed.

4

Filter by ticker and transaction type

Narrow results to purchases (P) at Apple.

curl "https://api.form4api.com/v1/transactions?ticker=AAPL&code=P&per_page=10" \
  -H "X-Api-Key: YOUR_API_KEY"
5

Paginate through large result sets

Responses are arrays. When a page returns fewer records than per_page, you've reached the end. The maximum page size is 100 for /v1/transactions and 500 for other endpoints. Both SDKs expose a paginate() method that handles this loop automatically.

# Page 1
curl "https://api.form4api.com/v1/transactions?ticker=NVDA&per_page=100&page=1" \
  -H "X-Api-Key: YOUR_API_KEY"

# Page 2 (repeat until response array is shorter than per_page)
curl "https://api.form4api.com/v1/transactions?ticker=NVDA&per_page=100&page=2" \
  -H "X-Api-Key: YOUR_API_KEY"
6

Use the async client (Python)

AsyncForm4ApiClient mirrors every method of the sync client — just await each call. Use it with FastAPI, Django Async, or any asyncio-based framework.

import asyncio
from form4api import AsyncForm4ApiClient

async def main():
    async with AsyncForm4ApiClient("YOUR_API_KEY") as client:
        txns = await client.transactions.list(ticker="AAPL", per_page=5)
        for t in txns:
            print(t.insider_name, t.shares_amount, "@", t.price_per_share)

asyncio.run(main())

// authentication

Authentication

All API requests must include your API key in the X-Api-Key request header. You can find your key in the dashboard.

Keep your API key secret — do not expose it in client-side JavaScript or commit it to source control. Use environment variables or a secrets manager. Form4API is built by Theodor Nielsen on 100% public SEC EDGAR data.

curl "https://api.form4api.com/v1/transactions" \
  -H "X-Api-Key: YOUR_API_KEY"

401 response — invalid or missing key

{
  "error": {
    "code": "MISSING_API_KEY",
    "message": "Missing or invalid X-Api-Key header.",
    "requestId": "req_abc123"
  }
}

Which SDKs are available?

Official client libraries wrap authentication and request handling for you.

Pythonpip install form4api
JavaScriptnpm install form4api

// rate-limits

Rate Limits

Each API key has two independent limits: a per-minute burst and a daily cap. Both return 429 Too Many Requests with a Retry-After header (seconds) when exceeded.

Every response also carries the per-minute window state so you can throttle proactively instead of waiting for a 429: X-RateLimit-Limit, X-RateLimit-Remaining, and X-RateLimit-Reset (Unix timestamp, seconds, when the minute window resets).

PlanRequests / dayRequests / minute
Free50020
Pro50,000200
Business250,000500
EnterpriseUnlimited2,000

Per-minute limit exceeded (resets in seconds)

{
  "error": {
    "code": "RATE_LIMIT_EXCEEDED",
    "message": "Rate limit exceeded. Resets in 47 seconds.",
    "requestId": "0HN9K2P4QR8S1:00000001"
  }
}

Daily cap exceeded (resets at midnight UTC)

{
  "error": {
    "code": "DAILY_LIMIT_EXCEEDED",
    "message": "Daily request limit reached. Resets at midnight UTC.",
    "requestId": "0HN9K2P4QR8S1:00000002"
  }
}
NoteThe key-creation endpoint (POST /v1/keys) is additionally limited to 5 requests per 10 minutes per IP address to prevent abuse. This limit does not count against your API key quota.

// pagination & conventions

Pagination & conventions

Every list endpoint follows the same pagination contract — predictable across /v1/transactions, /v1/filings, /v1/insiders, /v1/companies, /v1/signals, /v1/form144, /v1/holdings, and /v1/managers. Each endpoint page references this section instead of re-stating the rules.

Query parameters

ParamTypeDefaultNotes
pageinteger11-based page number.
per_pageinteger50Max 100 for /v1/transactions; max 500 for other list endpoints.

How do I know when I've reached the end?

Every list endpoint returns a JSON array. When a page returns fewer records than per_page, you've reached the end. There's no total-count header, no next cursor token, and no has_more field — the short-page signal is the contract. This keeps responses cacheable at the CDN edge (every query is just a deterministic URL) and avoids the consistency problems of cursor pagination over an actively-updated dataset.

Built-in paginate helper

Both SDKs expose a paginate() method that handles the loop for you — yields one page (an array) at a time, retries on 429, stops on the first short page. Prefer it over hand-written loops.

# Page through all NVDA insider transactions, 100 per page
curl "https://api.form4api.com/v1/transactions?ticker=NVDA&per_page=100&page=1" \
  -H "X-Api-Key: YOUR_API_KEY"

curl "https://api.form4api.com/v1/transactions?ticker=NVDA&per_page=100&page=2" \
  -H "X-Api-Key: YOUR_API_KEY"

Other conventions

Date formatISO 8601. Date-only values (2026-01-01) are interpreted as 2026-01-01T00:00:00Z. Date filters (from / to) are inclusive.
OrderingResults are returned in a deterministic descending order — typically by transactionDate, filedAt, or reportPeriod depending on the endpoint. See each endpoint's reference for specifics.
Null fieldsOptional fields are null (not missing) when the underlying SEC filing did not include them.
Empty resultsAn empty array ([]) with HTTP 200 — never 404 — when a query matches no rows.
EncodingAll responses are UTF-8 JSON. Numbers are JSON numbers (not strings); monetary values are decimal numbers in USD.

// errors

Errors

All errors use a consistent JSON envelope. The code field is a machine-readable string you can match on; the requestId can be sent to support to help diagnose issues.

Error envelope

{
  "error": {
    "code": "INVALID_API_KEY",
    "message": "The provided API key is invalid.",
    "requestId": "req_7f3a9c"
  }
}
HTTPCodeDescription
401MISSING_API_KEYNo X-Api-Key header was sent.
401INVALID_API_KEYThe API key exists but is invalid or revoked.
402PLAN_REQUIREDThe endpoint requires a higher plan (e.g. Signals + Sentiment require Business).
403PRO_TIER_REQUIREDA Pro-gated filter parameter (e.g. a post-trade return filter) was used on a lower plan.
404NOT_FOUNDThe requested resource (ticker, CIK, accession number, subscription ID) does not exist.
429RATE_LIMIT_EXCEEDEDPer-minute burst limit reached. Check the Retry-After header for seconds to wait.
429DAILY_LIMIT_EXCEEDEDDaily request cap reached. Resets at midnight UTC.
400INVALID_REQUESTRequest body is missing required fields (e.g. webhook url or eventTypes).
400INVALID_EVENT_TYPEAn unrecognised event type was supplied. Valid: TransactionFiled, ClusterBuy, ClusterSell.
400QUERY_TOO_SHORTName search requires at least 2 characters.
400SUBSCRIPTION_LIMIT_EXCEEDEDWebhook subscription cap for your plan reached (Free 1, Pro 5, Business 25). See the Webhooks section for per-plan limits.
400EXPORT_UNBOUNDEDThe CSV export was called without a bounding filter (e.g. ticker or date range). Add a bound to constrain the result set.
400INSECURE_URLWebhook URL must use HTTPS.
400PRIVATE_ADDRESSWebhook URL resolves to a private or loopback address.
400UNRESOLVABLE_HOSTWebhook URL hostname could not be resolved via DNS.
400INVALID_RANGEThe since parameter for webhook events is more than 30 days in the past.

// transactions

Transactions

Returns individual insider transactions parsed from Form 4 filings. Each record represents a single row in a Form 4 table — one trade by one insider at one price.

GET/v1/transactions
NameTypeRequiredDescription
tickerstringoptionalFilter by stock ticker symbol (e.g. AAPL, MSFT).
cikstringoptionalFilter by company CIK (alternative to ticker).
insider_cikstringoptionalFilter to transactions by a specific insider CIK.
codestringoptionalFilter by SEC transaction code. Common values: P (open-market purchase), S (open-market sale), A (grant/award), M (option exercise), F (tax withholding on vest/exercise), D (disposition to issuer), C (conversion), J (other acquisition or disposition), G (gift). Full list of 22 codes documented in the Glossary.
codesstringoptionalCSV list of transaction codes to include (e.g. P,M,A). Mutually exclusive with exclude_codes.
exclude_codesstringoptionalCSV list of transaction codes to exclude (e.g. F,D). Mutually exclusive with codes.
categorystringoptionalHigh-level trade category preset. Values: open_market (P + S codes only), grants (A + M), derivatives (derivative-flagged rows), gifts (G), other. Composable with other filters.
exclude_categorystringoptionalExclude a category. Same values as category. E.g. exclude_category=derivatives removes all derivative transactions.
exclude_derivativebooleanoptionalIf true, omit derivative-security transactions (options, warrants, convertibles). Equivalent to exclude_category=derivatives.
significantbooleanoptionalPreset filter for high-conviction trades: open-market only (P code), no 10b5-1 plan, no derivatives. Equivalent to category=open_market&exclude_10b5=true&exclude_derivative=true.
exclude_10b5booleanoptionalIf true, omit transactions filed under a Rule 10b5-1 pre-scheduled trading plan. Useful for filtering to discretionary conviction trades only.
fromstringoptionalStart date filter (ISO 8601, e.g. 2026-01-01). Filters by transactionDate.
tostringoptionalEnd date filter (ISO 8601).
min_valuenumberoptionalPro only. Minimum transaction value in USD (sharesAmount × pricePerShare). Rows where totalValue is null are excluded.
max_valuenumberoptionalPro only. Maximum transaction value in USD.
min_sharesnumberoptionalPro only. Minimum number of shares transacted.
max_sharesnumberoptionalPro only. Maximum number of shares transacted.
min_return_1dnumberoptionalPro+ only. Minimum 1-trading-day post-filing return as a decimal (e.g. 0.05 = 5%). Excludes transactions without a computed 1d return.
max_return_1dnumberoptionalPro+ only. Maximum 1-trading-day post-filing return.
min_return_1wnumberoptionalPro+ only. Minimum 1-week (5 trading days) post-filing return.
max_return_1wnumberoptionalPro+ only. Maximum 1-week post-filing return.
min_return_1mnumberoptionalPro+ only. Minimum 1-month (21 trading days) post-filing return.
max_return_1mnumberoptionalPro+ only. Maximum 1-month post-filing return.
min_return_3mnumberoptionalPro+ only. Minimum 3-month (63 trading days) post-filing return.
max_return_3mnumberoptionalPro+ only. Maximum 3-month post-filing return.
min_return_6mnumberoptionalPro+ only. Minimum 6-month (126 trading days) post-filing return.
max_return_6mnumberoptionalPro+ only. Maximum 6-month post-filing return.
has_returnsbooleanoptionalPro+ only. true = only transactions with all 5 horizons populated. false = only transactions where one or more horizons are still null.
per_pagenumberoptionalNumber of results to return. Default: 50, max: 100.
pagenumberoptionalPage number for pagination. Default: 1.

Date filters (from / to) are both inclusive, treated as UTC, and filter on transactionDate. A date-only value (e.g. 2026-01-01) is interpreted as 2026-01-01T00:00:00Z. Results are ordered by transactionDate descending.

curl "https://api.form4api.com/v1/transactions?ticker=AAPL&per_page=5" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "ticker": "AAPL",
    "companyName": "Apple Inc.",
    "insiderName": "Cook Timothy D",
    "insiderCik": "0001214156",
    "insiderTitle": "Chief Executive Officer",
    "isDirector": false,
    "isOfficer": true,
    "is10PctOwner": false,
    "accessionNumber": "0001140361-26-013190",
    "securityTitle": "Common Stock",
    "transactionCode": "S",
    "isOpenMarket": true,
    "is10b5Plan": false,
    "sharesAmount": 5087,
    "pricePerShare": 251.25,
    "totalValue": 1278153.75,
    "sharesOwnedAfter": 3340280,
    "directIndirect": "D",
    "isDerivative": false,
    "transactionDate": "2026-04-02T00:00:00Z",
    "periodOfReport": "2026-04-01T00:00:00Z",
    "return1d": 0.0124,
    "return1w": 0.0237,
    "return1m": 0.0418,
    "return3m": 0.1156,
    "return6m": 0.1842
  }
]
isOpenMarkettrue only when transactionCode is P (purchase) or S (sale). All other codes — option exercises, awards, tax withholding — return false.
is10b5Plantrue when the trade was filed under a Rule 10b5-1 pre-scheduled trading plan. These trades are automatic and carry no conviction signal. Use ?exclude_10b5=true to omit them from results.
insiderTitleOfficer title as reported on the Form 4 (e.g. "Chief Executive Officer"). null when not disclosed.
isDirector / isOfficer / is10PctOwnerRelationship flags from the Form 4 header. An insider may have more than one role (e.g. a founder who is both CEO and 10% owner).
totalValuesharesAmount × pricePerShare in USD. null when pricePerShare is null (common for grants and option exercises).
directIndirect"D" = directly owned. "I" = indirectly owned (via trust, spouse, or other entity).
isDerivativetrue when the security is a derivative (option, warrant, convertible). Derivative transactions report shares underlying the instrument, not shares directly transferred.
periodOfReportThe date the Form 4 covers — typically the same as transactionDate, but may differ for deferred or reportable transactions.
return1d / 1w / 1m / 3m / 6mStock return at 1 / 5 / 21 / 63 / 126 trading days after the filing date, as a decimal (0.05 = +5%). Anchored on the first market close at or after filedAt, split-adjusted via Yahoo Finance daily bars. null when the horizon hasn't been reached yet (e.g. a 4-month-old filing has no return6m) or the ticker has no price data on file. All horizons populated within ~6 months of any filing.

How are Form 4/A amendments handled?

When an insider files an amendment to a previously-filed Form 4 (designated Form 4/A), they're correcting an error in the original — typically a wrong share count, a wrong transaction code, or a missing transaction. Naive ingestion pipelines treat the amendment as a new filing, which silently double-counts the transaction in downstream analytics. Form4API's parser detects the amendment relationship via the EDGAR accession-number link, retires the original transaction, applies the corrected values in place, and exposes a single canonical record at /v1/transactions with an isAmended flag and a reference to the original accession number.

Cluster signals, sentiment, post-trade returns, and any aggregations you build on top automatically use the corrected data. No reconciliation logic is required in your code — the API guarantees exactly one transaction record per real-world event regardless of how many amendments the insider files.

isAmendedtrue when this record was rewritten from a Form 4/A. false when the original Form 4 was the final version.
amendedFromAccessionNumberOriginal Form 4 accession the amendment supersedes. null when isAmended is false.

// quality filters (free)

Use significant=true to get only high-conviction open-market buys — no 10b5-1 plans, no derivatives. Equivalent to combining category=open_market&exclude_10b5=true&exclude_derivative=true.

/v1/transactions?significant=true&from=2026-01-01

// pro tier

Size filtering (min_value, max_value, min_shares, max_shares) and return screening (min_return_*, max_return_*, has_returns) require the Pro plan or higher.

Response fields are visible on every tier — only the filter parameters are gated. Free-tier requests with any gated filter return 403 PRO_TIER_REQUIRED.

Example — significant open-market buys over $1M where the stock was up >20% three months later:

/v1/transactions?significant=true&min_value=1000000&min_return_3m=0.20

// filings

Filings

Returns Form 4 filing headers. Use these endpoints when you need filing-level metadata such as the accession number, filed timestamp, and period of report. To get the underlying transactions, use /v1/transactions.

GET/v1/filings/recent

Returns the most recent Form 4 filings across all companies.

NameTypeRequiredDescription
tickerstringoptionalFilter by company ticker (e.g. AAPL).
per_pagenumberoptionalNumber of results to return. Default: 20, max: 100.
curl "https://api.form4api.com/v1/filings/recent?per_page=10" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "accessionNumber": "0001140361-26-019658",
    "companyTicker": "GYRE",
    "companyName": "GYRE THERAPEUTICS, INC.",
    "periodOfReport": "2026-05-05T00:00:00Z",
    "filedAt": "2026-05-08T02:02:09Z",
    "amendmentType": "Original",
    "transactionCount": 2
  }
]
GET/v1/filings/{accession}

Returns a single filing by its SEC accession number, including a count of its transactions. To retrieve the transactions themselves use /v1/transactions.

curl "https://api.form4api.com/v1/filings/0001209191-26-034821" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "accessionNumber": "0001140361-26-017175",
  "companyTicker": "AAPL",
  "companyName": "Apple Inc.",
  "periodOfReport": "2026-04-23T00:00:00Z",
  "filedAt": "2026-05-04T07:01:02Z",
  "amendmentType": "Original",
  "transactionCount": 1
}

// insiders

Insiders

Search for individual insiders (directors, officers, 10%+ owners) by name, fetch a single insider profile by CIK, or retrieve their complete trade history.

GET/v1/insiders

Search insiders by name. Returns a paginated list.

NameTypeRequiredDescription
namestringoptionalPartial name match (case-insensitive, minimum 2 characters). E.g. "cook" matches "Cook Timothy D". Returns 400 QUERY_TOO_SHORT if fewer than 2 characters are supplied.
per_pagenumberoptionalNumber of results per page. Default: 20, max: 100.
pagenumberoptionalPage number for pagination. Default: 1.
curl "https://api.form4api.com/v1/insiders?name=cook" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "cik": "0001214128",
    "name": "Cook Timothy D",
    "isDirector": true,
    "isOfficer": true,
    "isTenPercentOwner": false,
    "officerTitle": "Chief Executive Officer",
    "totalFilings": 48
  }
]
GET/v1/insiders/{cik}

Fetch a single insider profile by their SEC CIK number. The CIK is returned by the list endpoint and by any transaction record.

curl "https://api.form4api.com/v1/insiders/0001214128" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "cik": "0001214128",
  "name": "Cook Timothy D",
  "isDirector": true,
  "isOfficer": true,
  "isTenPercentOwner": false,
  "officerTitle": "Chief Executive Officer",
  "totalFilings": 48
}
GET/v1/insiders/{cik}/transactions

Returns all Form 4 transactions filed by this insider, newest first. Supports date range filtering and pagination.

NameTypeRequiredDescription
fromstringoptionalStart date (ISO 8601, e.g. 2026-01-01). Filters by transactionDate.
tostringoptionalEnd date (ISO 8601).
pagenumberoptionalPage number. Default: 1.
per_pagenumberoptionalResults per page. Default: 50, max: 100.
curl "https://api.form4api.com/v1/insiders/0001214128/transactions?per_page=10" \
  -H "X-Api-Key: YOUR_API_KEY"
GET/v1/insiders/{cik}/summaryPro+

One-call aggregate of this insider's entire career: total bought / sold USD, net flow, top companies by transaction count, transaction-code breakdown (P/S/F/M/A/G), 10b5-1 vs discretionary split, and post-trade return averages (discretionary open-market trades only — 10b5-1 plan trades and grants/exercises excluded for cleaner signal). Saves you a loop over /transactions when you need career-level analytics rather than the trade ledger.

curl "https://api.form4api.com/v1/insiders/0001214128/summary" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "cik": "0001214128",
  "name": "Cook Timothy D",
  "officerTitle": "Chief Executive Officer",
  "isDirector": true,
  "isOfficer": true,
  "isTenPercentOwner": false,
  "career": {
    "firstTransaction": "2011-09-09T00:00:00Z",
    "lastTransaction": "2026-04-30T00:00:00Z",
    "totalTransactions": 142,
    "totalBoughtUsd": 0,
    "totalSoldUsd": 821345670.00,
    "netUsd": -821345670.00,
    "companies": [
      { "ticker": "AAPL", "companyName": "Apple Inc.", "transactionCount": 142, "firstAtCompany": "2011-09-09T00:00:00Z" }
    ],
    "transactionTypeBreakdown": {
      "P": 0, "S": 78, "F": 12, "M": 36, "A": 14, "G": 0, "Other": 2
    },
    "tenB5Plan": {
      "totalUnderPlan": 64,
      "totalDiscretionary": 14,
      "pctUnder10b5Plan": 45.07
    },
    "returns": {
      "openMarketTransactionsWithReturns": 78,
      "avgReturn1d": 0.0021,
      "avgReturn1w": 0.0114,
      "avgReturn1m": 0.0327,
      "avgReturn3m": 0.0865,
      "avgReturn6m": 0.1542
    }
  }
}
GET/v1/insiders/{cik}/scorecardPro

Predictive track record for a single insider: hit rate (fraction of open-market buys with a positive absolute return after 3 months), average and median 3-month and 6-month returns, best and worst single buy, and a scored-buy count. Useful for ranking insiders by historical signal quality before acting on a new filing. Requires at least 5 matured discretionary open-market buys — returns sampleSufficient: false otherwise (field values are null; do not infer signal from insufficient data).

Methodology: absolute post-filing return — not market-adjusted. A buy "hits" when the stock closes higher 63 trading days after the filing date, regardless of index moves. Only discretionary open-market purchases (code P, no 10b5-1 plan, no derivatives) with a matured 3-month return window are counted.
curl "https://api.form4api.com/v1/insiders/0001214128/scorecard" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "insiderCik": "0001214128",
  "insiderName": "Cook Timothy D",
  "scoredBuyCount": 12,
  "sampleSufficient": true,
  "hitRate3m": 0.75,
  "avgReturn3m": 0.112,
  "medianReturn3m": 0.084,
  "scoredBuyCount6m": 10,
  "sampleSufficient6m": true,
  "hitRate6m": 0.70,
  "avgReturn6m": 0.198,
  "medianReturn6m": 0.153,
  "bestBuy": {
    "ticker": "AAPL",
    "filedAt": "2019-08-14T00:00:00Z",
    "return3m": 0.412
  },
  "worstBuy": {
    "ticker": "AAPL",
    "filedAt": "2022-02-01T00:00:00Z",
    "return3m": -0.218
  },
  "lastTradeAt": "2024-11-01T00:00:00Z",
  "methodology": "absolute-return-v1"
}
GET/v1/insiders/leaderboardBusiness

Ranked list of insiders sorted by 3-month hit rate descending, limited to those with sampleSufficient: true. Useful for building a watchlist of historically accurate insiders, or weighting a cluster-buy signal by participant quality. Accepts per_page (default 20, max 100) and page. Each row is the same shape as the scorecard response.

Same methodology caveat as /scorecard above: absolute return, not market-adjusted. Rankings are a historical signal, not a forward guarantee.
curl "https://api.form4api.com/v1/insiders/leaderboard?per_page=10" \
  -H "X-Api-Key: YOUR_API_KEY"

// companies

Companies

Look up a company by ticker to get its SEC profile and the list of registered insiders who have filed Form 4 for that company.

GET/v1/companies

Returns a list of companies, optionally sorted and limited.

NameTypeRequiredDescription
sortstringoptionalSort order. Accepted values: name (alphabetical, default) or totalFilings (most-filed first).
limitintegeroptionalMaximum number of results to return. Default 100.
curl "https://api.form4api.com/v1/companies?sort=totalFilings&limit=10" \
  -H "X-Api-Key: YOUR_API_KEY"
GET/v1/companies/{ticker}

Returns the SEC profile for a company.

NameTypeRequiredDescription
tickerstringrequiredThe company ticker symbol (path parameter).
curl "https://api.form4api.com/v1/companies/AAPL" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "cik": "0000320193",
  "name": "Apple Inc.",
  "ticker": "AAPL",
  "exchange": "Nasdaq",
  "totalFilings": 119,
  "activeInsiders": 19,
  "sicDescription": "Electronic Computers",
  "stateOfIncorporation": "CA",
  "website": null
}
sicDescriptionSEC SIC industry description (e.g. "Electronic Computers"). null when not available.
stateOfIncorporationTwo-letter US state code where the company is incorporated (e.g. "CA", "DE"). null for foreign issuers.
websiteCompany website URL as filed with the SEC. null when not disclosed.
activeInsidersNumber of distinct insiders who have filed at least one Form 4 for this company.
GET/v1/companies/{ticker}/insiders

Returns all insiders who have filed Form 4 for this company, with their CIK and most recent transaction date.

NameTypeRequiredDescription
tickerstringrequiredThe company ticker symbol (path parameter).
curl "https://api.form4api.com/v1/companies/AAPL/insiders" \
  -H "X-Api-Key: YOUR_API_KEY"

// signals

Signals

Signals surface statistically notable insider activity. A cluster buy is triggered when 3 or more distinct insiders at the same company file open-market purchases (code P) within a rolling 5-day window ending on the filing date. A cluster sell follows the same rule for sales (code S). Option exercises, grants, and tax withholdings do not count toward the cluster threshold. Pre-scheduled trades filed under a Rule 10b5-1 plan are also excluded — these carry no conviction signal.

One signal record is stored per company per day and is updated each time a new filing for that company is processed. Signals are ordered by signalDate descending.

Available on Business and Enterprise plans only. Free and Pro keys receive a 402 PLAN_REQUIRED error.
GET/v1/signals
NameTypeRequiredDescription
tickerstringoptionalFilter by company ticker (e.g. NVDA).
cluster_buybooleanoptionalIf true, return only signals where a cluster buy is active.
cluster_sellbooleanoptionalIf true, return only signals where a cluster sell is active.
pagenumberoptionalPage number. Default: 1.
per_pagenumberoptionalResults per page. Default: 100, max: 500.
curl "https://api.form4api.com/v1/signals?cluster_buy=true&per_page=5" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "ticker": "OPCH",
    "companyName": "Option Care Health, Inc.",
    "signalDate": "2026-05-07T00:00:00Z",
    "buySellRatio": 2.47,
    "isClusterBuy": true,
    "isClusterSell": false,
    "insiderCount": 11
  }
]
buySellRatioTotal shares purchased ÷ total shares sold by all insiders over the past 90 days. Capped at 99 when there are buys but no sells.
insiderCountNumber of distinct insiders who filed any transaction for this company in the past 90 days — not just those who contributed to the cluster trigger.
signalDateThe date the triggering Form 4 was filed with the SEC, not the transaction date.

402 response — plan too low

{
  "error": {
    "code": "PLAN_REQUIRED",
    "message": "This endpoint requires the Business plan or higher. Your current plan is Free.",
    "requestId": "req_7f3a9c"
  }
}

How is the insider sentiment score calculated?

Monthly insider sentiment score for a ticker, computed MSPR-style: (buyValue − sellValue) / (buyValue + sellValue) × 100, clamped to ±100. Positive = net buying conviction; negative = net selling.

Our score uses only open-market transactions (codes P and S), excluding 10b5-1 plan trades, option exercises, grants, and tax withholdings. Pre-scheduled 10b5-1 sales carry no conviction signal, so leaving them in pollutes the score — this is the key differentiator vs other vendors' MSPR. Months with no qualifying transactions are omitted from the array; clients that want a dense time series can zero-fill on their side.

Available on Business and Enterprise plans only.
GET/v1/signals/sentiment/{ticker}
NameTypeRequiredDescription
monthsnumberoptionalMonths of history to return. Default: 24, min: 1, max: 60.
curl "https://api.form4api.com/v1/signals/sentiment/NVDA?months=6" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "ticker": "NVDA",
  "companyName": "NVIDIA Corporation",
  "monthly": [
    {
      "period": "2026-05",
      "score": -82.5,
      "buyValue": 250000.00,
      "sellValue": 2580000.00,
      "buyCount": 1,
      "sellCount": 4
    },
    {
      "period": "2026-04",
      "score": 12.7,
      "buyValue": 1100000.00,
      "sellValue": 850000.00,
      "buyCount": 3,
      "sellCount": 2
    }
  ]
}

// form-144

Form 144

Form 144 is the SEC notice of proposed sale — insiders must file it before selling restricted or control securities above the 5,000-share or $50,000 / 3-month threshold. The actual sale shows up later in Form 4, typically within a few days.

This makes Form 144 a leading indicator: you see the intent to sell before the trade prints. The isUnder10b5Plan flag separates pre-scheduled disposition (low signal) from discretionary intent (higher signal) — derived from the planAdoptionDates element in the filing.

Unlike Form 4, Form 144 carries the insider as plain text only — there is no CIK on the insider field. Use insider_name as a forgiving ILIKE substring (matches cook against Timothy D Cook or COOK, TIM).

Available on Business and Enterprise plans only. Free and Pro keys receive a 402 PLAN_REQUIRED error.
GET/v1/form144
NameTypeRequiredDescription
tickerstringoptionalFilter by company ticker (e.g. NVDA).
insider_namestringoptionalCase-insensitive substring match on the insider's name as filed.
fromdateoptionalOnly return notices filed on or after this date (UTC).
todateoptionalOnly return notices filed on or before this date (UTC).
exclude_10b5booleanoptionalIf true, omit notices filed under a 10b5-1 plan.
pagenumberoptionalPage number. Default: 1.
per_pagenumberoptionalResults per page. Default: 50, max: 100.
curl "https://api.form4api.com/v1/form144?ticker=NVDA&exclude_10b5=true&per_page=5" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "accessionNumber": "0001950047-26-003316",
    "ticker": "NVDA",
    "companyName": "NVIDIA Corporation",
    "insiderName": "Huang Jen Hsun",
    "relationship": "Director / Officer",
    "broker": "Charles Schwab",
    "sharesProposed": 120000,
    "aggregateMarketValue": 24500000.00,
    "approxSaleDate": "2026-06-03",
    "exchange": "NASDAQ",
    "acquiredDate": "2019-12-12",
    "natureOfAcquisition": "Founders Shares",
    "isUnder10b5Plan": false,
    "filedAt": "2026-05-21T00:00:00Z",
    "noticeDate": "2026-05-21"
  }
]
sharesProposedFrom the filing's noOfUnitsSold field (despite the name, this is the proposed quantity, not the executed one).
isUnder10b5PlanTrue when the notice references a 10b5-1 plan adoption. Lets you separate discretionary intent from pre-scheduled sales.
approxSaleDateInsider's stated expected sale date. Filings dated MM/DD/YYYY are normalised to UTC midnight.
acquiredDateWhen the insider originally acquired the shares — often years before this notice.

402 response — plan too low

{
  "error": {
    "code": "PLAN_REQUIRED",
    "message": "This endpoint requires the Business plan or higher. Your current plan is Free.",
    "requestId": "req_7f3a9c"
  }
}

// transactions-export

Transactions Export

Streams a bulk RFC 4180 CSV of Form 4 insider transactions. Accepts the same filter grammar as GET /v1/transactions but returns a CSV file rather than paginated JSON. Use this endpoint when you need a full dataset for backtesting, spreadsheet analysis, or bulk ingestion.

Available on Business and Enterprise plans only. Free and Pro keys receive a 402 PLAN_REQUIRED error.

Bounded request required. At least one of ticker, cik, insider_cik, or from must be provided. Requests without any bounding parameter return 400 EXPORT_UNBOUNDED.

Hard cap: 100,000 rows per request. For full history, chunk by date range (e.g. one calendar year at a time). Rows stream in ascending filedAt order.

Use filedAt, not transactionDate, for backtesting. A Form 4 must be filed within 2 business days of the trade. Filtering on transactionDate leaks lookahead bias because you would not have known about the trade until it was filed. The from / to parameters on this endpoint filter on filedAt, not transactionDate. See the backtesting guide for a worked example.

GET/v1/transactions/export
NameTypeRequiredDescription
tickerstringoptionalFilter by stock ticker symbol (e.g. AAPL). One of ticker, cik, insider_cik, or from is required.
cikstringoptionalFilter by company CIK. One of ticker, cik, insider_cik, or from is required.
insider_cikstringoptionalFilter to transactions by a specific insider CIK. One of ticker, cik, insider_cik, or from is required.
codestringoptionalFilter by SEC transaction code (e.g. P, S, A, M).
codesstringoptionalCSV list of transaction codes to include (e.g. P,M,A). Mutually exclusive with exclude_codes.
exclude_codesstringoptionalCSV list of transaction codes to exclude (e.g. F,D). Mutually exclusive with codes.
categorystringoptionalHigh-level trade category preset: open_market, grants, derivatives, gifts, other.
exclude_categorystringoptionalExclude a category. Same values as category.
exclude_derivativebooleanoptionalIf true, omit derivative-security transactions (options, warrants, convertibles).
significantbooleanoptionalPreset: open-market only, no 10b5-1 plan, no derivatives. Equivalent to category=open_market&exclude_10b5=true&exclude_derivative=true.
exclude_10b5booleanoptionalIf true, omit transactions filed under a Rule 10b5-1 pre-scheduled trading plan.
fromdateoptionalStart date filter (ISO 8601, e.g. 2020-01-01). Filters by filedAt. One of ticker, cik, insider_cik, or from is required.
todateoptionalEnd date filter (ISO 8601). Filters by filedAt. Inclusive, UTC.
min_valuenumberoptionalPro only. Minimum transaction value in USD.
max_valuenumberoptionalPro only. Maximum transaction value in USD.
min_sharesnumberoptionalPro only. Minimum number of shares transacted.
max_sharesnumberoptionalPro only. Maximum number of shares transacted.
min_return_1dnumberoptionalPro+ only. Minimum 1-trading-day post-filing return as a decimal (e.g. 0.05 = 5%).
max_return_1dnumberoptionalPro+ only. Maximum 1-trading-day post-filing return.
min_return_1wnumberoptionalPro+ only. Minimum 1-week post-filing return.
max_return_1wnumberoptionalPro+ only. Maximum 1-week post-filing return.
min_return_1mnumberoptionalPro+ only. Minimum 1-month post-filing return.
max_return_1mnumberoptionalPro+ only. Maximum 1-month post-filing return.
min_return_3mnumberoptionalPro+ only. Minimum 3-month post-filing return.
max_return_3mnumberoptionalPro+ only. Maximum 3-month post-filing return.
min_return_6mnumberoptionalPro+ only. Minimum 6-month post-filing return.
max_return_6mnumberoptionalPro+ only. Maximum 6-month post-filing return.
has_returnsbooleanoptionalPro+ only. true = only transactions with all 5 return horizons populated.
inst_ownership_trendstringoptionalFilter by institutional ownership trend. Values: rising, falling, stable.
curl -H "X-Api-Key: YOUR_API_KEY" \
  "https://api.form4api.com/v1/transactions/export?ticker=AAPL&from=2020-01-01&to=2024-12-31" \
  -o aapl-insider.csv

CSV columns (27)

filedAt,transactionDate,ticker,companyName,insiderName,insiderCik,insiderTitle,isDirector,isOfficer,isTenPercentOwner,transactionCode,isBuyOrSell,isDerivative,is10b5Plan,securityTitle,sharesAmount,pricePerShare,value,sharesOwnedAfter,directOrIndirect,accessionNumber,periodOfReport,return1d,return1w,return1m,return3m,return6m
filedAtISO 8601 UTC timestamp of when the Form 4 was filed with the SEC. Use this column as your event timestamp for backtesting - not transactionDate.
isBuyOrSelltrue when transactionCode is P (purchase) or S (sale) - i.e. an open-market trade.
directOrIndirectD = directly owned. I = indirectly owned (via trust, spouse, or other entity).
valuesharesAmount × pricePerShare in USD. Empty when pricePerShare is null (common for grants and option exercises).
return1d ... return6mPost-filing stock return at 1 / 5 / 21 / 63 / 126 trading days as a decimal (e.g. 0.05 = +5%). Empty when the horizon has not been reached yet or the ticker has no price data.

400 response - missing bound

{
  "error": {
    "code": "EXPORT_UNBOUNDED",
    "message": "At least one of ticker, cik, insider_cik, or from is required for export requests.",
    "requestId": "req_8c2b1d"
  }
}

// form-144-export

Form 144 Export

Streams a bulk RFC 4180 CSV of Form 144 notice-of-proposed-sale filings. Accepts the same filter grammar as GET /v1/form144 but returns a CSV file rather than paginated JSON. Use this endpoint to build offline datasets, backtest leading-indicator strategies, or track proposed-sale history across a watchlist.

Available on Business and Enterprise plans only. Free and Pro keys receive a 402 PLAN_REQUIRED error.

Bounded request required. At least one of ticker, insider_name, or from must be provided. Requests without any bounding parameter return 400 EXPORT_UNBOUNDED.

Hard cap: 100,000 rows per request. For full history, chunk by date range (e.g. one calendar year at a time). Rows stream in ascending filedAt order.

GET/v1/form144/export
NameTypeRequiredDescription
tickerstringoptionalFilter by company ticker (e.g. NVDA). One of ticker, insider_name, or from is required.
insider_namestringoptionalCase-insensitive substring match on the insider's name as filed. One of ticker, insider_name, or from is required.
fromdateoptionalStart date filter (ISO 8601). Filters by filedAt. One of ticker, insider_name, or from is required.
todateoptionalEnd date filter (ISO 8601). Filters by filedAt. Inclusive, UTC.
exclude_10b5booleanoptionalIf true, omit notices filed under a 10b5-1 plan.
curl -H "X-Api-Key: YOUR_API_KEY" \
  "https://api.form4api.com/v1/form144/export?ticker=NVDA&from=2020-01-01&to=2024-12-31" \
  -o nvda-form144.csv

CSV columns (15)

filedAt,noticeDate,ticker,companyName,insiderName,relationship,brokerName,sharesProposed,aggregateMarketValue,approxSaleDate,exchange,acquiredDate,natureOfAcquisition,isUnder10b5Plan,accessionNumber
filedAtISO 8601 UTC timestamp of when the Form 144 was filed with the SEC. Use this as the event timestamp for leading-indicator strategies.
noticeDateThe date of the notice as stated on the filing, normalised to YYYY-MM-DD.
sharesProposedThe number of shares the insider proposes to sell. This is an intent figure, not a confirmed execution.
aggregateMarketValueEstimated market value of the proposed sale at the time of filing, in USD.
approxSaleDateThe insider's stated expected sale date. Filings with MM/DD/YYYY format are normalised to YYYY-MM-DD.
isUnder10b5Plantrue when the notice references a 10b5-1 plan. Use exclude_10b5=true to omit these and focus on discretionary intent.
acquiredDateWhen the insider originally acquired the shares proposed for sale.

400 response - missing bound

{
  "error": {
    "code": "EXPORT_UNBOUNDED",
    "message": "At least one of ticker, insider_name, or from is required for export requests.",
    "requestId": "req_9a3e4f"
  }
}

// holdings

Institutional Holdings (13F-HR)

Quarterly Form 13F-HR holdings filed by institutional investment managers with discretion over more than $100M in 13F-eligible equity securities. Filed within 45 days of quarter end (so Q1 holdings land mid-May, Q2 mid-August, etc.).

Each row is one position. A single security can appear multiple times in one filing when the manager attributes shares across sub-managers — Berkshire, for instance, lists each security up to 14 times, once per subsidiary insurance company.

Use cusip when you need exact security matching across all filers (the only stable cross-filing identifier). Use ticker for issuer-side queries — this resolves via the issuer CIK and only covers issuers we already track from Form 4, so coverage is high for US large-caps but partial for ETFs and bonds.

Both /v1/holdings and /v1/managers require the Business or Enterprise plan. Free and Pro keys receive a 402 PLAN_REQUIRED error.
GET/v1/holdings
NameTypeRequiredDescription
tickerstringoptionalFilter to a specific issuer ticker (e.g. NVDA). Resolves via the issuer CIK — only matches holdings where the underlying company is in our database.
cusipstringoptionalExact 9-character CUSIP match. Use this when you need 100% coverage (some issuers don't have a Form-4-mapped ticker).
manager_cikstringoptionalFilter by filing manager CIK (e.g. 1067983 for Berkshire). Leading zeros optional.
quarterdateoptionalFilter to a specific report period (always a quarter-end date, e.g. 2026-03-31).
min_valuenumberoptionalMinimum USD value of the position. Filters out small holdings.
pagenumberoptionalPage number. Default: 1.
per_pagenumberoptionalResults per page. Default: 50, max: 100.
curl "https://api.form4api.com/v1/holdings?manager_cik=1067983&per_page=3" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "manager": "Berkshire Hathaway Inc",
    "managerCik": "1067983",
    "reportPeriod": "2026-03-31T00:00:00Z",
    "issuerName": "APPLE INC",
    "ticker": "AAPL",
    "cusip": "037833100",
    "titleOfClass": "COM",
    "value": 91234567890,
    "shares": 300000000,
    "shareType": "SH",
    "investmentDiscretion": "SOLE",
    "votingSole": 300000000,
    "votingShared": 0,
    "votingNone": 0,
    "accessionNumber": "0001193125-26-226661",
    "filedAt": "2026-05-15T00:00:00Z"
  }
]
valuePosition value in USD. Per the SEC's 2020 amendment, this is dollars (not thousands). Older historical filings used thousands; we backfill only post-amendment data.
shareTypeSH = share count. PRN = principal amount (for bonds / convertibles).
investmentDiscretionSOLE = manager has sole discretion. DFND = defined / shared with another party. OTR = other.
tickerMay be null when we couldn't resolve the issuer's CUSIP to an issuer in our database (ETFs, foreign ADRs, less-followed issuers). The cusip field is always populated.

Which 13F managers does the index cover?

Summary view of every 13F-HR filer, returning the latest filing per manager with aggregate AUM and position count. Useful for discovery ("who are the biggest institutional filers?") and ranking ("rank holders of AAPL by AUM").

GET/v1/managers
NameTypeRequiredDescription
namestringoptionalCase-insensitive substring match on the manager name as filed (e.g. "berkshire" matches "Berkshire Hathaway Inc").
min_aumnumberoptionalMinimum total reported AUM in USD. Filters out smaller funds.
pagenumberoptionalPage number. Default: 1.
per_pagenumberoptionalResults per page. Default: 50, max: 100.
curl "https://api.form4api.com/v1/managers?min_aum=100000000000&per_page=5" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "name": "Berkshire Hathaway Inc",
    "cik": "1067983",
    "latestReportPeriod": "2026-03-31T00:00:00Z",
    "latestAum": 263095703570,
    "latestPositionCount": 90,
    "latestFiledAt": "2026-05-15T00:00:00Z",
    "latestAccessionNumber": "0001193125-26-226661"
  }
]

402 response — plan too low

{
  "error": {
    "code": "PLAN_REQUIRED",
    "message": "This endpoint requires the Business plan or higher. Your current plan is Free.",
    "requestId": "req_7f3a9c"
  }
}

// webhooks

Webhooks

Subscribe to real-time events instead of polling. When a matching event fires, Form4API POSTs a JSON payload to your endpoint within seconds of the SEC publishing the filing. Each delivery is signed with X-Insider-Signature so you can verify it came from us.

POST/v1/webhooks

Create a new webhook subscription. The signing secret is returned once — store it immediately. Subscription caps are tier-dependent; Free-tier subscriptions are flagged isReadOnly: true and cannot be modified after creation.

PlanActive subscriptions
Free1 (read-only)
Pro5
Business25
EnterpriseUnlimited

Request body

NameTypeRequiredDescription
urlstringrequiredHTTPS endpoint that will receive webhook payloads. Must be publicly reachable.
eventTypesstring[]requiredArray of event types to subscribe to. Valid values: TransactionFiled, ClusterBuy, ClusterSell.

Response

NameTypeRequiredDescription
subscriptionIdnumberoptionalUnique subscription ID. Use this to delete the webhook.
secretstringoptionalSigning secret — shown once only. Store it securely to verify X-Insider-Signature.
urlstringoptionalThe endpoint URL.
eventTypesstring[]optionalSubscribed event types.
isReadOnlybooleanoptionalTrue for Free-tier subscriptions — they receive events but cannot be modified after creation.
warningstringoptionalReminder that the secret will not be returned again.
curl -X POST "https://api.form4api.com/v1/webhooks" \
  -H "X-Api-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "url": "https://yourapp.com/webhooks/form4",
    "eventTypes": ["TransactionFiled", "ClusterBuy"]
  }'
GET/v1/webhooks

List all webhook subscriptions for your API key. Secrets are never returned in this response.

curl "https://api.form4api.com/v1/webhooks" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "subscriptionId": 42,
    "url": "https://yourapp.com/webhooks/form4",
    "eventTypes": ["TransactionFiled", "ClusterBuy"],
    "createdAt": "2026-05-01T10:00:00Z",
    "isActive": true
  }
]
DELETE/v1/webhooks/{id}

Delete a webhook subscription by its numeric ID. Returns 204 No Content on success, or 404 NOT_FOUND if the ID doesn't exist or belongs to a different key.

curl -X DELETE "https://api.form4api.com/v1/webhooks/42" \
  -H "X-Api-Key: YOUR_API_KEY"

# Returns 204 No Content on success
GET/v1/webhooks/events

Returns up to 500 delivery records from the last 24 hours by default. Use the optional since parameter (ISO 8601) to replay from a specific timestamp — up to 30 days back. Useful for catching missed deliveries after a planned outage.

curl "https://api.form4api.com/v1/webhooks/events" \
  -H "X-Api-Key: YOUR_API_KEY"

# Replay from a specific point in time (up to 30 days back)
curl "https://api.form4api.com/v1/webhooks/events?since=2026-05-01T00:00:00Z" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "deliveryId": 1042,
    "subscriptionId": 7,
    "eventType": "TransactionFiled",
    "attemptCount": 1,
    "deliveredAt": "2026-05-04T14:23:11Z",
    "nextRetryAt": null,
    "lastStatusCode": 200,
    "isDead": false,
    "payload": { "filingId": 123, "accessionNumber": "0001140361-26-017175" }
  }
]

How do webhook event payloads look?

Every webhook POST has a top-level type field and a data object whose shape depends on the event type.

{
  "type": "TransactionFiled",
  "data": {
    "ticker": "AAPL",
    "companyName": "Apple Inc.",
    "insiderName": "Cook Timothy D",
    "insiderTitle": "Chief Executive Officer",
    "isDirector": false,
    "isOfficer": true,
    "is10PctOwner": false,
    "transactionCode": "S",
    "isOpenMarket": true,
    "is10b5Plan": false,
    "sharesAmount": 10000,
    "pricePerShare": 212.45,
    "totalValue": 2124500.00,
    "transactionDate": "2026-04-30T00:00:00Z"
  }
}

How do I verify webhook signatures?

Each request includes an X-Insider-Signature header with the value sha256=<hex> — HMAC-SHA256 of the raw request body signed with your subscription secret. Always verify before processing.

import crypto from 'crypto'

export async function POST(req: Request) {
  const body = await req.text()
  const sig = req.headers.get('X-Insider-Signature') ?? ''
  const expected = 'sha256=' + crypto
    .createHmac('sha256', process.env.WEBHOOK_SECRET!)
    .update(body)
    .digest('hex')

  if (sig !== expected) {
    return new Response('Invalid signature', { status: 401 })
  }

  const event = JSON.parse(body)
  // handle event.type: 'TransactionFiled' | 'ClusterBuy' | 'ClusterSell'
  return new Response('ok', { status: 200 })
}

// usage

Usage

Check your current quota, view daily request history, and inspect recent API calls — all from your own API key without needing to log into the dashboard.

GET/v1/keys/usage

Returns your current plan, how many requests you have made today, your daily limit, and when the counter resets (midnight UTC).

curl "https://api.form4api.com/v1/keys/usage" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "plan": "Free",
  "requestsToday": 42,
  "dailyLimit": 500,
  "requestsThisMonth": 842,
  "resetAt": "2026-05-16T00:00:00Z"
}
GET/v1/keys/usage/history

Returns a daily breakdown of request counts. Useful for tracking usage trends or building your own monitoring dashboard. Dates are UTC; days with zero requests are omitted.

NameTypeRequiredDescription
daysnumberoptionalNumber of days to include. Default: 30, max: 90.
curl "https://api.form4api.com/v1/keys/usage/history?days=7" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  { "date": "2026-05-15", "count": 42 },
  { "date": "2026-05-14", "count": 318 },
  { "date": "2026-05-13", "count": 204 }
]
GET/v1/keys/usage/activity

Returns your most recent API requests with endpoint, HTTP status, and duration. Useful for debugging integration issues or auditing unexpected usage. Logs are retained for 90 days.

NameTypeRequiredDescription
limitnumberoptionalNumber of recent requests to return. Default: 100, max: 200.
curl "https://api.form4api.com/v1/keys/usage/activity?limit=5" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

[
  {
    "endpoint": "/v1/transactions",
    "statusCode": 200,
    "durationMs": 4,
    "createdAt": "2026-05-15T07:31:22Z"
  },
  {
    "endpoint": "/v1/companies/AAPL",
    "statusCode": 200,
    "durationMs": 3,
    "createdAt": "2026-05-15T07:31:18Z"
  }
]

// billing

Billing

Programmatically generate a Stripe checkout URL to upgrade your plan. The endpoint requires a valid API key and returns a one-time checkout session URL. Redirect the user to this URL to complete payment. See pricing for plan limits and prices.

POST/v1/billing/checkout
ParamInValues
planqueryPro | Business | Enterprise
curl -X POST "https://api.form4api.com/v1/billing/checkout?plan=Pro" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "checkoutUrl": "https://checkout.stripe.com/c/pay/cs_live_..."
}
POST/v1/billing/portal

Creates a Stripe Customer Portal session for managing an existing subscription — cancel, change plan, update payment method. Requires an active paid subscription. Returns a one-time portal URL; redirect the user to it.

curl -X POST "https://api.form4api.com/v1/billing/portal" \
  -H "X-Api-Key: YOUR_API_KEY"

Response

{
  "portalUrl": "https://billing.stripe.com/session/..."
}
Alternatively, upgrade from the dashboard without touching the API.

// mcp

MCP / AI Assistants

The form4api-mcp package wraps the Form4API REST API as an MCP (Model Context Protocol) server. Once configured, any MCP-compatible AI assistant — Claude Desktop, Claude Code, Cursor, Windsurf, Zed — can call Form4API directly without you writing any code.

How do I install and configure the MCP server?

The server runs via npx — no global install needed. Add it to your client's config file and restart the client.

# Claude Desktop — claude_desktop_config.json
# macOS: ~/Library/Application Support/Claude/claude_desktop_config.json
# Windows: %APPDATA%\Claude\claude_desktop_config.json
{
  "mcpServers": {
    "form4api": {
      "command": "npx",
      "args": ["-y", "form4api-mcp"],
      "env": {
        "FORM4API_KEY": "fapi_live_your_key_here"
      }
    }
  }
}

Get your FORM4API_KEY from the dashboard (free, no credit card).

Which MCP tools are available? (23)

ToolDescription
Form 4 insider trading
get_transactionsSearch insider transactions — filter by ticker, insider, date range, transaction codes or whole categories (exclude_category=derivatives), 10b5-1 plan trades, or use significant=true for real discretionary buys/sells only. Pro adds trade-size screening (min_value, min_shares).
get_recent_filingsMost recent Form 4 filings, optionally filtered by ticker.
get_filingSingle filing by SEC accession number.
get_insider_profileInsider profile — name, title, director/officer/10% owner flags.
get_insider_transactionsAll transactions for a specific insider by CIK.
get_company_overviewCompany profile — name, CIK, SIC sector, state, website, filing counts.
get_company_insidersAll insiders who have filed Form 4s for a company.
list_companiesList companies sorted by name or filing count.
get_insider_career_summaryAggregate career rollup: total bought/sold, top companies, 10b5-1 split, return averages. (Pro plan+)
get_insider_scorecardBuy track-record scorecard for an insider (CIK) — hit rate and avg/median 3m/6m return on discretionary open-market buys; null when fewer than 5 matured samples. (Pro plan+)
get_insider_leaderboardTop insiders ranked by hit rate or avg return; filter by horizon (3m/6m), min_trades, and limit. (Business plan+)
Signals + sentiment
get_signalsCluster buy/sell signals — multiple insiders at the same company in the same direction; 10b5-1 trades excluded. (Business plan+)
get_sentimentMSPR-style monthly sentiment score per ticker (−100 to +100), 10b5-1 excluded. (Business plan+)
Form 144 + institutional
get_form144Notice-of-proposed-sale filings — early signal ~2 days before the Form 4 sale lands. (Business plan+)
get_holdingsInstitutional positions from Form 13F-HR; filter by ticker, CUSIP, manager, quarter, or min value. (Business plan+)
get_managersInstitutional manager index with latest AUM. (Business plan+)
Utility
check_usageYour API key usage stats — plan, requests today, daily limit.
get_key_activityRecent API requests for this key.
get_usage_historyDaily request counts for the last N days.
search_insidersSubstring search on insider names.
list_webhooksList your webhook subscriptions.
get_webhook_eventsReplay webhook delivery events since a timestamp.
get_public_statsCorpus coverage stats — filings, transactions, history span, 13F holdings/AUM. No key required.

What example prompts work with MCP?

Once configured, ask your AI assistant natural-language questions:

  • >What insider trades happened at NVDA this week, excluding 10b5-1 plan trades?
  • >Show me significant insider buys at NVDA — real open-market purchases only, no plans or option exercises
  • >Show me cluster buy signals from the last 7 days
  • >What is Tim Cook's career insider-trading summary — total bought/sold and return averages?
  • >Are there any Form 144 filings at TSLA suggesting upcoming sales?
  • >Pull all open-market purchases over $500k at Tesla in 2026
  • >What has the CFO of Microsoft been doing with their shares this year?
  • >Check my Form4API usage and plan
Plan note: All Form 4 core tools (get_transactions, get_recent_filings, company, insider, and utility tools) work on the Free plan. get_insider_career_summary and get_insider_scorecard require Pro. Signals, sentiment, Form 144, holdings, institutional managers, and insider leaderboard (get_signals, get_sentiment, get_form144, get_holdings, get_managers, get_insider_leaderboard) require the Business plan. When a tool requires a higher plan, the AI surfaces a clear upgrade message with a link to pricing — no cryptic errors.

// faq

Frequently asked questions

Developer-focused answers covering amendments, 10b5-1 plan filtering, date semantics, post-trade returns, rate-limit behaviour, and sandbox availability. The same content emits an identical FAQPage JSON-LD block on this page.

// glossary

Glossary

Key terms from SEC filings and insider trading data used throughout this API. Mirrored as a DefinedTermSet JSON-LD block on this page so AI crawlers can quote each definition cleanly.

Accession Number
The SEC's unique identifier for a single filing, formatted as XXXXXXXXXX-YY-ZZZZZZ (e.g. 0001140361-26-013190). The first segment is the filer's CIK, YY is the year, and ZZZZZZ is a sequence number. Use this to fetch a specific filing from the /v1/filings/{accession} endpoint.
Beneficial Ownership
Shares that an insider has an economic interest in, even if they are not registered in the insider's name. An insider is considered a beneficial owner of shares held by a spouse, a trust they control, or a company they own more than 50% of.
CIK
Central Index Key — the SEC's permanent numeric identifier for every entity that files with the SEC, including individuals and companies. CIKs are always 10 digits, zero-padded (e.g. 0001214156). Use a CIK to look up an insider's full filing history via /v1/insiders/{cik}.
Open Market Transaction
A discretionary purchase or sale executed on a public exchange at the prevailing market price. In Form 4 data, open-market transactions are identified by transaction codes P (purchase) and S (sale). These are the trades most relevant for signal analysis — they represent the insider choosing to put their own money in, or taking it out. Non-market events such as option exercises (M), tax withholding (F), grants (A), and gifts (G) are also reported on Form 4 but are not discretionary and should not be treated as conviction signals. The isOpenMarket field makes this distinction explicit.
Rule 10b5-1 Plan
A pre-scheduled trading arrangement that allows corporate insiders to buy or sell company stock at predetermined times, prices, or quantities, set up in advance when the insider held no material non-public information (MNPI). Trades executed under a 10b5-1 plan are automatic — the insider does not make a real-time decision to trade. Because they are pre-committed and not driven by current information, they carry no conviction signal. Form4API marks these trades with is10b5Plan: true and excludes them from cluster buy/sell signal computation. Use ?exclude_10b5=true on the transactions endpoint to filter them out.
Cluster Signal
A ClusterBuy or ClusterSell signal is triggered when three or more insiders at the same company independently file Form 4 transactions in the same direction (all buys or all sells) within a 5-day window. Clusters are considered a stronger signal than a single insider trade because they suggest shared conviction among multiple informed parties.
Derivative Security
A security whose value is derived from an underlying asset — typically company stock. Common derivatives reported on Form 4 include stock options, warrants, and convertible notes. When isDerivative is true in a transaction, sharesAmount refers to the number of shares underlying the derivative, not shares directly transferred.
Direct vs Indirect Ownership
The directIndirect field indicates how an insider holds shares. "D" (direct) means shares are registered in the insider's own name. "I" (indirect) means shares are held through an intermediary such as a trust, LLC, partnership, or a family member's account.
Form 4
The SEC filing required under Section 16 of the Securities Exchange Act of 1934. Corporate insiders — directors, officers, and shareholders owning more than 10% of a company — must file Form 4 within two business days of any change in their beneficial ownership of company securities. Form4API parses every Form 4 filed with the SEC and exposes the data via this API.
Insider
For SEC reporting purposes, an insider is any director, officer, or 10%-or-greater shareholder of a public company. These individuals have a heightened duty to disclose their trades because they may have access to material non-public information. Insider trading data is public — only the trades of these registered insiders are reported on Form 4.
Period of Report
The date field on a Form 4 indicating when the reported transaction occurred. This is usually identical to transactionDate but can differ for transactions that are grouped or reported after a delay. When the two dates differ, periodOfReport reflects the filing's stated coverage date.
Section 16
Section 16 of the Securities Exchange Act requires insiders to report their ownership and any changes to it. Section 16(a) mandates the Form 4 filings this API is built on. Section 16(b) requires insiders to disgorge any "short-swing profits" — gains from buying and selling the same stock within a six-month window.
Transaction Code
A single letter on Form 4 indicating the nature of the transaction. The most common codes are: P (open-market purchase), S (open-market sale), A (grant or award), M (exercise or conversion of derivative), F (shares withheld to cover tax on vest/exercise), D (disposition to the issuer). Less common but valid codes include: C (conversion of derivative), J (other acquisition or disposition), G (gift), X (in-the-money derivative exercise), O (out-of-the-money derivative exercise), E (expiration of long derivative), H (expiration of short derivative), I (discretionary transaction), L (small acquisition), U (tender offer disposition), W (acquisition by will or descent), Z (voting trust deposit/withdrawal), V (voluntary exempted disposition), K (equity swap), B (automatic sell to cover taxes), T (Rule 10b5-1 plan transaction).

// background reading