File "class.ftp.inc"
Full Path: /home/analogde/www/Code03/inc/class.ftp.inc
File size: 7.89 KB
MIME-type: text/x-php
Charset: utf-8
<?php
//
// $Id: class.ftp.inc,v1.0 2004-12-18 12:27a EST Onion Exp $
//
/*
* FTP Class
*/
class FTP {
/*
* Public Properties
*/
public $host = '';
public $port = 21;
public $user = '';
public $pass = '';
public $show_pass = false;
public $welcome_msg = '';
/*
* Private Properties
*/
private $ftp_sock;
private $data_sock;
private $command_log = array ();
private $response_log = array ();
private $full_log = array ();
/*
* Constructor
*
* void __construct ( string host [, int port [, string user [, string pass [, bool show_pass ]]]] )
*/
public function __construct ( $host, $port = 21, $user = 'anonymous', $pass = 'root@localhost', $show_pass = false ) {
$this->host = $host;
$this->port = (int) $port;
$this->user = $user;
$this->pass = $pass;
$this->show_pass = $show_pass;
$this->ftp_sock = new Socket ($host, $port);
$this->welcome_msg = implode ('', $this->get_log (2));
$this->write ('USER '.$user);
$this->write ('PASS '.$pass);
}
/*
* Destructor
*
* void __destruct ( void )
*/
public function __destruct ( ) {
$this->write ('QUIT');
}
/*
* Public Methods
*/
/*
* FTP::is_ok ()
*
* Returns true if an error has not occured.
*
* bool is_ok ( void )
*/
public function is_ok ( ) {
return ($this->get_last_response_num () < 500);
}
//
// XXX NOTE: Refer to http://faqs.org/rfcs/rfc959.html for explanation of various FTP commands. XXX
//
/*
* FTP::allo ()
*
* bool allo ( int size )
*/
public function allo ( $size ) {
$this->write ('ALLO '.$size);
return $this->is_ok ();
}
/*
* FTP::cwd ()
*
* bool cwd ( string dir )
*/
public function cwd ( $dir ) {
$this->write ('CWD '.$dir);
return $this->is_ok ();
}
/*
* FTP::cdup ()
*
* bool cdup ( void )
*/
public function cdup ( ) {
$this->write ('CDUP');
return $this->is_ok ();
}
/*
* FTP::dele ()
*
* bool dele ( string file_path )
*/
public function dele ( $file_path ) {
$this->write ('DELE '.$file_path);
return $this->is_ok ();
}
/*
* FTP::ls ()
*
* Refer to "LIST" in the RFC.
*
* mixed ls ( [ string dir ] )
*/
public function ls ( $dir = null ) {
$this->pasv (&$addr, &$port);
$this->type ('A');
$this->write ('LIST'.($dir === null ? '' : ' '.$dir));
return $this->is_ok () ? $this->data_sock->get_contents () : false;
}
/*
* FTP::mkd ()
*
* bool mkd ( string dir_name )
*/
public function mkd ( $dir_name ) {
$this->write ('MKD '.$dir_name);
return $this->is_ok ();
}
/*
* FTP::nlst ()
*
* mixed nlst ( [ string dir ] )
*/
public function nlst ( $dir = null ) {
$this->pasv (&$addr, &$port);
$this->type ('A');
$this->write ('NLST'.($dir === null ? '' : ' '.$dir));
return $this->is_ok () ? $this->data_sock->get_contents () : false;
}
/*
* FTP::pasv ()
*
* Currently the only way this thing can transfer data with a server.
*
* bool pasv ( string &addr, int &port )
*/
public function pasv ( &$addr, &$port ) {
$this->write ('PASV');
if ($this->is_ok ()) {
if (preg_match ('#(\d{1,3}),(\d{1,3}),(\d{1,3}),(\d{1,3}),(\d{1,3}),(\d{1,3})#', $this->get_last_response_str (), $p)) {
$addr = vsprintf ('%d.%d.%d.%d', array ($p[1], $p[2], $p[3], $p[4]));
$port = (int) ((int) $p[5] << 8) + $p[6];
$this->data_sock = new Socket ($addr, $port);
return true;
} else {
// debugger crap
$debug = new Debugger (__FILE__, __CLASS__, end (explode ('::', __METHOD__)), __LINE__, '$addr should be an IP. $port should be a valid port.', 'something else', array ('this' => $this, 'this->get_last_response_str ()' => $this->get_last_response_str (), 'this->full_log' => $this->full_log));
foot ('<pre>'.htmlentities ($debug->__toString ()).'</pre>');
}
}
return false;
}
/*
* FTP::port ()
*
* This would be the other way, but I can't do it right now (read the "TODO" file for why).
*
* void port ( void )
*/
public function port ( ) {
// define this later
}
/*
* FTP::pwd ()
*
* string pwd ( void )
*/
public function pwd ( ) {
$this->write ('PWD');
if (preg_match ('#"(.*?)"#', $this->get_last_response_str (), $pwd_match)) {
return $pwd_match[1];
} else {
// debugger crap
$debug = new Debugger (__FILE__, __CLASS__, end (explode ('::', __METHOD__)), __LINE__, 'current directory', print_r ($pwd_match, 1), array ('this' => $this, 'this->get_last_response_str ()' => $this->get_last_response_str (), 'this->full_log' => $this->full_log, 'pwd_match' => $pwd_match));
foot ('<pre>'.htmlentities ($debug->__toString ()).'</pre>');
}
}
/*
* FTP::rename ()
*
* Refer to "RNFR" and "RNTO" in the RFC.
*
* bool rename ( string from, string to )
*/
public function rename ( $from, $to ) {
$this->write ('RNFR '.$from);
$this->write ('RNTO '.$to);
return $this->is_ok ();
}
/*
* FTP::retr ()
*
* mixed retr ( string file_name )
*/
public function retr ( $file_name ) {
$this->pasv (&$addr, &$port);
$this->write ('RETR '.$file_name);
return $this->is_ok () ? $this->data_sock->get_contents () : false;
}
/*
* FTP::rmd ()
*
* bool rmd ( string dir_name )
*/
public function rmd ( $dir_name ) {
$this->write ('RMD '.$dir_name);
return $this->is_ok ();
}
/*
* FTP::site ()
*
* bool site ( string cmd )
*/
public function site ( $cmd ) {
$this->write ('SITE '.$cmd);
return $this->is_ok ();
}
/*
* FTP::stor ()
*
* bool stor ( string local_filename [, string remote_filename ] )
*/
public function stor ( $local_filename, $remote_filename = null ) {
$remote_filename === null ? $remote_filename = $local_filename : '';
$this->pasv (&$addr, &$port);
$this->write ('STOR '.$remote_filename);
if ($this->is_ok ()) {
$this->data_sock->write (file_get_contents ($local_filename));
}
return $this->is_ok ();
}
/*
* FTP::syst ()
*
* mixed syst ( void )
*/
public function syst ( ) {
$this->write ('SYST');
return $this->is_ok () ? $this->get_last_response_str () : false;
}
/*
* FTP::type ()
*
* bool type ( string type )
*/
public function type ( $type ) {
$this->write ('TYPE '.$type);
return $this->is_ok ();
}
/*
* FTP::get_log ()
*
* Returns one of the three logs.
*
* mixed get_log ( int type )
*/
public function get_log ( $type = 0 ) {
switch ($type) {
case 0:
return $this->full_log;
case 1:
return $this->command_log;
case 2:
return $this->response_log;
default:
return false;
}
}
/*
* FTP::get_last_command ()
*
* Returns the last command sent to the server.
*
* string get_last_command ( void )
*/
public function get_last_command ( ) {
return end ($this->command_log);
}
/*
* FTP::get_last_response ()
*
* Returns the last reponse given from the server.
*
* string get_last_response ( void )
*/
public function get_last_response ( ) {
return end ($this->response_log);
}
/*
* FTP::get_last_response_num ()
*
* Returns the last reponse number given from the server.
*
* int get_last_response_num ( void )
*/
public function get_last_response_num ( ) {
return preg_match ('#^(\d{1,3})#', $this->get_last_response (), $matches) ? (int) $matches[1] : 0;
}
/*
* FTP::get_last_response_str ()
*
* Returns the last reponse message given from the server.
*
* string get_last_response_str ( void )
*/
public function get_last_response_str ( ) {
return preg_match ('#^\d+(.*)$#', $this->get_last_response (), $matches) ? trim ($matches[1]) : '';
}
/*
* Private Methods
*/
/*
* FTP::write ()
*
* Sends a command to the server and logs stuff.
*
* void write ( string cmd )
*/
private function write ( $cmd ) {
$this->ftp_sock->write ("$cmd\r\n");
$cmd_str = (!$this->show_pass && preg_match ('#^PASS#', $cmd) ? 'PASS xxx' : $cmd)."\r\n";
$this->command_log[] = $cmd_str;
$this->full_log[] = $cmd_str;
for (;$line = $this->ftp_sock->get_line (); $this->response_log[] = $line, $this->full_log[] = $line);
}
}