直接使用 Win32 CreateFile() 函数打开文件,这样您就可以指定 FILE_FLAG_DELETE_ON_CLOSE 标志,然后使用 THandleStream 类包装生成的句柄。
type
TMyHandleStream = class(THandleStream)
public
destructor Destroy; override;
end;
destructor TMyHandleStream.Destroy;
begin
inherited;
CloseHandle(Handle);
end;
var
h: THandle;
r, f: String;
SS: TStringStream;
Uid: TGuid;
begin
CreateGuid(Uid);
f := 'C:\some folder\' + GuidToString(Uid) + '.rpt';
h := Windows.CreateFile(PChar(f), GENERIC_READ or GENERIC_WRITE, FILE_SHARE_READ, nil, CREATE_ALWAYS, FILE_FLAG_DELETE_ON_CLOSE, 0);
if h = INVALID_HANDLE_VALUE then RaiseLastOSError;
Result := TMyHandleStream.Create(h);
try
r := getRunReportJSON(ARunReportObj);
SS := TStringStream.Create(r, TEncoding.ASCII);
try
ServerContainer1.IdHTTP1.Post(gUrl, SS, Result);
finally
SS.Free;
end;
Result.Position := 0;
except
Result.Free;
raise;
end;
end;
从TFileStream 派生一个新类并覆盖其析构函数以删除文件:
type
TMyFileStream = class(TFileStream)
public
destructor Destroy; override;
end;
destructor TMyFileStream.Destroy;
begin
inherited;
DeleteFile(Self.FileName);
end;
var
r, f: String;
SS: TStringStream;
Uid: TGuid;
begin
CreateGuid(Uid);
f := 'C:\some folder\' + GuidToString(Uid) + '.rpt';
Result := TMyFileStream.Create(f, fmCreate or fmOpenReadWrite);
try
r := getRunReportJSON(ARunReportObj);
SS := TStringStream.Create(r, TEncoding.ASCII);
try
ServerContainer1.IdHTTP1.Post(gUrl, SS, Result);
finally
SS.Free;
end;
Result.Position := 0;
except
Result.Free;
raise;
end;
end;
使用this forum answer中显示的TFileStreamEx类:
type
TFileStreamEx = class(THandleStream)
public
constructor Create(const FileName: string; Mode: Word; flags: DWORD = FILE_ATTRIBUTE_NORMAL);
destructor Destroy; override;
end;
constructor TFileStreamEx.Create(const FileName: string; Mode: Word; flags: DWORD = FILE_ATTRIBUTE_NORMAL);
const
AccessMode: array[0..2] of LongWord = (
GENERIC_READ,
GENERIC_WRITE,
GENERIC_READ or GENERIC_WRITE);
ShareMode: array[0..4] of LongWord = (
0,
0,
FILE_SHARE_READ,
FILE_SHARE_WRITE,
FILE_SHARE_READ or FILE_SHARE_WRITE);
begin
if Mode = fmCreate then
begin
inherited Create(
CreateFile(
PChar(FileName),
GENERIC_READ or GENERIC_WRITE,
0,
nil,
CREATE_ALWAYS,
flags,
0
)
);
if Handle = INVALID_HANDLE then
raise EFCreateError.CreateFmt(SFCreateError, [FileName]);
end
else
begin
inherited Create(
CreateFile(
PChar(FileName),
AccessMode[Mode and 3],
ShareMode[(Mode and $F0) shr 4],
nil,
OPEN_EXISTING,
flags,
0
)
);
if Handle = INVALID_HANDLE then
raise EFOpenError.CreateFmt(SFOpenError, [FileName]);
end;
end;
destructor TFileStreamEx.Destroy;
begin
if Handle <> INVALID_HANDLE then CloseHandle(Handle);
end;
var
r, f: String;
SS: TStringStream;
Uid: TGuid;
begin
CreateGuid(Uid);
f := 'C:\some folder\' + GuidToString(Uid) + '.rpt';
Result := TFileStreamEx.Create(f, fmCreate or fmOpenReadWrite, FILE_FLAG_DELETE_ON_CLOSE);
try
r := getRunReportJSON(ARunReportObj);
SS := TStringStream.Create(r, TEncoding.ASCII);
try
ServerContainer1.IdHTTP1.Post(gUrl, SS, Result);
finally
SS.Free;
end;
Result.Position := 0;
except
Result.Free;
raise;
end;
end;