0
votes

I use Delphi 10.2 Tokyo with Indy (the integrated version).

Scenario: I do http GET requests (TIdHttp) in threads, and use proxies. Sometimes, a proxy seems to cause Indy not to timeout, and not to return from a GET. I also assign the onWork event handler to react to an Abort button and call within this handler the idHttp.Disconnect function. When the GET seems to be frozen, the abort also does not work, possible that in this case the onWork event is not triggered, I have no idea.

The main thread is idle and only create lets say 50 threads, each does a GET via its instance of TIdHttp. Ans sometiumes, as I mentioend, a proxy cause of GET not to return which result then in a "hanging" thread.

My question is: How can I force Indy to abort, from an external thread? Is there anything what can be done via code when the GET refuse to return?

1
First off, do you have a non-infinite ReadTimeout assigned? Don't call Disconnect in the OnWork events. Raise an exception instead, like calling SysUtils.Abort. But if the connection is hung/blocked, the OnWork events won't be firing. Your main thread can directly call Disconnect to abort a blocking socket operation in progress in another thread, but that is not portable (it works on Windows, might not on other platforms) - Remy Lebeau
@Remy Lebeau: I have a timeout set to 30 seconds, but its not triggered also when the GET is "frozen". I use firemonkey, so it need to work on Win32/Win64 and macOS. I just had another issue, identical, just without the use of proxies, so its not due to proxies. I did a GET to a website with data to process as parameter of the url. The server who process the data take 2 minutes to response. The GET is in this case also "frozen" with no way to abort by my user, because the onWork isn't triggered during this "waiting" of the GET to return. - user7415109
The ReadTimeout should work, assuming the connection is actually idle and not just sending data slowly. If it is not working, you will have to debug it to figure out why. calling Disconnect from a different thread is probably your best option. - Remy Lebeau

1 Answers

0
votes

I solved my issues by using a background thread to disconnect sockets and implement a timeout, which seems to work even socket are "frozen" and the onWork is not triggered. I do this by adding the TIdHttp instances I create to an array, together with the time the instance was created. If the GET return normal, the array entry will be removed. In a background thread, I check if the user clicked Abort, and then loop through the array and call disconnect on each instance. I also check in the same thread if a timeout period was reached, and also call disconnect. Might not be the perfect solution, but it works for me.