Може ли POST методът на TIndyHTTP да бъде извикан многократно много бързо?

Използвам Indy версия 10.5498, за да публикувам някои данни от много части/формуляри, включително прикачен файл към api. Моят код е адаптиран от този, предоставен ми от Remy в тази публикация, с обработка на грешки в протокола, взета от тук. Кодът, който имам сега, работи добре и получавам отговор от сървъра с данни около 2 секунди след публикуването.

Въпреки това понякога може да се наложи да направя публикация няколко пъти много бързо, например като премина през набора от данни, върнат от база данни, и направя публикация за всеки запис.

Има ли нещо, което трябва да знам или някакъв специален код, който трябва да напиша, за да се справя със ситуацията, при която може да правя втори POST, преди първият POST да е завършил изпращането (или поне преди да бъде получен отговорът на сървъра? Или POST блокиращо повикване ли е, което не връща контрола, докато не бъде получен отговорът?

В момента компонентът TIdHTTP е поставен във формуляра, а не динамично създаден. Бих могъл да създам нов TIdHTTP обект за всяка публикация и след това да го унищожа, ако е необходимо.

Кодът, който използвам, за да публикувам в момента, е по-долу

function TForm1.Upload(url: string; params, filenames: TStrings): string;
var
 FormData : TIdMultiPartFormDataStream;
 ResponseText : string;
 i : integer;
begin
  FormData := TIdMultiPartFormDataStream.Create;
  try
    for i := 0 to params.Count - 1 do
      FormData.AddFormField(params.Names[i], params.ValueFromIndex[i]);
    for i := 0 to filenames.Count - 1 do
       FormData.AddFile('attachment', filenames[i]);   

    //add authorisation header
    IdHTTP1.Request.CustomHeaders.Add('Authorization:Basic ' + U_generalStuff.base64encodeStr(ATHORISATION_STR));

    //way to use just one try except yet get the full text server response whether its a 400 error or a success response
    //see https://stackoverflow.com/questions/54475319/accessing-json-data-after-indy-post
    // Make sure it uses HTTP 1.1, not 1.0,  and disable EIdHTTPProtocolException on errors
    IdHTTP1.ProtocolVersion := pv1_1;
    IdHTTP1.HTTPOptions := IdHTTP1.HTTPOptions + [hoKeepOrigProtocol, hoNoProtocolErrorException, hoWantProtocolErrorContent];
    try
       ResponseText := IdHTTP1.Post(url, FormData);   //post to the api
    except
      on E: Exception do
         begin
         ResponseText := E.ClassName + ': ' + E.message;
         raise;
         end;
    end; //try-except
  finally
     result := ResponseText;
  end; //try finally
end;

Оттогава видях тази публикация, която говори за нишки и използване на паралелната библиотека. Това нещо ли трябва да проуча, за да отговоря на въпроса си?


person user2834566    schedule 09.05.2019    source източник


Отговори (1)


Като повечето неща в Indy, TIdHTTP.Post() е синхронна операция. Той не се връща обратно към повикващия, докато не бъде получен пълен отговор (или докато не възникне грешка). Така че, ако извикате TIdHTTP.Post() в обикновен цикъл, НЕ МОЖЕТЕ да изпратите нова POST заявка, докато предишната заявка не бъде напълно завършена. Ако трябва да направите това, ще трябва да извикате TIdHTTP.Post() асинхронно, като го извикате в множество работни нишки (и дайте на всяка нишка свой собствен TIdHTTP обект, тъй като не можете да използвате повторно TIdHTTP обект в множество едновременни заявки).

person Remy Lebeau    schedule 10.05.2019
comment
Добре благодаря. Сега разбирам поведението, с което мога да работя. - person user2834566; 12.05.2019