Jump to content
Stéphane Wierzbicki

How can I delete an archive Item using TZipFile class

Recommended Posts

Posted (edited)

Hello,

 

Anyone knows how I can delete an archive Item using TZipFile class ? 

I found a TZipFileHelper class helper on the net. It is useless since we cannot access TZipFile private members anymore.

 

procedure TZipFileHelper.Delete(FileName: string);
var
  i, j: Integer;
  StartOffset, EndOffset, Size: UInt32;
  Header: TZipHeader;
  Buf: TBytes;
begin
  i := IndexOf(FileName);
  if i <> -1 then begin
    // Find extents for existing file in the file stream
    StartOffset := Self.FFiles[i].LocalHeaderOffset;
    EndOffset := Self.FEndFileData;
    for j := 0 to Self.FFiles.Count - 1 do begin
      if (Self.FFiles[j].LocalHeaderOffset > StartOffset) and
         (Self.FFiles[j].LocalHeaderOffset <= EndOffset) then
        EndOffset := Self.FFiles[j].LocalHeaderOffset;
    end;
    Size := EndOffset - StartOffset;
    // Update central directory header data
    Self.FFiles.Delete(i);
    for j := 0 to Self.FFiles.Count - 1 do begin
      Header := Self.FFiles[j];
      if Header.LocalHeaderOffset > StartOffset then begin
        Header.LocalHeaderOffset := Header.LocalHeaderOffset - Size;
        Self.FFiles[j] := Header;
      end;
    end;
    // Remove existing file stream
    SetLength(Buf, Self.FEndFileData - EndOffset);
    Self.FStream.Position := EndOffset;
    if Length(Buf) > 0 then
      Self.FStream.Read(Buf[0], Length(Buf));
    Self.FStream.Size := StartOffset;
    if Length(Buf) > 0 then
      Self.FStream.Write(Buf[0], Length(Buf));
    Self.FEndFileData := Self.FStream.Position;
  end;
end;

 

 

ps: I'm using Delphi RIO

Edited by Stéphane Wierzbicki

Share this post


Link to post
5 hours ago, Stéphane Wierzbicki said:

access TZipFile private members

WITH is your friend:

// from https://stackoverflow.com
procedure TSomeClassHelper.CheckAccessToPrivate;
begin
 With Self do begin // access via with works
   FInt :=1;
   SomeMethod;
 end;
end;
// Declared in another unit as:
type TSomeClass = class
    private
      FInt : integer;
      procedure SomeMethod;
  end;

 

Share this post


Link to post
On 8/31/2019 at 10:37 AM, Stéphane Wierzbicki said:

That is clearly a bug ! I'm surprised EMB did not fixed it!.

They are aware of it. Just as they have already fixed other access issues related to helpers, it is likely only a matter of time before they do fix this one too. 

Edited by Remy Lebeau

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×