.NET SDK reference

Every public member of HFTFeed.Client 1.1.2, the threads your callbacks run on, errors, server logout reasons, limits and troubleshooting.

This page describes version 1.1.2 of HFTFeed.Client. For a step-by-step introduction, start with Connect with the .NET SDK.

Package

ItemValue
Package idHFTFeed.Client
Version1.1.2
Target frameworksnet10.0 and net8.0 (usable from .NET 8 and later; .NET 9 uses the net8.0 build)
DependenciesNone
NamespaceHFTFeed.Client
Public typesHFTFeedClient, HFTFeedSymbol, Md, ConnectionStatus, HFTFeedException, HFTFeedAuthException, HFTFeedLogoutException, HFTFeedThrottledException, HFTFeedTimeoutException

The assembly also contains public types in the HFTfeed.Fix2.Codec namespace. They are internal building blocks of the SDK, not part of its supported API, and can change in any release.

HFTFeedClient

public sealed class HFTFeedClient : IDisposable

Constructors

ConstructorEndpoint
HFTFeedClient(string email, string password)fix-server.hftfeed.com, port 9030
HFTFeedClient(string email, string password, bool useAlternatePort)Port 9031 when useAlternatePort is true, otherwise 9030
HFTFeedClient(string email, string password, string host, int port)The host and port you pass

email and password are your hftfeed.com login. The constructors throw ArgumentNullException when email or password is null, or host is null or blank. Nothing connects until you call Start.

The default endpoint is also available as constants: HFTFeedClient.DefaultHost ("fix-server.hftfeed.com", a name since 1.1.2 — 1.1.0 and 1.1.1 held an address), HFTFeedClient.DefaultPort (9030) and HFTFeedClient.AlternatePort (9031). The host is resolved on every connect, so the machine needs DNS, and a move of the feed to another address needs no new SDK.

Methods

MethodWhat it does
void Start()Signs in over HTTPS, connects, logs on and loads the symbol list. Blocks until all of that is done, or throws. Throws HFTFeedThrottledException without connecting when no connection attempt is left.
Task StartAsync(CancellationToken cancellationToken = default)The same, asynchronously.
void Start(string clientId), Task StartAsync(string clientId, CancellationToken cancellationToken = default)Connects with the SenderCompID you pass (the Quote Sender Comp ID on your Connection page) and skips the HTTPS sign-in. The server still checks your email, password and plan, and that the SenderCompID belongs to your account. Throws ArgumentNullException for a null or empty clientId.
void Stop()Sends a FIX Logout, closes the connection, sets DISCONNECTED, stops automatic reconnects and clears the subscription list. Safe to call more than once, and before Start.
Task StopAsync()Runs Stop() on a thread-pool thread.
void Dispose()Calls Stop() and marks the client as disposed. Starting a disposed client throws ObjectDisposedException.
HFTFeedSymbol[] GetSymbols()The symbol list from the last logon. Empty before the first successful Start.
void Subscribe(string symbolKey)Starts streaming one symbol.
void Unsubscribe(string symbolKey)Stops streaming one symbol. Does nothing for null.
void SubscribeAll()Subscribes, in one request, to every symbol from GetSymbols() that isn't subscribed yet.
void UnsubscribeAll()Cancels every subscription in one request.
void RequestSnapshot(string symbolKey)Asks for one tick with the latest price, delivered on OnNewTick. Does not subscribe.

Don't call Start on a client that is already connected, and don't call Start, Stop or Dispose from inside a callback.

Properties

