3

I was looking for some tutorials/source codes to resume paused/aborted downloads. I found a source code, but I'm getting this error:

procedure TForm1.Download(url, pathLocal : String);
var
   eFile     : TFileStream;
   IdHTTP  : TIdHTTP;

begin
   idHTTP := TIdHTTP.Create(nil);

   if FileExists(pathLocal) then //Caso o arquivo já exista ele o abre, caso contrário cria um novo
      eFile := TFileStream.Create(pathLocal,fmOpenReadWrite)
   else
      eFile := TFileStream.Create(pathLocal,fmCreate);

   try
      try
         eFile.Seek(0,soFromEnd); //Colocando o ponteiro no final do arquivo

         IdHTTP.Head(url); //Buscando informações do arquivo

         if eFile.Position < IdHTTP.Response.ContentLength then //Somente se o arquivo já não foi totalmente baixado
         begin
            IdHTTP.Request.ContentRangeStart := eFile.Position; //Definindo onde deve inciar o download
            IdHTTP.Request.ContentRangeEnd := IdHTTP.Response.ContentLength; //Verificando o tamanho do arquivo

            if eFile.Position > 0 then
            begin //É importante que o range seja definido com o tamanho inicial e o final
               IdHTTP.Request.Range := Format('%d-%d',[eFile.Position,IdHTTP.Response.ContentLength]); 
            end;

            IdHTTP.Get(url,eFile);
         end;
      except
         ShowMessage('Conexão interrompida.');
      end;
   finally
      eFile.Free;
      IdHTTP.Disconnect;
      IdHTTP.Free;
   end;
end;

This is the error:

Undeclared identifier: 'Range'

How can I fix this?

paulohr
  • 576
  • 1
  • 9
  • 24

2 Answers2

3

The ContentRange... properties are not used for HTTP requests, only HTTP responses. Take them out of your code completely. Use only the Range property (which exists in Indy 10 so make sure you are not using Indy 9 or earlier). As for the Range property itself, you are not formatting it correctly. It needs a bytes= prefix, and you can omit the end value to tell the server you want the rest of the file:

IdHTTP.Request.Range := Format('bytes=%d-',[eFile.Position]);

If you use the Ranges property instead, it handles those details for you (the Range property is deprecated):

IdHTTP.Request.Ranges.Add.StartPos := eFile.Position;

Before you send a ranged request, be sure to check if Head() set the Response.AcceptRanges property to bytes first, otherwise Get() could fail with an error or send you the entire file regardless of your specified range.

Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
2

Your problem it seems related to your indy version , try updating to the last version of indy , also instead of Request.Range try using Request.Ranges check this question for an example Delphi XE: idHttp & Request.Range, a bug?

Community
  • 1
  • 1
RRUZ
  • 134,889
  • 20
  • 356
  • 483