⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 transfer.pas

📁 AutoUpdate是一个通过网络对软件进行自动更新的系统。可以自动根据软件的版本号、最后修改时间、文件的大小等因素自动的判断哪些文件应该
💻 PAS
字号:
unit Transfer;

interface

uses
  SysUtils, Windows, Messages, Classes, Graphics, Controls,
  Forms, Dialogs, IdFTP, IdComponent, IdURI, Contnrs;


type
  TOnTransferStart = procedure (Sender: TObject; const AWorkCountMax: Integer)
          of object;
  TOnTransfer = procedure (Sender: TObject; const AWorkCount: Integer) of
          object;
  TOnTransferEnd = procedure (Sender: TObject) of object;
  TProxySeting = record
    ProxyServer: string;
    ProxyPort: Integer;
    ProxyUser: string;
    ProxyPass: string;
  end;
  
  TTransfer = class(TPersistent)
  private
    FCurrentDir: string;
    FFileName: string;
    FHost: string;
    FOnTransfer: TOnTransfer;
    FOnTransferEnd: TOnTransferEnd;
    FOnTransferStart: TOnTransferStart;
    FPassword: string;
    FPort: Integer;
    FURI: TIdURI;
    FUser: string;
    procedure SetHost(const Value: string); virtual;
    procedure SetURI(Value: TIdURI);
  protected
    function GetOnStatus: TIdStatusEvent; virtual; abstract;
    procedure SetOnStatus(Value: TIdStatusEvent); virtual; abstract;
  public
    procedure Abort; virtual; abstract;
    procedure Connect; virtual; abstract;
    procedure Get(FileName: String); overload; virtual; abstract;
    procedure Get(Stream: TStream); overload; virtual; abstract;
    procedure SetProxy(ProxyObj: TPersistent); overload; virtual; abstract;
    procedure SetProxy(ProxyInfo: TProxySeting); overload; virtual; abstract;
    procedure Work(Sender: TObject; AWorkMode: TWorkMode; const AWorkCount:
            Integer); virtual;
    procedure WorkEnd(Sender: TObject; AWorkMode: TWorkMode);
    procedure WorkStart(Sender: TObject; AWorkMode: TWorkMode; const
            AWorkCountMax: Integer); virtual;
    procedure ClearProxySeting; virtual; abstract;
    property CurrentDir: string read FCurrentDir write FCurrentDir;
    property FileName: string read FFileName write FFileName;
    property Host: string read FHost write SetHost;
    property Password: string read FPassword write FPassword;
    property Port: Integer read FPort write FPort;
    property URI: TIdURI read FURI write SetURI;
    property User: string read FUser write FUser;
  published
    property OnStatus: TIdStatusEvent read GetOnStatus write SetOnStatus;
    property OnTransfer: TOnTransfer read FOnTransfer write FOnTransfer;
    property OnTransferEnd: TOnTransferEnd read FOnTransferEnd write
            FOnTransferEnd;
    property OnTransferStart: TOnTransferStart read FOnTransferStart write
            FOnTransferStart;
  end;
  
  TFTPTransfer = class(TTransfer)
  private
    FIdfTP: TIdfTP;
    procedure SetHost(const Value: string); override;
  protected
    function GetOnStatus: TIdStatusEvent; override;
    procedure SetOnStatus(Value: TIdStatusEvent); override;
  public
    constructor Create;
    destructor Destroy; override;
    procedure Abort; override;
    procedure Connect; override;
    procedure Get(FileName: String); overload; override;
    procedure Get(Stream: TStream); overload; override;
    procedure SetProxy(ProxyObj: TPersistent); overload; override;
    procedure SetProxy(ProxyInfo: TProxySeting); overload; override;
    procedure WorkStart(Sender: TObject; AWorkMode: TWorkMode; const
            AWorkCountMax: Integer); override;
    procedure ClearProxySeting; override;
  end;
  
  TTransferFactory = class(TObject)
  private
    FIdURI: TIdURI;
    FObjectList: TObjectList;
  public
    constructor Create;
    destructor Destroy; override;
    function CreateTransfer(URL:  String): TTransfer; overload;
    Function CreateTransfer(URL: String; ProxySeting: TProxySeting): TTransfer; overload;
  end;
  
  ExceptionNoSuport = class(Exception)
  end;
  

implementation

{
********************************** TTransfer ***********************************
}
procedure TTransfer.SetHost(const Value: string);
begin
  FHost := Value;
end;

procedure TTransfer.SetURI(Value: TIdURI);
begin
  // TODO -cMM: TTransfer.SetURI default body inserted
  //if Assigned(FURI) then FURI.Free;
  FURI := Value;
  self.Host := FURI.Host;
  if trim(FURI.Username) = '' then
    self.User := 'Anonymous'
  else
    self.User := FURI.Username;
  self.Password := FURI.Password;
  if trim(FURI.Path) = '' then
    Self.CurrentDir := '/'
  else
    self.CurrentDir := FURI.Path;
  self.FileName := FURI.Document;
  if (FURI.Port = '') then
    self.Port := 21
  else
    self.Port := StrToInt(FURI.Port);
end;

procedure TTransfer.Work(Sender: TObject; AWorkMode: TWorkMode; const
        AWorkCount: Integer);
begin
  if Assigned(FOnTransfer) then
    FOnTransfer(Sender, AWorkCount);
  Application.ProcessMessages;
end;

procedure TTransfer.WorkEnd(Sender: TObject; AWorkMode: TWorkMode);
begin
  if Assigned(FOnTransferEnd) then
    FOnTransferEnd(Sender);
end;