PropertyTypeDescription
ConnectionStatusConnectionStatusCONNECTED or DISCONNECTED. Read-only.
Connected, IsConnectedbooltrue while the status is CONNECTED.
AutoReconnectboolReconnect after an unexpected drop. Default false. See Automatic reconnect.
HeartbeatSecondsintFIX heartbeat interval sent at logon. Default 30. Set it before Start; the server accepts 5 to 60.
ReuseTickObjectboolPass the same Md instance to every OnNewTick call. Default false. See Receiving without allocations.
BusyPollMicrosecondsintNew in 1.1.1. Opt-in low-latency receive: how many microseconds the receive thread keeps checking the socket after it runs dry, before it waits in the kernel. Keeps one CPU core busy while the feed is active. Default 0 (off). Set it before Start; typical values 1,000 to 50,000. Negative values throw ArgumentOutOfRangeException. See Performance and latency.
ReceiveBufferSizeintNew in 1.1.1. Kernel receive buffer (SO_RCVBUF) of the feed connection, in bytes. Default 0 keeps the operating system's default. Set it before Start. Negative values throw ArgumentOutOfRangeException.
TPSlongTicks received in the last second.
TPMlongTicks received in the last minute.
SubscribedSymbolsCountintNumber of symbols the client considers subscribed.
Host, Portstring, intThe endpoint this client connects to.
ClientIdstringThe SenderCompID in use. Empty until Start.

Events

The events are properties of delegate type. Assign a handler with =, or combine handlers with += and -=.

EventArgumentRaised whenThread
OnNewTickMdA tick arrives.The receive thread.
OnConnectionStatusConnectionStatusThe status changes.CONNECTED: the thread that finished connecting (a thread-pool thread, or the reconnect thread). DISCONNECTED: the receive thread, or the thread that called Stop.
OnSubscribestringA subscribe method ran. See Notices.The thread that called the method; the reconnect thread for Resubscribed.
OnUnsubscribestringAn unsubscribe method ran.The thread that called the method.
OnErrorExceptionThe client hit a problem it handled itself. See Reported on OnError.Whichever thread hit it.
OnFixMsgstringAny FIX message is received or sent. Diagnostics only.The receive thread for incoming messages; the sending thread for outgoing ones.

Connection lifecycle

What Start does

StepTime limitWhen it fails
1. Sign in over HTTPS to identitytoolkit.googleapis.com and read the account's SenderCompID and plan. Skipped by Start(clientId).20 sHFTFeedAuthException; OperationCanceledException on timeout
2. Reserve one of the connections allowed for Host (given back if the connection is not established), then open a TCP connection to Host:Port.10 sHFTFeedThrottledException when no attempt is left (nothing is sent); HFTFeedTimeoutException (Could not connect to …); SocketException when the connection is refused or the network is unreachable
3. Send the FIX Logon and wait for the answer.10 sHFTFeedLogoutException with the server's reason; HFTFeedTimeoutException (Logon did not complete …); HFTFeedException (… closed the connection before the Logon completed …) when the server closes the connection
4. Request the symbol list and wait for it.10 sHFTFeedTimeoutException (SecurityList did not complete …); HFTFeedException when the server closes the connection

Start() also checks for a free connection attempt before step 1, so a refused call doesn't sign in either. Then the status becomes CONNECTED and OnConnectionStatus fires. A Logout received during these steps is also passed to OnError. A Start that throws has already closed its connection and never starts automatic reconnects; you can call Start again. Stop() from another thread ends a Start in progress, which then throws OperationCanceledException.

Stop and Dispose

Stop() sends a Logout if the connection is open, closes the socket without waiting for the server's reply, sets DISCONNECTED, cancels automatic reconnects (including an attempt or a wait in progress) and clears the list of subscribed symbols. Dispose() calls Stop(); it never throws and is safe to call more than once.

Connecting again after Stop

A stopped client can be started again with Start; a disposed one can't. SubscribedSymbolsCount is 0 after Stop(), and the next Start subscribes to nothing, so call Subscribe or SubscribeAll again once Start has returned. The symbol list is loaded again at every logon.

Automatic reconnect

With AutoReconnect = true, the client reconnects when the connection closes unexpectedly: a network failure, a server restart, a heartbeat timeout or any other disconnect that came without a Logout. It waits a random time before each attempt:

AttemptWait before the attempt
11 to 2 s
22 to 4 s
34 to 8 s
48 to 16 s
5 and later15 to 30 s

After that wait, an attempt also waits until the connection limit allows another connection.

Each attempt repeats steps 2 to 4 of Start with the SenderCompID from your first Start; it does not repeat the HTTPS sign-in, but the server checks your login and plan on every logon. After a successful attempt the client raises OnConnectionStatus(CONNECTED), then subscribes again to every symbol it had subscribed, in one request, and raises OnSubscribe with Resubscribed: <n> symbols. Failed attempts are reported on OnError.

