You mean the console app can only be run once?
Yes there can only be a single console app and each window in the GUI will send\recv messages to the command-line app. The console app lifetime will be the duration of the GUI application. Imagine that there are 4 windows in the GUI app: A, B, C, D. If window A requests data it should only come back to window A and not other windows. In theory I wanted to be able to write something like this for each of the functions:
// psuedo code
{
QProcess()->write
("GetTradeData\n");
// send a command to the console app QProcess()->read
(output
);
// read it's response and return it to the caller }
// psuedo code
::GetTradeData( QString* output )
{
QProcess()->write("GetTradeData\n"); // send a command to the console app
QProcess()->read(output); // read it's response and return it to the caller
}
To copy to clipboard, switch view to plain text mode
Sending requests to the command application seems to work great: each window can send data to the command line app via the QProcess()->write() method. Unfortunately QProcess()->read() seems to never return a buffer. I'm not sure if this is because 1) the race condition between the console application outputting data and the GUI calling read() or 2) all command line output is going to the function that I have connected the signals and slots to:
connect(myCommandLineApp, SIGNAL(readyReadStandardOutput()), this, SLOT(recvCommandOutput()));
connect(myCommandLineApp, SIGNAL(readyReadStandardError()), this, SLOT(recvCommandErrorOutput()));
connect(myCommandLineApp, SIGNAL(readyReadStandardOutput()), this, SLOT(recvCommandOutput()));
connect(myCommandLineApp, SIGNAL(readyReadStandardError()), this, SLOT(recvCommandErrorOutput()));
To copy to clipboard, switch view to plain text mode
That code works great for the asychronous output that's sometimes outputted by the console app.
Not sure what you mean with polling.
QProcess is, and likely any other backend you might implement will be, asynchronous, so there is not and likely won't be any reason for polling.
Here's where I'm stumped. Because I never received output from the QProcess()->read() call I instead had recvCommandOutput() insert results into a results data structure. The results output have a transaction ID that I can set when I make my query. I then attempted to poll on the results data structure like so looking for my transaction ID:
// psuedo code
{
QProcess()->write
(transactionId
+ "GetTradeData\n");
// send a command to the console app
do{
results = CheckForResults( transactionId );
}while( results == NULL)
}
// psuedo code
::GetTradeData( QString* output )
{
QProcess()->write(transactionId + "GetTradeData\n"); // send a command to the console app
do{
results = CheckForResults( transactionId );
}while( results == NULL)
}
To copy to clipboard, switch view to plain text mode
The issue with this is that the polling will loop forever. recvCommandOutput() is never hit once I start looping. Again I believe this is because I have a single MainWindow thread.
Reading between the lines in both of your messages I now believe I am making a mistake in attempting to make the asychronous calls appear sychronous to the GUI. While it would make the GUI code easier to write I feel like I will run into issues in the future.
While I understand that you are not currently using direct networking the QNetworkAccessManager and QNetworkReply provides a reasonable example of one way to handle separation of responses. When given a request the (typically single) QNetworkAccessManager (StockQuote) immediately returns a QNetworkReply (IStockQuoteReply with concrete subclasses StockQuoteReply, StockVolumeReply perhaps) that you connect to the handlers that should deal with the reply. The reply object is the one that issues the various signals related to the request that created it. In this way you avoid having all replies go to a single place that must then separate them.
Yes, the more I think about it this is the correct way to go. Do you know if there is something similar for command line app output? Also, how would you handle the case where there are multiple StockQuote and StockVolume windows open? Again only one window should receive the output.
Thank you both for all your help. I'm beginning to get an idea for what I have to write.
Bookmarks