Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.kalshi.com/llms.txt

Use this file to discover all available pages before exploring further.

API Key Setup

FIX API keys use the same RSA key pair as the REST API. Generate a 2048-bit RSA key pair and register the public key in your account profile. The resulting API Key ID (UUID) is your SenderCompID.
openssl genpkey -algorithm RSA -pkeyopt rsa_keygen_bits:2048 -out kalshi-fix.key
openssl rsa -in kalshi-fix.key -pubout -out kalshi-fix.pub

Logon (35=A)

The initiator sends a Logon message. The acceptor responds with either a Logon (success) or Logout (failure).

Required Fields

TagNameDescriptionValue
98EncryptMethodMethod of encryptionNone<0>
96RawDataClient logon message signatureBase64 encoded signature
108HeartbeatIntHeartbeat interval (seconds)N > 3
1137DefaultApplVerIDDefault application versionFIX50SP2<9>

Optional Fields

TagNameDescriptionDefault
141ResetSeqNumFlagReset sequence numbers on logon. Must be Y for KalshiNR, KalshiDC, KalshiPT.N
8013CancelOrdersOnDisconnectCancel orders on any disconnection (including graceful logout)N
20126ListenerSessionListen-only session. KalshiNR/RT only, requires SkipPendingExecReports=Y.N
20127ReceiveSettlementReportsReceive settlement reports. KalshiRT only.N
20200MessageRetentionPeriodHow long session messages will be stored for retransmission, max of 72 hours. KalshiRT and KalshiRFQ only.24
21005UseDollarsEnable dollar-based price format for prices, including subpenny precisionN
21011SkipPendingExecReportsSkip PENDING_{NEW|REPLACE|CANCEL} execution reportsN
21012UseExpiredOrdStatusEmit Expired<C> (150/39) for expiry-style system cancellations (CloseCancel and OrderExpiryCancel) instead of Canceled<4>N
21007EnableIocCancelReportPartially filled IOC orders produce a cancel reportN
21008PreserveOriginalOrderQtyOrderQty tag 38 always reflects original order quantity across all statesN

Signature Generation

The RawData field must contain a PSS RSA signature of the pre-hash string:
PreHashString = SendingTime + SOH + MsgType + SOH + MsgSeqNum + SOH + SenderCompID + SOH + TargetCompID
SendingTime in SignatureThe SendingTime in the PreHashString must match exactly the value in field 52 of the Logon message. Format: YYYYMMDD-HH:MM:SS.mmm.SendingTime must be within 30 seconds of the server’s current time, or the message will be rejected with SessionRejectReason<373>=10.
from base64 import b64encode
from Cryptodome.Signature import pss
from Cryptodome.Hash import SHA256
from Cryptodome.PublicKey import RSA

private_key = RSA.import_key(open('kalshi-fix.key').read().encode('utf-8'))

sending_time = "20230809-05:28:18.035"
msg_type = "A"
msg_seq_num = "1"
sender_comp_id = "your-fix-api-key-uuid"
target_comp_id = "Kalshi"  # Or appropriate TargetCompID

msg_string = chr(1).join([
    sending_time, msg_type, msg_seq_num,
    sender_comp_id, target_comp_id
])

msg_hash = SHA256.new(msg_string.encode('utf-8'))
signature = pss.new(private_key).sign(msg_hash)
raw_data_value = b64encode(signature).decode('utf-8')

Heartbeat & Sequence Numbers

BehaviorDetail
Default heartbeat interval30 seconds
Missed heartbeatConnection terminates if heartbeat response not received within interval
Sequence number lower than expectedConnection terminated
Sequence number higher than expectedRecoverable with ResendRequest (KalshiRT only)

Message Retransmission

Message retransmission (ResendRequest, SequenceReset) is only supported on KalshiRT and KalshiRFQ.
For all other sessions, ResetSeqNumFlag<141> in the Logon message must always be Y or the Logon will be rejected.
The drop copy session provides an alternative way to query for missed execution reports. For a real-time streaming feed, see Listener Sessions.

ResendRequest (35=2)

KalshiRT only. Lookback window limited to 24 hours (or up to 72 hours if MessageRetentionPeriod was set on Logon).
TagNameDescription
7BeginSeqNoLower bound (inclusive)
16EndSeqNoUpper bound (inclusive)

Logout (35=5)

Either side may initiate a Logout. The counterparty responds with a Logout, and the transport connection is terminated. If CancelOrdersOnDisconnect=Y was set on Logon, all open orders are canceled.