The client stops retrying when an attempt succeeds, when you call Stop() or Dispose() (which also end an attempt or a wait in progress), when you set AutoReconnect to false, or when the server answers an attempt with a Logout. It never reconnects after the server ended a session with a Logout, and it only reconnects sessions that were established: a Start that fails throws instead.

Connection attempts

The server accepts at most 6 new connections per minute from one IP address. A connection over that limit is closed at once without an answer and gives the address a strike. One strike expires every 10 minutes; 3 strikes block the address for 5 minutes, 6 for an hour and 9 for a day, and the server closes every connection from a blocked address the same way.

The SDK therefore opens at most 5 connections per host in any 60 seconds. The count is shared by every HFTFeedClient in the process and covers Start and automatic reconnects alike:

  • A connection counts from the moment the client starts to open it, so clients connecting at the same time can't overshoot.
  • If the TCP connection is not established (connection refused, host unreachable, connect timeout, or cancelled), the attempt never reached the server and no longer counts.
  • An established connection counts for 60 seconds whatever happens next: logon refused, closed by the server, or ended by Stop(). A connection that completes after the client stopped waiting for it (after the 10-second connect timeout) is counted when it completes.
CallerWhen 5 connections are already in the window
Start, StartAsyncThrow HFTFeedThrottledException at once, without connecting. RetryAfter is the time until the next of them is 60 seconds old.
Automatic reconnectWaits until another connection is allowed. Stop() and Dispose() end the wait.

The count is kept per host name exactly as passed to the constructor (ignoring case), not per port: ports 9030 and 9031 share it. It is not shared between processes, and the server counts everything from your IP address, so several programs on one machine or behind one NAT can still go over the server's limit together.

Heartbeats

  • The client sends a Heartbeat when it has sent nothing for HeartbeatSeconds, and answers every TestRequest from the server at once.
  • The server sends a Heartbeat when it has sent nothing for the heartbeat interval. When it has heard nothing from you for 1.2 intervals it sends a TestRequest, and after 2 intervals it closes the connection without a Logout.
  • The server clamps the interval to 5 to 60 seconds, but the client times its own heartbeats from the value you set. Keep HeartbeatSeconds in that range.
  • The client does not time out a silent connection by itself. It notices a drop when the socket closes or a send fails.

Symbols

public class HFTFeedSymbol

PropertyTypeDescription
SymbolKeystringThe server's numeric symbol id, as text. Use it for Subscribe, Unsubscribe and RequestSnapshot. Ticks carry it in Md.Symbol.
SymbolNamestringInstrument name, for example EURUSD.
DigitsdoubleNumber of decimals in the symbol's prices.

ToString() returns "<SymbolKey> <SymbolName> (<Digits>)". The list contains the symbols the server currently publishes. It is loaded at every logon, including automatic reconnects.

Subscriptions

Notices

The subscription methods report their local outcome as text on OnSubscribe or OnUnsubscribe. Only the notices that say Subscribed or Unsubscribed mean a request was sent.

NoticeEventMeaning
Subscribed: <key>OnSubscribeThe subscribe request was sent.
Already subscribed: <key>OnSubscribeThe client already lists this key; nothing was sent.
Wrong symbol key: <key>OnSubscribeThe key is not in the symbol list (you may have passed a name). Also raised by RequestSnapshot. Nothing was sent.
Wrong symbol key: <empty>OnSubscribeThe key was null or empty.
No symbols available yetOnSubscribeSubscribeAll was called before the symbol list arrived.
Already subscribed: 0 new symbolsOnSubscribeSubscribeAll found nothing new to subscribe.
Subscribed: <n> symbolsOnSubscribeSubscribeAll sent its request; n is the total number of subscribed symbols.
Resubscribed: <n> symbolsOnSubscribeSubscriptions were restored after an automatic reconnect.
Unsubscribed: <key>OnUnsubscribeThe unsubscribe request was sent.
Not subscribed: <key>OnUnsubscribeThe client doesn't list this key; nothing was sent.
Unsubscribed: <n> symbolsOnUnsubscribeUnsubscribeAll removed n symbols (0 when there were none).

