Sources
Delphi Russian Knowledge Base
DRKB - это самая большая и удобная в использовании база знаний по Дельфи в рунете, составленная Виталием Невзоровым

Разбор адреса FTP

01.01.2007
{ **** UBPFD *********** by kladovka.net.ru ****
>> Разбор адреса FTP
 
Функция анализирует строку aSrc и если в стоке дан корректный адрес FTP, возвращает имя пользователя, пароль, хост, порт и каталог. Если дан некорректный адрес, функция возвращает false, иначе - true.
Учтена возможность, когда в адресе не указываются некоторые параметры. В этом случае, если нотация соблюдена, опущенные параметры возвращаются пустыми строками.
 
Минимально подробный адрес: ftp://myftp.ru - В этом случае будет возвращён адрес, порт по умолчанию (21) и true.
Максимально подробный адрес: ftp://MyLogin:MyPassword@MyFtp.ru:6000/MyDirectory/ - Будут возвращены все параметры и true.
 
Зависимости: Classes, SysUtils
Автор:       Роман Василенко, romix@nm.ru, ICQ:826361, Пятигорск
Copyright:   Роман Василенко
Дата:        13 июня 2004 г.
********************************************** }
 
function ParseFTP(aSrc: string; out oUserName, oPassword, oHost: string;
   
out oPort: word; out oDir: string): boolean;
const
    ssPrefix
= 0;
    ssUserName
= 1;
    ssPassword
= 2;
    ssHost
= 3;
    ssPort
= 4;
    ssDir
= 5;
var
    f
, StrState: integer;
    sPort
, pfx: string;
begin
    oUserName
:='';
    oPassword
:='';
    oHost
:='';
    sPort
:='';
    oPort
:=21;
    oDir
:='';
   
StrState:=ssPrefix;
    result
:=false;
    f
:=1;
    repeat
       
case StrState of
            ssPrefix
: //Разбор префикса ftp:// и определение анонимности адреса
           
if aSrc[f]<>':' then
                pfx
:=pfx+aSrc[f]
           
else begin
               
if (ansisametext(trim(pfx),'ftp')) and
                   
(aSrc[f]+aSrc[f+1]+aSrc[f+2]='://') then begin
                   
if pos('@',aSrc)<1 then
                       
StrState:=ssHost //Anonymous
                   
else
                       
StrState:=ssUserName; //UserName[:Password]
                    inc
(f,2);
               
end else break;
           
end;
            ssUserName
: //Извлечение имени пользователя
           
if aSrc[f]='@' then //Пароль не указан
               
StrState:=ssHost
           
else
               
if aSrc[f]=':' then //Пароль указан
                   
StrState:=ssPassword
               
else
                    oUserName
:=oUserName+aSrc[f];
            ssPassword
: //Извлечение пароля
           
if aSrc[f]='@' then
               
StrState:=ssHost
           
else
                oPassword
:=oPassword+aSrc[f];
            ssHost
: //Извлечение хоста
           
if aSrc[f]=':' then //Порт указан
               
StrState:=ssPort
           
else
               
if aSrc[f]='/' then //Порт не указан, возможно указан каталог
                   
StrState:=ssDir
               
else
                    oHost
:=oHost+aSrc[f];
            ssPort
: //Извлечение порта
           
if aSrc[f]='/' then
               
StrState:=ssDir
           
else
                sPort
:=sPort+aSrc[f];
            ssDir
: oDir:=oDir+aSrc[f];
       
end;
        inc
(f);
   
until f>length(aSrc);
   
if (StrState>ssPassword) and (trim(oHost)<>'') then
        result
:=true;
   
try
       
if trim(sPort)<>'' then oPort:=strtoint(sPort);
   
except
        result
:=false;
   
end;
end;

Пример использования:

...
 
procedure TForm1
.Button1Click(Sender: TObject);
const
    yn
: array[false..true] of string=('INVALID', 'VALID');
var
    xValid
: boolean;
    xUser
, xPassword, xHost, xDir: string;
    xPort
: word;
begin
    xValid
:=ParseFTP(Edit1.Text, xUser, xPassword, xHost, xPort, xDir);
   
ShowMessage(format('Address is %s'#13#13'Host: %s'#13'Port: %d'#13+
       
'Dir: %s'#13'User: %s'#13'Password: %s',
       
[yn[xValid], xHost, xPort, xDir, xUser, xPassword]));
end;
 
...