procedure TTransfer.WorkStart(Sender: TObject; AWorkMode: TWorkMode; const
        AWorkCountMax: Integer);
begin
  if Assigned(FOnTransferStart) then
    FOnTransferStart(Sender, AWorkCountMax);
end;

{
********************************* TFTPTransfer *********************************
}
constructor TFTPTransfer.Create;
begin
  inherited Create;
  FIdFTP := TIdFTP.Create(nil);
  FIdFtp.OnWorkBegin := Self.WorkStart;
  FIdFtp.OnWork := Self.Work;
  FIdFtp.OnWorkEnd := Self.WorkEnd;
  FIdFtp.RecvBufferSize := 8192;
  FIdFtp.SendBufferSize := 4096;
  FIdFtp.Passive := true;
  self.Port := 21;
end;

destructor TFTPTransfer.Destroy;
begin
  if Assigned(FIdFtp) then
  begin
    FIdFtp.Disconnect;
    FreeAndNil(FIdFTP);
  end;
  inherited Destroy;
end;

procedure TFTPTransfer.Abort;
begin
  FIdFtp.Abort;
end;

procedure TFTPTransfer.Connect;
begin
  try
    FIdFtp.Host := self.Host;
    FIdFtp.Username := self.User;
    FidFtp.Password := self.Password;
    FIdFtp.Port := self.Port;
    FIdFtp.Connect();
    if (FidFtp.Username <> 'Anonymous') then
      FIdFtp.Login;
  except
    raise;
  end;
end;

procedure TFTPTransfer.Get(FileName: String);
begin
  try
    if (not FIdFTP.Connected) then
      Connect();
    FIdFtp.ChangeDir(self.CurrentDir);
    FIdFtp.Get(self.FileName, FileName, true);
    FIdFtp.Disconnect;
  except
    raise;
  end;
end;

procedure TFTPTransfer.Get(Stream: TStream);
begin
  try
    if (not FIdFTP.Connected) then
      Connect();
    FIdFtp.ChangeDir(self.CurrentDir);
    FIdFtp.Get(self.FileName, Stream, true);
    FIdFtp.Disconnect;
  except
    raise;
  end;
end;

function TFTPTransfer.GetOnStatus: TIdStatusEvent;
begin
  Result := FIdFtp.OnStatus
end;

procedure TFTPTransfer.SetHost(const Value: string);
begin
  if (Host <> '') then
   if (Host <> Value) then
      FIdFtp.Disconnect;
  inherited SetHost(Value);
end;

procedure TFTPTransfer.SetOnStatus(Value: TIdStatusEvent);
begin
  FIdFtp.OnStatus := Value;
end;

procedure TFTPTransfer.SetProxy(ProxyObj: TPersistent);
begin
  FIdFtp.ProxySettings.Assign(ProxyObj);
end;

procedure TFTPTransfer.SetProxy(ProxyInfo: TProxySeting);
begin
  FIdFtp.ProxySettings.ProxyType := fpcmUserSite;
  FIdFtp.ProxySettings.Host := ProxyInfo.ProxyServer;
  FIdFtp.ProxySettings.UserName := ProxyInfo.ProxyUser;
  FIdFtp.ProxySettings.Port := ProxyInfo.ProxyPort;
  FIdFtp.ProxySettings.Password := ProxyInfo.ProxyPass;
end;

procedure TFTPTransfer.WorkStart(Sender: TObject; AWorkMode: TWorkMode; const
        AWorkCountMax: Integer);
begin
  //inherited WordStart(Sender, AWorkMode, AWorkCountMax);
  if (Assigned(OnTransferStart))  then
    if (AWorkCountMax > 0) then
      inherited WorkStart(Sender, AWorkMode, AWorkCountMax)
    else
      inherited WorkStart(Sender, AWorkMode, FIdFtp.Size(Self.FileName));
      //OnTransferStart(Sender, );
end;

procedure TFTPTransfer.ClearProxySeting;
begin
  // TODO -cMM: TFTPTransfer.ClearProxySeting default body inserted
  inherited;
  FIdFtp.ProxySettings.ProxyType := fpcmNone;
end;

{
******************************* TTransferFactory *******************************
}
constructor TTransferFactory.Create;
begin
  inherited Create;
  FObjectList := TObjectList.Create;
  FIdURI := TIdURI.Create;
end;

destructor TTransferFactory.Destroy;
begin
  FreeAndNil(FObjectList);
  FreeAndNil(FIdURI);
  inherited Destroy;
end;

function TTransferFactory.CreateTransfer(URL:  String): TTransfer;
var
  Index: Integer;
begin
  //测试代理的代码
  //ProxyObj := TIdFtpProxySettings.Create;
  //ProxyObj.Host := '192.168.168.163';
  //ProxyObj.ProxyType := fpcmUserSite;
  //ProxyObj.Port := 2121;

  FIdURI.URI := URL;
  if AnsiUpperCase(FIdURI.Protocol) = 'FTP' then
  begin
    Index := FObjectList.FindInstanceOf(TFTPTransfer);
    if Index <> -1 then
      Result := FObjectList.Items[Index] as TTransfer
    else
    begin
    begin
      Result := TFTPTransfer.Create;
      FObjectList.Add(Result);
    end;
    end;
    Result.URI := FIdURI;
  end
  else
    raise ExceptionNoSuport.Create('不支持的网络协议!');
end;


function TTransferFactory.CreateTransfer(URL: String;
  ProxySeting: TProxySeting): TTransfer;
begin
  Result := CreateTransfer(URL);
  Result.SetProxy(ProxySeting);
end;

end.

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -