I've currently coded a server/client implementation in C++, where two clients connect to a server. I'm expecting from previous experience (I'm new to C++) that each client (and the server) will have an event handler, and events will come in when either the client wants to send a message to the server, or the client has received a message from the server. You can view it as a chat server; the 'outgoing' event from the client could be the triggered by the user typing something in the console, and the 'incoming' event could be triggered by receiving data from the server.
Is there a standard way of coding this in C++? I'd ideally like to register callback functions for each possible event type, and for the callback function registered to be passed back as a context to the event handler when each event is received, so I can process each event in its specific handling function. And of course once the event has been handled, I want my program to fall back into its event loop.
Any ideas? I'm very comfortable with the event-driven style of programming so would prefer to keep it this way if possible rather than learning entirely new paradigms.
C++ does not have a built-in event handler system (unlike, say, C# and delegates) but there exists plenty of libraries to do that. libsigc++ is one of them.
As a result, any library you use for networking will also have to provide event handling code, either their own or using another library. And if you're rolling out your own networking code, I honestly think creating your own event handling code isn't all that difficult, but I might be insane.
Related
I worked on the synchronous libusb in my Qt project with good results and now I need the asynchronous features of this library. I understood reading here, here and here that, after I've registered my callback function using the libusb_fill_control_transfer and submitted a transfer with libusb_submit_transfer , I need to "keep live" the libusb_handle_events_completed inside a while loop to get the transfer related events since the libusb doesn't have its own thread. for example you can read a code like this
libusb_fill_control_transfer(transfer, dev, buffer, cb, &completed, 1000);
libusb_submit_transfer(transfer);
while (!completed) {
libusb_handle_events_completed(ctx, &completed);
}
Now if I want read a packet that I don't know when it occurs, I think that goes against the asynchronous nature submit a read and wait in the while with libusb_handle_events_completed until the event is triggered.
Then, do I need to create a separate thread within the libusb_handle_events_completed in an infinite while loop?
Can anyone, with experience in the asynchronous features of libusb library, give some suggestions on the right approach to handle the transfer events?
I am new to creating Windows applications in C++. My task is to write two cpp files, one of which will send a number (x) to the other one, the other one will evaluate f(x) and send it back to the first one. I should implement it using Messages. Couldn't get anything specific online, Could someone pls give me a clue, where to start?
Great thanx!
Are you talking about window messages? If so, the sending app could use SendMessage, which would cause the receiving app to get its window procedure executed. Of course, this means that the receiving app needs to create a window whose window handle is somehow made available to the sending app.
You can do it in several ways.
Using WM_COPYDATA message to pass the data
Allocating global memory to pass data and sending your own message, such that second program can read the data from memory
Sending a message (if two ints suit your needs to pass data)
Using named pipes
Using TCP/IP local connection (peer to peer or through a server)
Look at ZeroMQ (http://zeromq.org ; cross-platform, LGPL). It is a very simple, lightweight and powerfull library. From the very basic level you can use it to exchange UDP-style datagrams, but through reliable transport (TCP or some variants). Also you have cancelling support, time-based polling and advanced network schemes (which are non-needed in your case). I've selected it for a similar task, and it performs very well.
I'm attempting to create a library whose API will be used in the following way:
WebService *service = new WebService( username, password );
User *user = service->getAuthenticatedUser();
UserAssets *assets = user->assets();
// And so on
Neither the authenticated user, nor their assets, will be downloaded when the WebServer instance is created, rather they will only be retrieved if explicitly requested.
Whenever I've had to retrieve data from the network before using Qt, I've followed the standard pattern of connection the finished() signal of the QNetworkReply to the appropriate slot and using that slot to handle the returned data.
My problem here is that pattern does not seem to accommodate my desired use-case. I would like the users of my library (other developers) to be able to use a single line to request and receive the data they desire, but the 'Qt way' seems, at least from my point of view, to require them to initiate the request on one line, and then connect some signal to some other slot to get the data back, which is not the experience I would like them to have.
I'm new to network programming, both in general and with Qt, but I've used libraries written in Python, communicating with the exact same service, that are able to achieve this, so it does seem to be possible.
Is it possible to perform the full lifecycle of a HTTP request with Qt with a single function call?
Your best bet is probably to use a QEventLoop. This would allow you to 1) initiate the HTTP connection and, from your caller's perspective, 2) effectively block until you get a response.
For example:
QNetworkReply wait for finished
As already other have mentioned you could use QEventLoop to wait for finished() or error() signals, and the quitting event loop. This solution while working, have some serious disadvantages.
If it takes longer to download given address, then you might be stuck in your event loop for quite a while. The event loop is processing events nicely, so your app doesn't frezze, but there are some quirks connected to it anyway. Imagine that user is waiting for load, and then presses another button, to load something else. Then you will have multiple loop-in-loop, and first file will have to wait for the second to finish downloading.
Doing things in single call suggest to many programmers, that this will happen at one instant. But your function is processing events internally, so this might not hold. Imagine a code like
// some pointer accessible to many functions/methods (eg. member, global)
MyData* myData=0;
Then a code calling your function:
if (myData){
QNetworkReply* reply = getMyWobsite(whatever);
myData->modify(reply);
}
Seems fine, but what if some other slot happens to call
myData=0;
If this slot will be executed while waiting for request, application will crash. If you decide to use QEventLoop in your function, be sure to mention it in function documentation, so programmers using it will be able to avoid such problems.
If you are not using qt for anything else, you might even consider some alternative libraries (eg. libcurl) that might have what you need already implemented.
Trying to understand What is IConnectionPoint and how this is connected to IConnectionPointContainer,IEnumConnectionPoints,IEnumConnections and EventHandling.
Read the artcicles from MSDN and CodeProject which is explaining a about other methods like: QueryInterface() and otherthings.
I am unable to figure out how all these things(IConnectionPointContainer,IEnumConnectionPoints,IEnumConnections) are interconnected with eachother and event Handling.
I just want to create a simpleClient which Will trigger an event in COM object.
If there are any articles or code snippet that can explain how things are related to each other with simple and small chunk of code will be helpfull.
Worth mentioning that I have started development in C recently, a beginner.
Edit #sharptooth
For the Line "typically your client will receive events and the COM object will trigger those events. "
From many articles, What I understood is When we use connection points at that point,
the client exposes a set of methods that the server uses.
I am just Outlining portion of the article from TechRepublich:
Client server vs. sink source
So the main difference between normal programming with COM in a standard client-server system and using connection points is that in the standard client-server case, the server exposes a list of methods that the client employs, and in the connection point case, the client exposes a set of methods that the server uses.
Looks like you get the big picture wrong. Typically your client will receive events and the COM object will trigger those events. To achieve this the client requests (QueryInterface()) the IConnectionPointContainer interface, calls IConnectionPointContainer::FindConnectionPoint() and IConnectionPoint::Advise() and passes a pointer to itself or some subobject there.
The client will have to implement some events interface (the one GUID of which is passed into IConnectionPointContainer::FindConnectionPoint()). Once subscribed (advised) the client will receive calls from the COM server - the events.
Typically the COM server does something routinely and decides to notify clients of it (say a user moves the mouse in an ActiveX control) - it just gets an array of pointers to event receivers and calls a method it wants on that interface.
COM events are in fact an implementation of callbacks. The same way you use callback in C++ (or C or any other languages supporting function pointers or interfaces) you use events in COM. Yes, you're right that when the server triggers the event the client in fact acts as a server reacting to the event. That's a callback scenario - the other code calls your functionality. In this case the server calls your implementation of the events interface.
These two articles provide useful information:
https://devblogs.microsoft.com/oldnewthing/?p=4113
https://devblogs.microsoft.com/oldnewthing/20130612-00/?p=4103
What #sharptooth forgot to mention is, the pointer passed to IConnectionPoint::Advise must be a pointer to a COM object.
This means It must not only implement the particular events interface but also the IUnknown interface.
I have a remote server which handles various different commands, one of which is an event fetching method.
The event fetch returns right away if there is 1 or more events listed in the queue ready for processing. If the event queue is empty, this method does not return until a timeout of a few seconds. This way I don't run into any HTTP/socket timeouts. The moment an event becomes available, the method returns right away. This way the client only ever makes connections to the server, and the server does not have to make any connections to the client.
This event mechanism works nicely. I'm using the boost library to handle queues, event notifications, etc.
Here's the problem. While the server is holding back on returning from the event fetch method, during that time, I can't issue any other commands.
In the source code, XmlRpcDispatch.cpp, I'm seeing in the "work" method, a simple loop that uses a blocking call to "select".
Seems like while the handling of a method is busy, no other requests are processed.
Question: am I not seeing something and can XmlRpcpp (xmlrpc++) handle multiple requests asynchronously? Does anyone know of a better xmlrpc library for C++? I don't suppose the Boost library has a component that lets me issue remote commands?
I actually don't care about the XML or over-HTTP feature. I simply need to issue (asynchronous) commands over TCP in any shape or form?
I look forward to any input anyone might offer.
I had some problems with XMLRPC also, and investigated many solutions like GSoap and XMLRPC++, but in the end I gave up and wrote the whole HTTP+XMLRPC from scratch using Boost.ASIO and TinyXML++ (later I swaped TinyXML to expat). It wasn't really that much work; I did it myself in about a week, starting from scratch and ending up with many RPC calls fully implemented.
Boost.ASIO gave great results. It is, as its name says, totally async, and with excellent performance with little overhead, which to me was very important because it was running in an embedded environment (MIPS).
Later, and this might be your case, I changed XML to Google's Protocol-buffers, and was even happier. Its API, as well as its message containers, are all type safe (i.e. you send an int and a float, and it never gets converted to string and back, as is the case with XML), and once you get the hang of it, which doesn't take very long, its very productive solution.
My recomendation: if you can ditch XML, go with Boost.ASIO + ProtobufIf you need XML: Boost.ASIO + Expat
Doing this stuff from scratch is really worth it.