When the client is not connected, the methods send nothing and OnError receives Not connected: call Start() before subscribing.

Server responses

The server does not confirm a subscription: ticks for the symbol start to arrive. Subscribing to a symbol twice, or unsubscribing from one you don't have, is ignored. A few ticks that were already on their way can still arrive shortly after Unsubscribe. When the server refuses a request, OnError receives an HFTFeedException with the message MarketDataRequest rejected: <reason>:

ReasonMeaning
Unknown symbol <key>The server doesn't publish this symbol (any more).
Too many subscriptionsThe session already has 64 subscriptions.
No data for <key>RequestSnapshot: the server has no price for this symbol yet.

The client still lists a refused symbol as subscribed. To try again, call Unsubscribe(key) and then Subscribe(key).

Request rate

The server accepts at most 50 messages per second from a session, counting everything the client sends. Messages over the limit are refused, and OnError receives Session-level reject: Rate limited; a refused subscribe request still counts as subscribed in the client. If a session goes over the limit in three different seconds within one minute, the server ends it with message rate limit. Use SubscribeAll(), or pace individual Subscribe calls.

Ticks

public class Md

PropertyTypeDescription
SymbolstringSymbol key (not the name).
BiddoubleBest bid, sent with the symbol's Digits decimals.
AskdoubleBest ask, sent with the symbol's Digits decimals.
BidSizedoubleSize at the bid as reported by the upstream source; 0 when not provided.
AskSizedoubleSize at the ask as reported by the upstream source; 0 when not provided.
EntryTimeUtcDateTimeUTC time of the price with millisecond precision: the source's timestamp when available, otherwise the time HFTFeed's server received the price. DateTime.MinValue when absent, or when the date and time lie beyond DateTime.MaxValue.

ToString() returns "<Symbol> <Bid>/<Ask>". Every tick carries both sides of the book for one symbol. Ticks arrive in the order the server sent them. When your application reads slowly, the server merges queued updates for a symbol and sends only the latest price.

Threading model

  • The client reads the network on one background thread per connection and calls OnNewTick on it, one tick at a time. Nothing else is read while a callback runs.
  • A slow OnNewTick backs up the connection. The server then merges queued updates, and if your session's queue stays full for 10 seconds it ends the session with slow consumer.
  • Other callbacks run on the threads listed under Events, so two callbacks can run at the same time. Make your handlers thread-safe.
  • An exception thrown by a callback is caught and passed to OnError; the client keeps running. Exceptions thrown by OnError itself are ignored.
  • The client's public methods can be called from any thread.

Process ticks off the receive thread shows how to hand ticks to a worker.

Receiving without allocations

With ReuseTickObject = true the client's receive path allocates nothing per tick, including while it waits for data; the SDK's own tests check this over 100,000 ticks and on a live connection. The symbol key string comes from the symbol list, so it is not allocated either. With the default false, the only allocation per tick is the new Md. Setting OnFixMsg adds one string per message.

client.ReuseTickObject = true;
client.OnNewTick = tick =>
{
    // The same Md instance is passed for every tick: copy the values you need,
    // and never keep a reference to it or read it from another thread.
    var key = tick.Symbol;
    var bid = tick.Bid;
    var ask = tick.Ask;
    OnQuote(key, bid, ask); // your own method
};

Tick rates

TPS and TPM count the ticks the client received in the last second and the last minute, whether or not OnNewTick is set. Reading them is cheap and safe from any thread:

using var monitor = new Timer(
    _ => Console.WriteLine($"{client.TPS} ticks/s, {client.TPM} ticks/min, {client.SubscribedSymbolsCount} symbols"),
    null, TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(5));

Raw FIX messages

OnFixMsg receives the text of every FIX message the client receives or sends, with the SOH () separators left in place, and a note when an incoming sequence number is not the expected one. It builds a string for every message, so use it only while debugging. The outgoing Logon contains your password in tag 554; mask it before you log anything:

client.OnFixMsg = raw =>
{
    var start = raw.IndexOf("554=", StringComparison.Ordinal);
    if (start >= 0)
    {
        start += 5;
        var end = raw.IndexOf('', start);
        raw = raw[..start] + "***" + (end >= 0 ? raw[end..] : "");
    }
    Console.WriteLine(raw.Replace('', '|'));
};

The FIX protocol reference explains every message you will see.

Exceptions

HFTFeedException derives from Exception. HFTFeedAuthException, HFTFeedLogoutException, HFTFeedThrottledException and HFTFeedTimeoutException derive from HFTFeedException. HFTFeedLogoutException adds:

  • Text: the server's reason (FIX tag 58). The exception's Message is Server logout: followed by Text.
  • IsTooManySessions: true when Text contains too many sessions.

HFTFeedThrottledException (new in 1.1.1) adds RetryAfter, a TimeSpan: how long until the next connection attempt is allowed.

Thrown by Start

Exception and messageCause and what to do
HFTFeedAuthException: Authorization failed: followed by the sign-in service's reasonWrong email or password, a disabled account, too many sign-in attempts, or the sign-in service could not be reached. Check that you can sign in on hftfeed.com with the same login, and that HTTPS to identitytoolkit.googleapis.com is allowed.
HFTFeedAuthException: No active HFTFeed subscription. Renew at https://hftfeed.com.The account has no active plan. Choose one on the pricing page.
HFTFeedAuthException: HFTFeed subscription expired. Renew at https://hftfeed.com.The plan has ended. Renew it on the Subscriptions page.
HFTFeedAuthException: Authorization failed: the account has no senderCompId claim.No SenderCompID has been assigned to the account yet. Contact support if this persists after you have an active plan.
HFTFeedAuthException: Authorization failed: no ID token returned. or … malformed ID token.An unexpected answer from the sign-in service. Try again; contact support if it persists.
HFTFeedLogoutException: Server logout: <reason>The server refused the logon. See Server logout reasons.
HFTFeedTimeoutException: Could not connect to <host>:<port> within 10000 ms.No TCP connection within 10 seconds, usually a firewall. Allow the port, or use port 9031.
HFTFeedTimeoutException: Logon did not complete within 10000 ms against <host>:<port>. or SecurityList did not complete …The server did not answer in time. Try again after a pause.
HFTFeedThrottledException: Connection attempt to <host> not made: the server allows 6 connection attempts per minute per IP address and bans addresses that exceed it, so this SDK allows 5 per 60 s, and this process has used them. Wait <n> s before calling Start again.Your process opened (or is opening) 5 connections to this host in the last 60 seconds. Nothing was sent. Wait RetryAfter, then call Start again. See Connection attempts.
HFTFeedException: <host>:<port> closed the connection before the Logon completed, without a Logout. … (or the SecurityList)The server closed the connection without an answer: your IP address made more than 6 connection attempts in a minute, or is temporarily blocked. Wait a few minutes before you try again.
SocketExceptionThe connection was refused or the network is unreachable.
OperationCanceledException (including TaskCanceledException)Your cancellation token fired, or the HTTPS sign-in took longer than 20 seconds.
ObjectDisposedExceptionThe client was disposed. Create a new one.

Reported on OnError

MessageMeaning
Server logout: <reason> (HFTFeedLogoutException)The server ended the session. See Server logout reasons.
Not connected: call Start() before subscribing.A subscription method was called while disconnected. Nothing was sent.
MarketDataRequest rejected: <reason>The server refused a subscription or snapshot request. See Server responses.
Session-level reject: <reason>The server refused a message, for example Rate limited.
Not connected: no socket.A message could not be sent because the connection had already closed.
Outbound frame did not fit the send buffer; message dropped.A request was too large to send.
Garbled frame from server: …, Receive buffer overflow: …Corrupted data was received and skipped.
SocketException, ObjectDisposedException, HFTFeedTimeoutExceptionThe connection failed, or a reconnect attempt failed.
<host>:<port> closed the connection before the Logon completed …A reconnect attempt was closed by the server without an answer. The client keeps retrying within the connection attempts limit.
Any other exceptionThrown by one of your own callbacks.

