Skip to main content
NOTE: This is the documentation for the websocket channel sec:insider_trades. Websocket access for personal use is only available through the Advanced plan. You can find fully-functional examples that stream data from many channels here: Connect to the websocket URI: wss://api.unusualwhales.com/socket?token=<YOUR_API_TOKEN> then join the sec:insider_trades channel. Each message carries insider transactions reported on SEC forms 3, 4, 5 and 144, and on their amendments, in aggregated form. A filing lists its transactions as rows. The rows that one reporting person files for one ticker with the same filing date and transaction date are aggregated into one message when they also share the form type, security title, security_ad_code, transaction_code, direction (acquired or disposed), and the officer title and role flags of the reporting person. Rows of different kinds therefore arrive as several messages. Three kinds of rows are left out: rows with an amount of zero, rows where the reporting person disclaims ownership, and rows of a filing that a later filing amended. For the individual rows, call /insider/transactions with group=false. The ids field lists the rows a message aggregates.

Delivery characteristics

  • Updates are event driven. The channel stays silent until an insider trade filing is processed. There is no heartbeat and no fixed schedule.
  • A message can be sent again. The aggregates of a reporting person for one ticker, filing date and transaction date are rebuilt together, and each rebuild sends them again. A newer message replaces every earlier one that shares an entry of ids.
  • The share counts can disagree with amount. For a message that aggregates several rows, shares_owned_before and shares_owned_after can come from different rows, so shares_owned_before + amount can differ from shares_owned_after.
  • Form 144 messages carry fewer values. Their security_ad_code, security_title and director_indirect are empty strings, and their shares_owned_before and shares_owned_after are 0. A form 144 aggregate is not sent when a form 4 aggregate exists for the same ticker, reporting person, transaction date, amount and transaction_code.
  • The channel sends nothing when you join. Messages sent while you are disconnected are not replayed.
  • The channel is global only. It covers every ticker at once. A join on sec:insider_trades:<TICKER> is answered with an {"error": "..."} frame.
Payload format:

Field reference

Every field is present in every message. A value the filing does not provide is sent as an empty string, 0 or false, never as null. A 0 can therefore mean either zero or not reported. Dates are strings in YYYY-MM-DD format. For director_indirect, natureofownership, date_excercisable, price_excercisable and expiration_date, a message that aggregates several rows carries the highest value among them. For text that is the last value in alphabetical order. The names natureofownership, date_excercisable and price_excercisable are spelled as shown.
The payload has the fields of the Kafka message InsiderTradeAgg, published to the topic sec-filings under the key insider_trade_agg.
Last modified on October 1, 2026