I am currently trying to build a program using FIX protocol to communicate with a broker (currenex). I sent my (self-generated) logon message to the server and got something back.
This is what I sent
8=FIX.4.49=8835=A49=xxxxxxxx56=CNX34=152=20140718-11:40:18.24498=0108=30141=Y554=xxxxxx10=128
(the SenderCompID and the password were replaced)
and I got
8=FIX.4.49=7635=A34=149=CNX52=20140718-11:40:33.22456=xxxxxxxx141=Y98=0108=3010=1458=FIX.4.49=7035=h34=249=CNX52=20140718-11:40:33.22656=xxxxxxxx336=0340=210=128
back from the server.
I think I built the logon message correct (or did I?). But when I sent a second request MarketDataRequest
8=FIX.4.49=13735=V49=xxxxxxxx56=CNX34=252=20140718-11:42:53.504262=363263=1264=0265=1266=N267=2269=1269=0146=155=GBP/USD554=xxxx10=013
I had no response at all. I asked the broker and they said the connection dropped right away every time after I logged in.
I thought it was some connection problem and I tried using RESTClient (Postman) to send the message but the result was the same.
Could any one take a look at my messages and point out if there is something stupid please?
All I need is the real-time exchange rate so a simple FIX message example will be very helpful. Thanks a lot!
Regards,
Bo
Your logon response message says that your trading session is open (340=2) so it's not broker-side problem. I think your program disconnects TCP/IP connection from server after login message. FIX protocol insists that TCP/IP connection must be kept alive during the whole FIX session - otherwise the session will be closed. So you need rewrite your program to keep connection alive and just send there yor requests and listen for responses. Don't close the connection.
Try using Minifix tool which will maintain the heartbeats and the session connection.
Ideally for a 35=V request you should get
35=W = Market Data-Snapshot/Full Refresh
35=X = Market Data-Incremental Refresh
35=Y = Market Data Request Reject
you get a 35=3 (reject) or 35=4 (or a seq reset) in response to a 35=A request.
Related
I have created an instant messenger chat application where by messages are posted to my server via a php service and stored in a mysql backed.
If a user has their 'inbox' page open and a new message is received I would need to update the table to show any new messages. The way I am doing this at the moment is by sending an http request to the server every 5 seconds.
As you can imagine this is pretty inefficient. What methods are available which would be more suitable and less resource heavy?
I have looked at keep alive connections and web sockets but Im not sure which direction I should be going in?
any help much appreciated!
Your approach is called polling, which is not efficient because it consumes more electricity from your phone and you have extra load to your server. The correct way of doing it is though Apple's push notification. Here is the tutorial for that. Basically your server will send request to Apple's push notification center when a new message is received.
However in your case it's a bit more complicated. You want this notification only after user entering the mail page. So you need to tweak your php server to send notification only after user entered the mail page. In this case you are sending only one request to your server telling it to start sending notifications, instead of constantly polling your server
I am using ejabberd server and ios xmppframework.
there are two clients, A and B.
When A and B are online, A can send message to B successfully.
If B is offline, B can receive the message when B is online again.
But when B is suddenly/unexpectedly lost connection, such as manually close wi-fi, the message sent by A is lost. B will never
receive this message.
I guess the reason is that B lost connection suddenly and the server still think B is online. Thus the offline message does work under this condition.
So my question is how to ensure the message that sent by A will be received by B? To ensure there is no messages lost.
I've spent the last week trying to track down missing messages in my XMPPFramework and eJabberd messaging app. Here are the full steps I went through to guarantee message delivery and what the effects of each step are.
Mod_offline
In the ejabberd.yml config file ensure that you have this in the access rules:
max_user_offline_messages:
admin: 5000
all: 100
and this in the modules section:
mod_offline:
access_max_user_messages: max_user_offline_messages
When the server knows the recipient of a message is offline they will store it and deliver it when they re-connect.
Ping (XEP-199)
xmppPing = XMPPPing()
xmppPing.respondsToQueries = true
xmppPing.activate(xmppStream)
xmppAutoPing = XMPPAutoPing()
xmppAutoPing.pingInterval = 2 * 60
xmppAutoPing.pingTimeout = 10.0
xmppAutoPing.activate(xmppStream)
Ping acts like a heartbeat so the server knows when the user is offline but didn't disconnect normally. It's a good idea to not rely on this by disconnecting on applicationDidEnterBackground but when the client looses connectivity or the stream disconnects for unknown reasons there is a window of time where a client is offline but the server doesn't know it yet because the ping wasn't expected until sometime in the future. In this scenario the message isn't delivered and isn't stored for offline delivery.
Stream Management (XEP-198)
xmppStreamManagement = XMPPStreamManagement(storage: XMPPStreamManagementMemoryStorage(), dispatchQueue: dispatch_get_main_queue())
xmppStreamManagement.autoResume = true
xmppStreamManagement.addDelegate(self, delegateQueue: dispatch_get_main_queue())
xmppStreamManagement.activate(xmppStream)
and then in xmppStreamDidAuthenticate
xmppStreamManagement.enableStreamManagementWithResumption(true, maxTimeout: 100)
Nearly there. The final step is to go back to the ejabberd.yml and add this line to the listening ports section underneath access: c2s:
resend_on_timeout: true
Stream Management adds req/akn handshakes after each message delivery. On it's own it won't have any effect on the server side unless that resend_on_timeout is set (which it isn't by default on eJabberd).
There is a final edge case which needs to be considered when the acknowledgement of a received message doesn't get to the server and it decides to hold it for offline delivery. The next time the client logs in they are likely to get a duplicate message. To handle this we set that delegate for the XMPPStreamManager. Implement the xmppStreamManagement getIsHandled: and if the message has a chat body set the isHandledPtr to false. When you construct an outbound message add an xmppElement with a unique id:
let xmppMessage = XMPPMessage(type: "chat", to: partnerJID)
let xmppElement = DDXMLElement(name: "message")
xmppElement.addAttributeWithName("id", stringValue: xmppStream.generateUUID())
xmppElement.addAttributeWithName("type", stringValue: "chat")
xmppElement.addAttributeWithName("to", stringValue: partnerJID.bare())
xmppMessage.addBody(message)
xmppMessage.addChild(xmppElement)
xmppMessage.addReceiptRequest()
xmppStream.sendElement(xmppMessage)
Then when you receive a message, inform the stream manager that the message has been handled with xmppStreamManager.markHandledStanzaId(message.from().resource)
The purpose of this final step is to establish a unique identifier that you can add to the XMPPMessageArchivingCoreDataStorage and check for duplicates before displaying.
I guess the reason is that B lost connection suddenly and the server
still think B is online. Thus the offline message does work under this
condition
Yes you are absolutely correct,this is well known limitation of TCP connections.
There are two approaches to your problem
1 Server side
As I can see you are using ejabbed as XMPP server you can implement
mod_ping , Enabling this module will enables server side
heartbeat[ping] ,in case of broken connection to server[ejabbed] will
try to send heartbeat to connection and will detect connection is lost
between server and client. Use of this approach has one
drawback,module mod_ping has property called ping_interval which
states how often to send heartbeat to connected clients, here lower
limit is 32 seconds any value below 32 is ignored by ejabbed,means
you have 32 seconds black window in which messages can be lost if user
is sowing as online
2 Client side
From client side you can implement Message Delivery Receipts
mechanism .With each Chat message send a receipt to receiver user of
as soon as receiver user receives message send back this receipt
id. This way you can detect that your message is actually delivered to
receiver. If you don't receive such acknowledgement between certain
time interval you can show user as offline locally(on mobile
phone),store any further messages to this user as offline message
locally[in SQLLight database ],and wait for offline presence stanza for that user
,as soon as you receive offline presence stanza it means that server
has finally detected connection to that user is lost and makes user
status as offline ,now you can send all messages to that user ,which
will be again stored as offline messages on server.This is best
approach to avoid black-window.
Conclusion
You can either use Approach 2 and design you client such way ,you can also use Approach 1 along with approach 2 to minimize server broken connection detraction time.
If B goes offline suddenly then user A have to check if B is online/offline while sending message to user B. If user B is offline then user A have to upload that message on Server using Web service. And user B have to call web service on below function.
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
So user B will get that all offline message which was lost due to connection Lost.
At last, I use Ping together with Stream Management:
http://xmpp.org/extensions/xep-0198.html
This problem is solved.
Can anybody give me a possible reason why my QSSLSocket would stop sending and receiving data without firing a stateChanged or disconnected signal.
My app starts a thread which connects to Facebooks XMPP server, authenticates and then goes into a while loop calling waitForReadyReady(10000) and then if this returns true it will read the data. Sometimes, After a while this call to waitForReadyReady will never return true even though there should be something to read and if I try to send data at this point the server won't receive anything.
I am sending pings to the XMPP server and can detect when this has happened after not receiving a reply to my ping but it's not really usable as an app until I get to the bottom of why communication is sometimes just breaking down between client and server.
Can anybody offer any insights please?
I'm having a problem with a .NET client connecting to an apache server for XML requests. Exactly every 50th time XML is transferred the response seems to be lost.
Looking at a WireShark trace on the client I can see that every 50th time the apache server sends an encrypted alert followed by a FIN, ACK. The client responds with a RST which closes the socket, but then the client continues to try to use the socket, it sends SYN packets without any response. When this happens the response doesn't get back to the application layer on the client.
After the client times out and reconnects (renegotiates encryption) it works another 49 times and then fails again.
Just to add this same .NET client is in use on many other client machines without a problem.
I can't find anyone else having this issue. Any ideas how to resolve this?
If a quick fix session is created by server(acceptor) at say 9AM, but the StartTime is at 11AM. This means the session exists but not active.
If the server receives an unsolicited message from an exchange that it needs to send on this session, will it persist this if I have configuration PersistMessages=Y and sends it to the client(initiator) when it connects after 11AM?
No, it would not persist messages received before start time and would send you a reject message. The message will be rejected at the interface itself, message isn't handled. You would have to resend it to get a response.
QuickFIX does persist (but not send) messages before a session is connected. The sequence numbers are updated and when the session is connected and the first message is sent, the counterparty FIX engine will see the gap in the sequence numbers and request a resend. QuickFIX will then resend the persisted messages. However, depending on your QuickFIX configuration, the outgoing messages might be considered to be too old and rejected locally.
As I understand, these are kept to take into account timings under which corresponding exchange would accept the orders.
Application or its sub-modules do not need to maintain timings and take some action on closing the fix session. Rather, QuickFix shall automatically deactivate the session.
Persistence of the message or re-sesnding when the session becomes active does not look desirable to me.
You can rather maintain some kind of queue to buffer such messages in sending application, and send them only when the time matches with active session timings.
That's my thoughts, hope that helps.