Server logout reasons

The server ends or refuses a session with a FIX Logout that carries a reason. The SDK passes it to OnError as an HFTFeedLogoutException (and throws it from Start during logon). It never reconnects automatically after a Logout.

Reason (Text)MeaningWhat to do
Invalid credentials: Authentication failedWrong email or password. Also sent while the account is temporarily locked after repeated failed logons.Fix the login, then wait a few minutes before trying again.
Invalid credentials: senderCompId mismatchThe SenderCompID doesn't belong to this account.Use the Quote Sender Comp ID from the Connection page, or Start() without an argument.
Invalid credentials: no subscriptionThe account has no plan.Choose a plan.
Invalid credentials: subscription expiredThe plan has ended.Renew it.
Invalid credentials: subscription not activeThe plan is not active.Check the Subscriptions page.
Invalid credentials: Authentication timeoutThe server could not verify your login in time.Try again after a short pause.
Invalid credentials: Authentication error (sometimes followed by more detail)The server hit an error while verifying your login.Try again after a short pause; contact support if it persists.
Invalid credentials: Authentication failed: … (with detail)Your login could not be verified.Contact support.
too many sessionsThe account already has a live session, on either port.Stop the other session. See Handle errors.
capacityThe server has reached its connection limit.Try again later.
drainingThe server is not accepting new sessions during maintenance. Existing sessions keep streaming.Try again in a few minutes.
subscription expired, renew at hftfeed.comThe plan ended while you were connected. The server checks this every minute.Renew, then start a new client.
access revokedAccess was removed, or the account was disabled, while you were connected.Contact support.
slow consumerYour application did not read data fast enough for 10 seconds.Make OnNewTick faster, then start a new client.
message rate limitMore than 50 messages per second in three different seconds within one minute.Pace your requests.
MsgSeqNum too lowA message arrived with a sequence number lower than expected.Should not happen with the SDK; contact support.
kicked by adminHFTFeed closed the session.Contact support.
Session disconnectedThe server's reply to your own Logout.Nothing.

Disconnects without a logout

In these cases the connection simply closes and the status changes to DISCONNECTED:

  • a network failure or a server restart;
  • the server heard nothing from the client for two heartbeat intervals;
  • the connection broke the protocol rules on the FIX protocol page;
  • your IP address opened more than 6 connections in a minute, or is temporarily blocked. The server closes such connections at once without an answer, so Start throws HFTFeedException with … closed the connection before the Logon completed …, and a reconnect attempt reports the same on OnError.

AutoReconnect applies only to a session that was established. The first case is the one it is for; the SDK's connection attempts limit keeps its own retries below the server's limit.

Limits

LimitValueWhen exceeded
Live sessions per account1, across both portsLogout too many sessions
Subscriptions per session64MarketDataRequest rejected: Too many subscriptions
Messages you send per second50Session-level reject: Rate limited; Logout message rate limit after three such seconds within a minute
New connections per IP address6 per minuteConnection closed without an answer, and a strike; 3, 6 or 9 strikes block the address for 5 minutes, an hour or a day, and one strike expires every 10 minutes
Connections the SDK opens per host5 in any 60 seconds, per process; refused or unanswered attempts don't countStart throws HFTFeedThrottledException; automatic reconnects wait
Failed logonsA few in a short time; 10 per hourAccount and IP address blocked for 5 minutes, longer if failures continue; 10 failures in an hour lock the account for 15 minutes
Heartbeat interval5 to 60 secondsClamped by the server
Silence before the server disconnects2 heartbeat intervalsConnection closed without a Logout
Slow readingQueue full for 10 secondsLogout slow consumer

HFTFeed may adjust these limits. When you reach one, the reason in the error or Logout tells you which.

