SEC Form 4 Insider Trades by Ticker: Shares, Price, Holdings
Pricing
from $2.10 / 1,000 insider transaction rows
SEC Form 4 Insider Trades by Ticker: Shares, Price, Holdings
Corporate insider buys and sells parsed out of SEC EDGAR Form 4 filings, one row per transaction: insider name and role, transaction code, date, shares, price per share, dollar value, shares held afterwards, option and RSU detail and Rule 10b5-1 flag. By ticker, issuer CIK or insider CIK.
Pricing
from $2.10 / 1,000 insider transaction rows
Rating
0.0
(0)
Developer
Samat Makatov
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
4 days ago
Last modified
Categories
Share
Corporate insider buys and sells parsed out of SEC EDGAR Form 4 filings, one row per transaction: insider name and role, transaction code, date, shares, price per share, dollar value, shares held afterwards, option and RSU detail and Rule 10b5-1 flag. By ticker, issuer CIK or insider CIK.
A Form 4 is the report an officer, director or 10% holder of a US-listed company must file within two business days of buying or selling that company's stock. This actor reads those filings straight from the SEC's own EDGAR system — the full-text search index finds the submissions, and each submission's ownership XML is parsed into rows — so one row is one reported line: who traded, on what date, under which transaction code, how many shares, at what price, and how many shares they held afterwards. No API key, no account, no proxy and no browser; dates are UTC, and numbers come out as numbers.
Need it tailored to your workflow? Missing a field, a filter, another source or a different output format? Open an issue and describe what you need — we read every request and adapt the actor.
Use cases
- Insider-buying screen across the whole market: run
mode: "market"withtransactionCodes: ["P"]for a month and get every open-market purchase anybody filed — the only Form 4 line that is a cash decision rather than compensation. - Watchlist monitoring on a schedule:
sinceHours: 24plusonlyNew: trueon a daily schedule turns the actor into an insider-trade feed that never repeats a transaction it has already delivered. - One company's insider history:
mode: "issuer"with a ticker and a date window gives every officer, director and 10% holder who traded that stock, with the filing link next to each row. - Follow one person or fund across companies:
mode: "insider"with a reporting-owner CIK returns that filer's trades at every issuer they report for — board members of several companies, family trusts, venture funds. - Compensation research:
transactionCodes: ["A", "M", "F"]withincludeDerivative: truereturns awards, option and RSU exercises and the shares handed back for tax, including the derivative table with strike price, underlying security and expiry. - Only the trades that matter:
minTransactionValueUsd: 1000000drops the routine award and tax-withholding lines, so a watchlist of twenty names returns a handful of rows instead of hundreds. - Answering an agent's question: "did anyone at NVDA buy recently?" is one small JSON input, and
fieldscuts the payload to the four columns the agent needs.
Input
No field is required. issuer mode needs at least one entry in tickers, insider mode at least one entry in insiderCiks; market mode needs neither. The input form is prefilled with a working issuer example (NVDA and AAPL over nine months) — those are prefill values, not defaults, so an empty field stays empty.
| Field | Type | Default | Allowed values / notes |
|---|---|---|---|
mode | string (enum) | issuer | issuer, insider or market — see Modes. Strict: the platform refuses any other value before the run starts. |
tickers | string[] | empty | issuer mode, at most 25 per run. Exchange symbols (NVDA, BRK-B or BRK.B) or CIK numbers with or without leading zeros (1045810, 0001045810). See Company symbols. |
insiderCiks | string[] | empty | insider mode, at most 25 per run. EDGAR CIK numbers only — see Finding a reporting-owner CIK. |
since | string | empty | Earliest filing date, YYYY-MM-DD (UTC). Empty together with until = the last 90 days. |
until | string | empty | Latest filing date, YYYY-MM-DD (UTC), that day included. Empty = today. |
sinceHours | number | empty | 1–8760. A moving window for schedules; while it is set it replaces since. |
onlyNew | boolean | false | Remember delivered transactions between runs and write only unseen ones, keyed by accession number plus the position of the line inside the filing. The memory itself is kept per mode and per company/insider list, so two watchlists do not shadow each other and the same watchlist in two tasks shares one memory. |
transactionCodes | string[] | empty (every code) | One-letter SEC codes, or plain words like buy, sell, grant, exercise. See Transaction codes. |
includeDerivative | boolean | true | Keep the option, RSU and warrant table as well, marked isDerivative: true. |
includeHoldings | boolean | false | Also write the lines that restate a position without a trade, as rowType: "holding". |
includeAmendments | boolean | true | Keep amended filings (4/A). Every row says which it came from in formType and isAmendment. |
minTransactionValueUsd | number | empty | Keep only lines worth at least this much (shares × pricePerShare as reported). A price filed as 0 makes the value 0, and a line filed without a price has no value at all — any floor above zero drops both. |
maxFilingsPerEntity | number | 25 | 1–500, newest first. The per-company or per-insider cap; one filing is one request. In market mode there is no entity: the run keeps reading filings until maxItems rows are found, its own submission budget is used up (it grows with maxItems, at most 1,500 per run) or its time budget runs out — the status message says which. |
maxItems | number | 50 | 1–2000. Hard cap on the rows this run writes, and therefore on what it costs. |
fields | string[] | empty (all) | Keep only these columns, in this order. rowType, ticker, issuerName, insiderName, transactionDate, transactionCode, shares, url and fetchedAt are always kept — they come first unless you list them, and a column you do list stays where you put it. Unknown names are reported in the status message. |
Reference
Modes
mode | Question it answers | What the run does |
|---|---|---|
issuer | Who traded inside the companies I name? | Searches Form 4 submissions by issuer CIK, resolved from your tickers. |
insider | Where did this person or fund trade? | Searches by reporting-owner CIK, so one filer is followed across every issuer. |
market | Everything filed in this window | No company filter at all; with transactionCodes: ["P"] this is the open-market-buying screen. |
An off-list value never reaches the run: mode is an enum, so the platform refuses anything but issuer, insider or market with HTTP 400 before the run starts.
Transaction codes
transactionCodes is free text, so case and spaces do not matter and the plain words in the last column are accepted too. Anything else is refused with the closest codes named in the error — a near miss is never silently swapped for another code. Leave the list empty to keep every code.
| Code | Meaning | Also accepted as |
|---|---|---|
P | Open-market or private purchase — cash out of the insider's pocket | buy, buys, purchase, bought |
S | Open-market or private sale | sell, sells, sale, sold |
A | Grant, award or other acquisition from the issuer | grant, award, rsu |
M | Exercise or conversion of a derivative security held | exercise |
F | Shares handed to the issuer to pay tax or an exercise price | tax, withholding |
D | Disposition back to the issuer | disposition |
G | Bona fide gift | gift |
C | Conversion of a derivative security | conversion |
X | Exercise of an in-the-money or at-the-money derivative security | — |
O | Exercise of an out-of-the-money derivative security | — |
E | Expiration of a short derivative position | — |
H | Expiration or cancellation of a long derivative position | — |
L | Small acquisition under Rule 16a-6 | — |
W | Acquisition or disposition by will or the laws of descent | — |
Z | Deposit into or withdrawal from a voting trust | — |
I | Discretionary transaction inside an employee plan | — |
J | Other acquisition or disposition | other |
K | Transaction in an equity swap or similar instrument | — |
U | Disposition in a tender of shares in a change-of-control transaction | — |
Screening tip: P and S are decisions about the stock. A and F are routine compensation and tax withholding, and they make up most Form 4 lines.
Company symbols
tickers is free text matched against the SEC's own ticker-to-CIK file (10,434 symbols on 2026-10-06). Accepted: any case (nvda), surrounding spaces, and both house styles of a class suffix (BRK-B and BRK.B mean the same company). A symbol the SEC file does not know is refused with the closest known symbols named in the error, never swapped for another company — so NVDAA fails with did you mean "NVDA"? instead of returning a different issuer. Funds, foreign private issuers, holding vehicles and insiders themselves often have no ticker at all: give their CIK number in the same field instead (any value made only of digits is read as a CIK).
Direct and indirect ownership
ownershipType is direct when the shares are held in the insider's own name, and indirect when they are held through a trust, a partnership, a fund or a family member; in that case natureOfOwnership carries the filer's own words ("By Trust", "By 401(k) Plan"). The two are reported as separate lines, so one filing often holds both.
Relationship flags
Every row carries the reporting owner's relationship to the company exactly as the filing states it: isDirector, isOfficer, isTenPercentOwner, isOther, with the officer's own job title in officerTitle and a readable join of the flags in insiderRole ("Director, Officer"). A filer may hold several of them at once.
Finding a reporting-owner CIK
A reporting owner — a person, a trust, a fund — has its own EDGAR CIK, and that number is what identifies them across every company they file for. Run issuer mode for a company you care about and read the insiderCik column of the rows; then put that number into insiderCiks with mode: "insider". Names are not accepted there on purpose: two officers can share a name, and the wrong CIK is the wrong person.
Examples
One ticker, one quarter — the core job
{ "mode": "issuer", "tickers": ["NVDA"], "since": "2026-01-01", "until": "2026-09-30", "maxFilingsPerEntity": 10, "maxItems": 20 }
Every officer, director and 10% holder who traded NVDA in the window, with shares, price, dollar value and holdings afterwards.
Insider buying across the whole market
{ "mode": "market", "transactionCodes": ["P"], "since": "2026-09-01", "until": "2026-09-30", "includeDerivative": false, "maxItems": 20 }
Only code P — insiders who paid cash for stock anywhere in the US market that month. Grants and tax withholding are left out.
Executive sales across a peer group, with only the columns you need
{ "mode": "issuer", "tickers": ["AAPL", "MSFT"], "transactionCodes": ["S"], "includeDerivative": false, "since": "2026-01-01", "until": "2026-09-30", "maxFilingsPerEntity": 15, "maxItems": 20,"fields": ["insiderName", "transactionDate", "shares", "pricePerShare", "transactionValueUsd"] }
Share sales side by side for two companies. The always-kept columns come first, then your five in exactly that order.
Option exercises and RSU grants, derivative table included
{ "mode": "issuer", "tickers": ["MSFT", "ORCL"], "transactionCodes": ["M", "A"], "includeDerivative": true, "since": "2026-01-01", "until": "2026-09-30", "maxItems": 20 }
The compensation side: strikePrice, exerciseDate, expirationDate, underlyingSecurityTitle and underlyingShares are filled on the derivative rows.
Follow one insider across every company
{ "mode": "insider", "insiderCiks": ["0001696841"], "since": "2026-01-01", "until": "2026-09-30", "maxItems": 20 }
Every Form 4 that reporting owner filed, whichever issuer it was for.
Only million-dollar sales
{ "mode": "issuer", "tickers": ["NVDA", "META", "AVGO"], "transactionCodes": ["S"], "minTransactionValueUsd": 1000000, "includeDerivative": false, "since": "2026-01-01", "until": "2026-09-30", "maxItems": 20 }
Value is shares × the price in the filing, so the small routine lines disappear.
A daily feed that never repeats itself
{ "mode": "market", "sinceHours": 24, "onlyNew": true, "includeDerivative": false, "maxItems": 200 }
Put this on a schedule: every run writes only transactions no earlier run with the same mode and the same company or insider list has delivered.
Output
One row per reported line of a Form 4. A real row from a cloud run (footnotes shortened here):
{"rowType": "transaction","ticker": "NVDA","issuerName": "NVIDIA CORP","issuerCik": "0001045810","insiderName": "Teter Timothy S.","insiderCik": "0001696841","insiderRole": "Officer","officerTitle": "EVP, General Counsel and Sec","isDirector": false,"isOfficer": true,"isTenPercentOwner": false,"isOther": false,"coFilers": [],"securityTitle": "Common Stock","transactionDate": "2026-09-21","transactionCode": "S","transactionCodeLabel": "Open-market or private sale","acquiredDisposed": "D","direction": "sell","shares": 12483,"pricePerShare": 222.1932,"transactionValueUsd": 2773637.72,"sharesOwnedAfter": 2705637,"ownershipType": "indirect","natureOfOwnership": "By Trust","isDerivative": false,"strikePrice": null,"exerciseDate": null,"expirationDate": null,"underlyingSecurityTitle": null,"underlyingShares": null,"formType": "4","isAmendment": false,"periodOfReport": "2026-09-21","filedAt": "2026-09-23","rule10b51Plan": true,"equitySwapInvolved": false,"footnotes": ["The reported transaction was effected pursuant to a Rule 10b5-1 trading plan adopted by the Reporting Person on May 22, 2026.", "Represents weighted average sales price. The shares were sold at prices ranging from $221.59 to $222.58. …"],"remarks": null,"accessionNumber": "0001696841-26-000014","lineIndex": 0,"url": "https://www.sec.gov/Archives/edgar/data/1045810/000169684126000014/0001696841-26-000014-index.htm","xmlUrl": "https://www.sec.gov/Archives/edgar/data/1045810/000169684126000014/wk-form4_1790196985.xml","fetchedAt": "2026-10-06T23:05:44.918Z"}
| Field | Type | Meaning |
|---|---|---|
rowType | string | transaction (a reported trade) or holding (a restated position, off by default) |
ticker | string | Trading symbol as the filing itself states it; empty for issuers without one |
issuerName, issuerCik | string | The company and its EDGAR CIK |
insiderName, insiderCik | string | The reporting owner and their EDGAR CIK — the number to use in insiderCiks |
insiderRole | string | Readable join of the relationship flags, e.g. Director, Officer |
officerTitle | string | The officer's job title as filed |
isDirector, isOfficer, isTenPercentOwner, isOther | boolean | The relationship the filing reports |
coFilers | object[] | The other reporting owners when several filed one Form 4 together (name, cik); empty otherwise |
securityTitle | string | What was traded, e.g. Common Stock, Restricted Stock Unit |
transactionDate | string | Trade date, YYYY-MM-DD (UTC); empty on a holding line |
transactionCode | string | The SEC's one-letter code — see Transaction codes |
transactionCodeLabel | string | That code in plain words |
acquiredDisposed | string | A (shares came in) or D (shares went out) |
direction | string | buy for code P, sell for code S, other for every other code |
shares | number | Shares in this line; empty on a holding line, which reports a position instead |
pricePerShare | number | Price as filed — often a weighted average with a footnote; gifts and most awards are filed as 0 or with no price at all |
transactionValueUsd | number | shares × pricePerShare — 0 when the price is filed as 0, empty when the filing reports no price |
sharesOwnedAfter | number | Shares of that security the owner held after the line |
ownershipType | string | direct or indirect |
natureOfOwnership | string | The filer's words for an indirect holding, e.g. By Trust |
isDerivative | boolean | true for a line from the option / RSU / warrant table |
strikePrice | number | Conversion or exercise price (derivative lines) |
exerciseDate, expirationDate | string | Dates from the derivative table; empty when the filer put them in a footnote instead |
underlyingSecurityTitle, underlyingShares | string, number | What the derivative converts into, and how many shares |
formType | string | 4 or 4/A |
isAmendment | boolean | true for a 4/A correction |
periodOfReport | string | Period of report from the filing header |
filedAt | string | Filing date (UTC) — what since / until / sinceHours filter on |
rule10b51Plan | boolean | The filing's aff10b5One flag: the trade was made under a Rule 10b5-1 plan; empty when the filer did not state it |
equitySwapInvolved | boolean | As coded in the filing |
footnotes | string[] | The footnote texts this very line points at |
remarks | string | The filing's remarks block |
accessionNumber | string | EDGAR submission id |
lineIndex | number | Position of this line inside the filing; with accessionNumber it is the row's identity and the onlyNew key |
url | string | The filing page on EDGAR |
xmlUrl | string | The ownership XML this row was parsed from |
fetchedAt | string | When the actor read the filing, ISO 8601 UTC |
Dataset views: Insider transactions (the buy/sell table), Options, RSUs and warrants (the derivative columns), Filing and ownership detail (accession, form, amendment flag, CIKs, 10b5-1, XML link).
Use it from code / agents
curl -X POST "https://api.apify.com/v2/acts/yadroo~sec-form4-insider-trades/run-sync-get-dataset-items?token=$APIFY_TOKEN" \-H "Content-Type: application/json" \-d '{"mode":"issuer","tickers":["NVDA"],"since":"2026-01-01","until":"2026-09-30","maxItems":20}'
import { ApifyClient } from 'apify-client';const client = new ApifyClient({ token: process.env.APIFY_TOKEN });const run = await client.actor('yadroo/sec-form4-insider-trades').call({mode: 'market',transactionCodes: ['P'],sinceHours: 24,maxItems: 100,});const { items } = await client.dataset(run.defaultDatasetId).listItems();
from apify_client import ApifyClientclient = ApifyClient(os.environ["APIFY_TOKEN"])run = client.actor("yadroo/sec-form4-insider-trades").call(run_input={"mode": "insider","insiderCiks": ["0001696841"],"since": "2026-01-01","maxItems": 50,})items = client.dataset(run["defaultDatasetId"]).list_items().items
MCP: add https://mcp.apify.com to Claude / Cursor / any MCP client and call the yadroo/sec-form4-insider-trades tool with the same JSON input. For an agent, fields is the cheap trick: {"mode":"issuer","tickers":["NVDA"],"transactionCodes":["P","S"],"fields":["insiderName","transactionDate","direction","shares","transactionValueUsd"],"maxItems":10} returns rows small enough to put straight into a prompt.
Pricing
Pay per event: $0.001 per run start + $0.003 per dataset row at the free tier. Volume tiers lower the row price automatically: $0.0027 (Bronze), $0.0024 (Silver), $0.0021 (Gold and above); the start event stays the same.
Worked examples at the free tier, start event included:
- 20 rows (one ticker, one quarter): $0.001 + 20 × $0.003 = $0.061
- 50 rows (the prefilled input, two tickers over nine months): $0.001 + 50 × $0.003 = $0.151
- 500 rows (a wide market-wide month): $0.001 + 500 × $0.003 = $1.501
- A run that finds nothing — no Form 4 in the window, or nothing matching your filters: $0.001, the start event alone
Every row written to the dataset is billed, and nothing else is: this actor writes no placeholder or "not found" marker rows, so an empty result costs only the start event. maxItems is the hard ceiling on both rows and cost. If you set Apify's Maximum cost per run, the run stops as soon as the next row would exceed it, keeps every row you have already paid for, and says so in its status message ("Stopped at your spending limit: N rows delivered").
Limits & FAQ
How fast is it? Measured in the Apify cloud on 2026-10-06, run UcHAF4hE16yrwCg6O: 354 requests over 350 submissions in 74 seconds — a sustained 297 requests per minute (4.95 per second), no throttling, 500 rows delivered, so about 420 rows a minute market-wide. One search page covers up to 100 submissions and every submission is then one request, which is why the row rate depends on your filters: the prefilled two-ticker watchlist returns 50 rows in 10 seconds, while the market-wide open-market-buying screen manages about 60 rows a minute, because only about one Form 4 line in fourteen is a code-P purchase (20 rows out of 86 submissions read, measured the same day). The widest input the schema allows — 2,000 rows market-wide — reads at most 1,500 submissions, roughly five minutes of requests, and so fits the 900-second default run timeout. With a narrow code or value filter a market-wide run usually uses up that submission budget before the row cap; its status message then says how many rows it saved and that a narrower time window goes further.
The SEC's rate limit. sec.gov's fair-access policy allows an automated client no more than 10 requests per second across all its machines and throttles the address temporarily above that; the block clears about ten minutes after the traffic drops. This actor paces itself with a single token bucket at 5 requests per second — half the ceiling — across every sec.gov host, retries included, and it sends the descriptive User-Agent the SEC asks for. If the address it runs on is throttled anyway, the run ends with a clear message asking you to start again in a few minutes rather than hammering the source.
Does a run ever stop early? Yes, and it says so. The run stops before its own timeout, keeps everything read so far and ends successfully with "Stopped before the run timeout: N rows saved"; the same happens at your maximum cost per run. To continue, narrow until to the day before the oldest row you got.
How far back does it go? Electronic Form 4 filing became mandatory at the end of June 2003, so mid-2003 to today is the honest range; a window ending before that returns nothing and the status says so. EDGAR's full-text search also answers at most 10,000 hits per query — a market-wide year has far more than that, so slice wide windows by month or quarter. The status message tells you when a run hit that cap.
since / until filter the filing date, not the trade date. An insider has two business days to report, so a window that ends on a Friday usually still misses that week's last trades, and transactionDate is normally 0–2 business days behind filedAt.
Amendments. forms=4 on EDGAR matches the root form, so amendments (4/A) arrive together with first reports and includeAmendments: true keeps them. An amendment carries the numbers that now stand, and the original filing stays in the data too — a correction never silently overwrites history. Each row says which it was in formType and isAmendment.
Prices and share counts are the filer's own. pricePerShare is frequently a weighted average with a footnote explaining the price range. Gifts and most awards have no real price, and filers report that in two ways: a price of 0 — then transactionValueUsd is 0 as well — or an empty price, and then the row carries no transactionValueUsd at all. Both kinds disappear under any minTransactionValueUsd floor above zero, the 0 rows because their value is below it and the priceless rows because they have no value to compare. Nothing is restated, split-adjusted or recalculated here: you get the numbers as filed, plus shares × pricePerShare.
One filing can be one row or fifteen. A Form 4 may report several lines, and when several owners file one form together (a fund and its managers) it stays one row per line, with the other filers in coFilers. Holding lines — positions restated without a trade — are off by default because they answer a different question; switch on includeHoldings to get them as rowType: "holding".
What about personal data? Form 4 exists to publish the insider's name, role and share count, and those are the fields returned. The ownership XML also carries the filer's mailing address block: it is deliberately not read, not emitted and not in any dataset view. No e-mail addresses, no phone numbers.
Empty result or error? An unusable input fails immediately with a message naming what to change (an unknown ticker with the closest known symbol, a CIK where a name was typed, a reversed date window). A valid input that simply has no filings, or none matching your filters, succeeds with zero rows and a status message explaining which it was.
Questions or problems: open an issue on the Issues tab of this actor.
Made by Yadroo. Sibling actors: sec-edgar-filings (the filing list this one starts from), sec-company-financials (XBRL facts per company), federal-register-documents, cisa-kev-vulnerabilities, openfda-records.