• Постановка задачи
  • Разработка формы
  • Разработка программного кода
  • Полный исходный код модуля
  • Глава 18

    FTP-клиент

    Постановка задачи

    Разработать FTP-клиент. Программа должна соединяться с FTP-cepвером, проходить аутентификацию и предоставлять пользователю возможность работать с файлами, которые находятся на сервере. У пользователя должна быть возможность передавать и получать файлы, создавать и удалять каталоги и т.п. Также пользователь может выполнять свои собственные команды на сервере.

    Разработка формы

    Создайте новый проект Delphi. Приготовьтесь к тому, что форма получится довольно большой (ширина — около 800 пикселей) и будет содержать большое количество разных кнопок и полей ввода. Присвойте ей заголовок FTP-client (свойство Caption) и разместите компоненты согласно табл. 18.1.

    Таблица 18.1. Свойства формы FTP-клиента

    Компонент Свойство Значение Пояснение
    Label1 (категория Standard) Caption FTP-сервер Надпись метки
    Left 56 Отступ слева
    Top 16 Отступ сверху
    Label2 Caption Имя пользователя Надпись метки
    Left 16 Отступ слева
    Top 48 Отступ сверху
    Label3 Caption Пароль Надпись метки
    Left 72 Отступ слева
    Top 80 Отступ сверху
    Edit1 (категория Standard) Name ftpserver Новое имя компонента
    Text ftp.narod.ru  Адрес FTP-сервера
    Left 120 Отступ слева
    Top 8 Отступ сверху
    Edit2 Name name Новое имя компонента
    Text test6001 Имя пользователя
    Left 120 Отступ слева
    Top 40 Отступ сверху
    Edit3 Name pass Новое имя компонента
    Left 120 Отступ слева
    Top 72 Отступ сверху
    Edit4 Name port Новое имя компонента
    Text 21 Имя пользователя
    Left 120 Отступ слева
    Top 104 Отступ сверху
    Edit5 Name del Новое имя компонента
    Left 512 Отступ слева
    Top 8 Отступ сверху
    Edit6 Name cd Новое имя компонента
    Left 512 Отступ слева
    Top 40 Отступ сверху
    Edit7 Name cmd Новое имя компонента
    Left 512 Отступ слева
    Top 72 Отступ сверху
    Edit8 Name md Новое имя компонента
    Left 512 Отступ слева
    Top 104 Отступ сверху
    Edit9 Name rd Новое имя компонента
    Left 512 Отступ слева
    Top 136 Отступ сверху
    Edit10 Name download Новое имя компонента
    Left 512 Отступ слева
    Top 168 Отступ сверху
    Button1 (категория Standard) Caption Подключиться Надпись на кнопке
    Left 8 Отступ слева
    Top 144 Отступ сверху
    Button2 Caption Отключиться Надпись на кнопке
    Left 123 Отступ слева
    Top 144 Отступ сверху
    Button3 Caption Загрузить файл на сервер Надпись на кнопке
    Left 512 Отступ слева
    Top 200 Отступ сверху
    Button4 Caption Удалить Надпись на кнопке
    Left 672 Отступ слева
    Top 8 Отступ сверху
    Button5 Caption Изменить каталог Надпись на кнопке
    Left 672 Отступ слева
    Top 40 Отступ сверху
    Button6 Caption Выполнить команду Надпись на кнопке
    Left 672 Отступ слева
    Top 72 Отступ сверху
    Button7 Caption Создать каталог Надпись на кнопке
    Left 672 Отступ слева
    Top 104 Отступ сверху
    Button8 Caption Удалить каталог Надпись на кнопке
    Left 672 Отступ слева
    Top 136 Отступ сверху
    Button9 Caption Скачать файл Надпись на кнопке
    Left 672 Отступ слева
    Top 168 Отступ сверху
    Memo (категория Standard) Name status1 Новое имя компонента, предназначенного для отображения состояния соединения
    Lines Статус: Текст в поле
    Left 264 Отступ слева
    Top 8 Отступ сверху
    Height 217 Высота
    Width 233 Ширина
    OpenDialog (категория Dialogs) Name Open1 Новое имя компонента, который будет использоваться для открытия файлов
    SaveDialog (категория Dialogs) Name Save1 Новое имя компонента, который будет использоваться для сохранения файлов
    NMFTP (категория FastNet) Name ftp Новое имя главного компонента программы

    Полученная форма должна соответствовать рис. 18.1.

    Рис. 18.1. Форма FTP-клиента

    Разработка программного кода

    Обработаем нажатия кнопок соединения и отключения от сервера. Обработчик события OnClick для кнопки Подключиться:

    procedure TForm1.Button1Click(sender: TObject);

    begin

     ftp.Host:= ftpserver.Text; //ftp-сервер

     ftp.UserID:= name.Text;//логин

     ftp.Password:= pass.Text;// пароль

     ftp.Port:= StrToInt(port.Text); //порт для подключения

     //соединяемся с сервером

     if not ftp.Connected then ftp.Connect;

    end;

    Здесь мы считываем все данные, которые необходимы для соединения с сервером. После этого мы пытаемся соединиться с сервером. Об успешности этой операции можно будет узнать в поле состояния.

    Обработаем нажатие кнопки Отключиться:

    procedure TForm1.Button2Click(Sender: TObject);

    begin

     if ftp.Connected then//если соединен

      ftp.Disconnect;//отключиться от сервера

    end;

    Если при нажатии кнопки Отключиться установлено соединение с сервером, то мы разрываем его.

    Теперь обработаем нажатие кнопок, которые служат для работы с сервером. Обработчик события OnClick для кнопки Удалить:

    procedure TForm1.Button4Click(Sender : TObject);

    begin

     ftp.Delete(del.text); //удалить файл

    end;

    Здесь мы удаляем файл, имя которого пользователь ввел в поле рядом с кнопкой.

    Обработаем нажатие кнопки Изменить каталог:

    procedure TForm1.Button5Click(Sender: TObject);

    begin

     ftp.ChangeDir(cd.Text); //изменяем каталог

    end;

    Устанавливаем текущим тот каталог, который указан в поле cd.

    Обработаем нажатие кнопки Выполнить команду:

    procedure TForm1.Button6Click(Sender: TObject);

    begin

     ftp.DoCommand(cmd.Text); //выполнение команды

    end;

    При работе с сервером мы предоставляем пользователю возможность работать не только с помощью команд, предусмотренных в интерфейсе, но и выполнять на сервере любые произвольные команды. Для этого у нас есть поле cmd, в котором пользователь вводит команду, и кнопка Выполнить команду, по нажатию которой введенная команда выполняется.

    Обработаем нажатие кнопки Создать каталог:

    procedure TForm1.Button7Click(Sender: TObject);

    begin

     ftp.MakeDirectory(md.Text); //создать каталог

    end;

    Обработаем нажатие кнопки Удалить каталог:

    procedure TForm1.Button8Click(Sender: TObject);

    begin

     ftp.RemoveDir(rd.Text); //удалить каталог

    end;

    Обработаем нажатие кнопки Скачать файл:

    procedure TForm1.Button9Click(Sender: TObject);

    begin

     //открытие диалогового окна сохранения файла

     if Save1.Execute

     then //скачиваем указанный файл

      ftp.Download(download.Text, save1.FileName)

     else ShowMessage('File not saved!'); {если пользователь отказался сохранять файл}

    end;

    Сначала мы предлагаем пользователю указать имя и путь размещения полученного файла. Затем мы загружаем файл и размещаем его по указанному пути.

    Наконец, обработаем нажатие кнопки Загрузить файл на сервер:

    procedure TForm1.Button3Click(Sender: TObject);

    var

     i: integer;

     FName, temp: string; //для получения имени файла

    begin

     if not Open1.Execute then ShowMessage('Файл не выбран!')

     else begin

     //очищаем переменные, которые содержат имя файла

     temp:= '';

     FName:= '';

     //получаем имя файла

     for i: = Length(Open1.FileName) downto 1 do

     begin

      if Open1.FileName[i] = '\' then break;

      temp:= temp+ Open1.FileName[i];

     end;

     for i:=length(temp) downto 1 do

      fname:= fname + temp[i];

      ftp.Upload(Open1.FileName, FName); //загружаем файл

     end;

    end;

    Здесь мы сначала просим пользователя выбрать файл, который он хочет передать на сервер. Затем узнаем имя выбранного файла и загружаем его на сервер с таким же именем.

    В общем, наш ftp-клиент уже полностью работоспособен и выполняет все необходимые функции. Единственное, что осталось сделать, — реализовать извещение пользователя о протекании всех операций и обо всех ошибках. Для этого следует создать несколько обработчиков событий компонента ftp.

    Событие в случае возникновения ошибки при проверке имени и пароля — OnAuthеntiсatiоnFailed:

    procedure TForm1.ftpAuthenticationFailed(var Handled: Boolean);

    begin

     status1.Lines.Add('Неверное имя или пароль');

    end;

    Событие при подключении — OnConnect:

    procedure TForm1.ftpConnect(Sender:tobject);

    begin

     status1.Lines.Add('Подключено');

     //локальный ip-адрес

     status1Lines.Add('IP клиента: ' + ftp.LocalIP);

     //удаленный ip-адрес

     status1Lines.Add('IPсервера: ' + ftp.RemoteIP);

    end;

    Событие в случае возникновения ошибки при подключении — OnConnectionFailed:

    procedure TForm1.ftpConnectionFailed(Sender: TObject);

    begin

     status1.Lines.Add('He удалось подключиться к серверу');

    end;

    Событие при отключении от сервера — OnDisconnect:

    procedure TForm1.ftpDisconnect(Sender: TObject);

    begin

     status1.Lines.Add('Отключено');

    end;

    Событие в случае возникновения некоторой ошибки — OnError:

    procedure TForml.ftpError(Sender: TComponent; Errno: Word; Errmsg: String);

    begin

     status1.Lines.Add('Ошибка: ' + errmsg);

    end;

    Событие в случае возникновения ошибки при подключении к серверу — OnInvaIidHost:

    procedure TForm1.ftpInvalidHost(var Handled: Boolean);

    begin

     status1.Lines.Add('Ошибка при подключении к серверу');

    end;

    Событие при изменении состояния — OnStatus:

    procedure TForm1.ftpStatus(Sender: TComponent; Status: String);

    begin

     status1.Lines.Add(Status);

    end;

    Событие при успешном выполнении операции — OnSuccess:

    procedure TForm1.ftpSuccess(Trans_Type: TCmdType);

    begin

     status1.Lines.Add('Успешно');

    end;

    Событие начала передачи данных — OnTransactionStart:

    procedure TForm1.ftpTransactionStart(Sender: TObject);

    begin

     status1.Lines.Add('Начало передачи данных');

    end;

    Событие завершения передачи данных — OnTransactionStop :

    procedure TForm1.ftpTransactionStop(Sender: TObject);

    begin

     statusl.Lines.Add('Конец передачи данных');

    end;

    Теперь программа полностью готова к использованию. Если у вас нет собственного Web-сайта, то для тестирования FTP-клиента можете зарегистрировать сайт на бесплатном хостинге.

    Полный исходный код модуля

    Полный код программного модуля FTP-клиента представлен в листинге 18.1.

    Листинг 18.1. Программный модуль FTP-клиента

    unit Unit1;


    interface


    uses

     Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, Dialogs, NMFtp, StdCtrls, Psock;


    type

     TForm1 = class(TForm)

     ftp: TNMFTP;

     ftpserver: TEdit;

     Label1: TLabel;

     Label2: TLabel;

     name: TEdit;

     Label3: TLabel;

     pass: TEdit;

     Label4: TLabel;

     port: TEdit;

     Button1: TButton;

     Button2: TButton;

     status1: TMemo;

     Button3: TButton;

     Open1: TOpenDialog;

     Button4: TButton;

     del: TEdit;

     Button5: TButton;

     cd: TEdit;

     cmd: TEdit;

     Button6: TButton;

     md: TEdit;

     Button7: TButton;

     rd: TEdit;

     Button8: TButton;

     download: TEdit;

     Button9: TButton;

     Save1: TSaveDialog;

     procedure Button1Click(Sender: TObject);

     procedure ftpStatus(Sender: TComponent; Status: String);

     procedure ftpError(Sender: TComponent; Errno: Word; Errmsg : String);

     procedure ftpDisconnect(Sender: TObject);

     procedure ftpConnect(Sender: TObject);

     procedure ftpConnectionFailed(Sender: TObject);

     procedure ftpInvalidHost(var Handled: Boolean);

     procedure ftpSuccess(Trans_Type: TCmdType);

     procedure ftpTransactionStart(Sender: TObject);

     procedure ftpTransactionStop(Sender: TObject);

     procedure ftpAuthenticationFailed(var Handled: Boolean);

     procedure Button2Click(Sender: TObject);

     procedure Button3Click(Sender: TObject);

     procedure FormDestroy(Sender: TObject);

     procedure Button5Click(Sender: TObject);

     procedure Button4Click(Sender: TObject);

     procedure Button6Click(Sender: TObject);

     procedure Button7Click(Sender: TObject);

     procedure Button8Click(Sender: TObject);

     procedure Button9Click(Sender: TObject);

    private

     { Private declarations }

    public

     { Public declarations }

    end;


    var

     Form1: TForm1;


    implementation

    {$R *.dfm}


    procedure TForm1.Button1Click(sender: TObject);

    begin

     ftp.Host:= ftpserver.Text; //ftp-сервер

     ftp.UserID:= name.Text;//логин

     ftp.Password:= pass.Text;// пароль

     ftp.Port:= StrToInt(port.Text); //порт для подключения

     //соединяемся с сервером

     if not ftp.Connected then ftp.Connect;

    end;


    procedure TForm1.ftpStatus(Sender: TComponent; Status: String);

    begin

     status1.Lines.Add(Status);

    end;


    procedure TForml.ftpError(Sender: TComponent; Errno: Word; Errmsg: String);

    begin

     status1.Lines.Add('Ошибка: ' + errmsg);

    end;


    procedure TForm1.ftpDisconnect(Sender: TObject);

    begin

     status1.Lines.Add('Отключено');

    end;


    procedure TForm1.ftpConnect(Sender:tobject);

    begin

     status1.Lines.Add('Подключено');

     //локальный ip-адрес

     status1Lines.Add('IP клиента: ' + ftp.LocalIP);

     //удаленный ip-адрес

     status1Lines.Add('IPсервера: ' + ftp.RemoteIP);

    end;


    procedure TForm1.ftpConnectionFailed(Sender: TObject);

    begin

     status1.Lines.Add('He удалось подключиться к серверу');

    end;


    procedure TForm1.ftpInvalidHost(var Handled: Boolean);

    begin

     status1.Lines.Add('Ошибка при подключении к серверу');

    end;


    procedure TForm1.ftpSuccess(Trans_Type: TCmdType);

    begin

     status1.Lines.Add('Успешно');

    end;


    procedure TForm1.ftpTransactionStart(Sender: TObject);

    begin

     status1.Lines.Add('Начало передачи данных');

    end;


    procedure TForm1.ftpTransactionStop(Sender: TObject);

    begin

     statusl.Lines.Add('Конец передачи данных');

    end;


    procedure TForm1.ftpAuthenticationFailed(var Handled: Boolean);

    begin

     status1.Lines.Add('Неверное имя или пароль');

    end;


    procedure TForm1.Button2Click(Sender: TObject);

    begin

     if ftp.Connected then//если соединен

      ftp.Disconnect;//отключиться от сервера

    end;


    procedure TForm1.Button3Click(Sender: TObject);

    var

     i: integer;

     FName, temp: string; //для получения имени файла

    begin

     if not Open1.Execute then ShowMessage('Файл не выбран!')

     else begin

     //очищаем переменные, которые содержат имя файла

     temp:= '';

     FName:= '';

     //получаем имя файла

     for i: = Length(Open1.FileName) downto 1 do

     begin

      if Open1.FileName[i] = '\' then break;

      temp:= temp+ Open1.FileName[i];

     end;

     for i:=length(temp) downto 1 do

      fname:= fname + temp[i];

      ftp.Upload(Open1.FileName, FName); //загружаем файл

     end;

    end;


    procedure TForm1.FormDestroy(Sender: TObject) ;

    begin

     if ftp.Connected then ftp.Disconnect;

    end;


    procedure TForm1.Button5Click(Sender: TObject);

    begin

     ftp.ChangeDir(cd.Text); //изменяем каталог

    end;


    procedure TForm1.Button4Click(Sender : TObject);

    begin

     ftp.Delete(del.text); //удалить файл

    end;


    procedure TForm1.Button6Click(Sender: TObject);

    begin

     ftp.DoCommand(cmd.Text); //выполнение команды

    end;


    procedure TForm1.Button7Click(Sender: TObject);

    begin

     ftp.MakeDirectory(md.Text); //создать каталог

    end;


    procedure TForm1.Button8Click(Sender: TObject);

    begin

     ftp.RemoveDir(rd.Text); //удалить каталог

    end;


    procedure TForm1.Button9Click(Sender: TObject);

    begin

     //открытие диалогового окна сохранения файла

     if Save1.Execute

     then //скачиваем указанный файл

      ftp.Download(download.Text, save1.FileName)

     else ShowMessage('File not saved!'); {если пользователь отказался сохранять файл}

    end;


    end.

    ⊚ Все файлы проекта и исполняемый файл рассмотренной программы находятся на прилагаемом к книге компакт-диске в папке Chapter_18.





     

    Главная | В избранное | Наш E-MAIL | Добавить материал | Нашёл ошибку | Наверх