Performance and latency

  • Run close to the server. The feed server is in the LD4 data center near London, and network distance adds more delay than anything in your process.
  • Keep OnNewTick fast. The client reads the next message only after your callback returns. Copy the values and hand them to a worker.
  • Avoid garbage. Set ReuseTickObject = true and copy values into structs, so the receive path creates no objects per tick and the garbage collector has less to do.
  • Leave OnFixMsg unset in production; it creates a string for every message.
  • Resolve symbols once. Build your key-to-symbol lookup after Start() instead of searching GetSymbols() per tick.
  • Subscribe only to what you use. Every extra symbol is extra data to read and handle.
  • TCP is set up for you. The client disables Nagle's algorithm, so requests leave immediately. On Linux and macOS the receive thread waits for data in a plain blocking receive, without allocating.
  • Busy polling, if you have a core to spare. With BusyPollMicroseconds greater than 0, the receive thread keeps checking the socket for that many microseconds after it runs dry before it waits in the kernel, so a tick that arrives in that window is read without a thread wake-up. While the feed is active this keeps one CPU core busy. Typical values are 1,000 to 50,000; set it before Start.
  • A larger receive buffer for bursts. ReceiveBufferSize sets the kernel receive buffer before connecting. It absorbs longer bursts while your OnNewTick handler is occasionally slow; it does not lower latency.
  • Warm up before you measure. .NET compiles code the first time it runs, so the first ticks after start take longer to handle. Measure after a warm-up period, with a Release build.
  • Synchronize your clock (NTP or PTP) before you compare EntryTimeUtc with local time.

Troubleshooting

SymptomLikely causeFix
Could not connect to fix-server.hftfeed.com:9030 … or a SocketExceptionA firewall or proxy blocks the port, or the name does not resolve.Allow DNS and outbound TCP to port 9030, or use port 9031 (useAlternatePort: true).
Authorization failed: …Wrong login, an account created with Google sign-in that has no password, or no HTTPS access to identitytoolkit.googleapis.com.Check that you can sign in on hftfeed.com with email and password; add a password under Settings → Profile → Authentication if needed; allow the HTTPS connection.
No active HFTFeed subscription or subscription expiredNo active plan.Check the Subscriptions page.
too many sessionsAnother program, a second client in the same program, or an earlier run that never called Stop() holds the session.Stop the other session. After a crash, wait up to two heartbeat intervals (60 seconds by default) and try again.
Start throws … closed the connection before the Logon completed …Your IP address is temporarily blocked, or made more than 6 connection attempts in a minute. Other programs and machines behind the same address count too.Wait at least 5 minutes, fix the cause, and retry more slowly.
HFTFeedThrottledException: Connection attempt to … not made …Your process already opened 5 connections to the server in the last 60 seconds, for example from a retry loop or several clients.Wait RetryAfter, then call Start again.
After a drop, reconnecting takes several secondsAutomatic reconnects wait 1 to 2 seconds before the first attempt, longer after each failure, and never exceed the connection-attempt limit.Nothing to fix; follow OnConnectionStatus and OnError.
Connected, but no ticksNo subscription was sent (check OnSubscribe for Wrong symbol key), the server refused it (check OnError), OnNewTick is not set, or the market is closed.Subscribe with SymbolKey, read both events, and check TPS.
Ticks show 1013 instead of EURUSDMd.Symbol is the symbol key.Map keys to names with GetSymbols().
Some symbols never tick after subscribing to manyToo many subscriptions or Rate limited on OnError.Stay within 64 symbols, pace your requests, then Unsubscribe and Subscribe the missing keys.
Logout slow consumerYour callbacks are too slow.Hand ticks to a worker queue.
No ticks after calling Start again on a stopped clientStop() cleared the subscriptions.Call Subscribe or SubscribeAll again after Start.
A stored tick changes its valuesReuseTickObject is true.Copy the values inside the callback.
Prices print with too few decimals, or with commasDefault double formatting and your culture settings.Format with "F" + (int)Digits and CultureInfo.InvariantCulture.
EntryTimeUtc is 0001-01-01The message carried no time.Treat DateTime.MinValue as unknown.
A 1.0.x application cannot connect1.0.x uses an address that no longer reaches the feed.Upgrade to 1.1.2.

Still stuck? Contact support with your SDK version, the time of the problem in UTC, your SenderCompID (client.ClientId) and the messages OnError reported. Never send your password.