660 行
		
	
	
		
			无行尾
		
	
	
		
			12 KiB
		
	
	
	
		
			PHP
		
	
	
	
	
	
			
		
		
	
	
			660 行
		
	
	
		
			无行尾
		
	
	
		
			12 KiB
		
	
	
	
		
			PHP
		
	
	
	
	
	
| <?php  if ( ! defined('BASEPATH')) exit('No direct script access allowed');
 | |
| /**
 | |
|  * CodeIgniter
 | |
|  *
 | |
|  * An open source application development framework for PHP 5.1.6 or newer
 | |
|  *
 | |
|  * @package		CodeIgniter
 | |
|  * @author		ExpressionEngine Dev Team
 | |
|  * @copyright	Copyright (c) 2008 - 2011, EllisLab, Inc.
 | |
|  * @license		http://codeigniter.com/user_guide/license.html
 | |
|  * @link		http://codeigniter.com
 | |
|  * @since		Version 1.0
 | |
|  * @filesource
 | |
|  */
 | |
| 
 | |
| // ------------------------------------------------------------------------
 | |
| 
 | |
| /**
 | |
|  * FTP Class
 | |
|  *
 | |
|  * @package		CodeIgniter
 | |
|  * @subpackage	Libraries
 | |
|  * @category	Libraries
 | |
|  * @author		ExpressionEngine Dev Team
 | |
|  * @link		http://codeigniter.com/user_guide/libraries/ftp.html
 | |
|  */
 | |
| class CI_FTP {
 | |
| 
 | |
| 	var $hostname	= '';
 | |
| 	var $username	= '';
 | |
| 	var $password	= '';
 | |
| 	var $port		= 21;
 | |
| 	var $passive	= TRUE;
 | |
| 	var $debug		= FALSE;
 | |
| 	var $conn_id	= FALSE;
 | |
| 
 | |
| 
 | |
| 	/**
 | |
| 	 * Constructor - Sets Preferences
 | |
| 	 *
 | |
| 	 * The constructor can be passed an array of config values
 | |
| 	 */
 | |
| 	public function __construct($config = array())
 | |
| 	{
 | |
| 		if (count($config) > 0)
 | |
| 		{
 | |
| 			$this->initialize($config);
 | |
| 		}
 | |
| 
 | |
| 		log_message('debug', "FTP Class Initialized");
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Initialize preferences
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	array
 | |
| 	 * @return	void
 | |
| 	 */
 | |
| 	function initialize($config = array())
 | |
| 	{
 | |
| 		foreach ($config as $key => $val)
 | |
| 		{
 | |
| 			if (isset($this->$key))
 | |
| 			{
 | |
| 				$this->$key = $val;
 | |
| 			}
 | |
| 		}
 | |
| 
 | |
| 		// Prep the hostname
 | |
| 		$this->hostname = preg_replace('|.+?://|', '', $this->hostname);
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * FTP Connect
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	array	 the connection values
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function connect($config = array())
 | |
| 	{
 | |
| 		if (count($config) > 0)
 | |
| 		{
 | |
| 			$this->initialize($config);
 | |
| 		}
 | |
| 
 | |
| 		if (FALSE === ($this->conn_id = @ftp_connect($this->hostname, $this->port)))
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_connect');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		if ( ! $this->_login())
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_login');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Set passive mode if needed
 | |
| 		if ($this->passive == TRUE)
 | |
| 		{
 | |
| 			ftp_pasv($this->conn_id, TRUE);
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * FTP Login
 | |
| 	 *
 | |
| 	 * @access	private
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function _login()
 | |
| 	{
 | |
| 		return @ftp_login($this->conn_id, $this->username, $this->password);
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Validates the connection ID
 | |
| 	 *
 | |
| 	 * @access	private
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function _is_conn()
 | |
| 	{
 | |
| 		if ( ! is_resource($this->conn_id))
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_no_connection');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 
 | |
| 	/**
 | |
| 	 * Change directory
 | |
| 	 *
 | |
| 	 * The second parameter lets us momentarily turn off debugging so that
 | |
| 	 * this function can be used to test for the existence of a folder
 | |
| 	 * without throwing an error.  There's no FTP equivalent to is_dir()
 | |
| 	 * so we do it by trying to change to a particular directory.
 | |
| 	 * Internally, this parameter is only used by the "mirror" function below.
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @param	bool
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function changedir($path = '', $supress_debug = FALSE)
 | |
| 	{
 | |
| 		if ($path == '' OR ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		$result = @ftp_chdir($this->conn_id, $path);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE AND $supress_debug == FALSE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_changedir');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Create a directory
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function mkdir($path = '', $permissions = NULL)
 | |
| 	{
 | |
| 		if ($path == '' OR ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		$result = @ftp_mkdir($this->conn_id, $path);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_makdir');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Set file permissions if needed
 | |
| 		if ( ! is_null($permissions))
 | |
| 		{
 | |
| 			$this->chmod($path, (int)$permissions);
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Upload a file to the server
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @param	string
 | |
| 	 * @param	string
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function upload($locpath, $rempath, $mode = 'auto', $permissions = NULL)
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		if ( ! file_exists($locpath))
 | |
| 		{
 | |
| 			$this->_error('ftp_no_source_file');
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Set the mode if not specified
 | |
| 		if ($mode == 'auto')
 | |
| 		{
 | |
| 			// Get the file extension so we can set the upload type
 | |
| 			$ext = $this->_getext($locpath);
 | |
| 			$mode = $this->_settype($ext);
 | |
| 		}
 | |
| 
 | |
| 		$mode = ($mode == 'ascii') ? FTP_ASCII : FTP_BINARY;
 | |
| 
 | |
| 		$result = @ftp_put($this->conn_id, $rempath, $locpath, $mode);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_upload');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Set file permissions if needed
 | |
| 		if ( ! is_null($permissions))
 | |
| 		{
 | |
| 			$this->chmod($rempath, (int)$permissions);
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Download a file from a remote server to the local server
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @param	string
 | |
| 	 * @param	string
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function download($rempath, $locpath, $mode = 'auto')
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Set the mode if not specified
 | |
| 		if ($mode == 'auto')
 | |
| 		{
 | |
| 			// Get the file extension so we can set the upload type
 | |
| 			$ext = $this->_getext($rempath);
 | |
| 			$mode = $this->_settype($ext);
 | |
| 		}
 | |
| 
 | |
| 		$mode = ($mode == 'ascii') ? FTP_ASCII : FTP_BINARY;
 | |
| 
 | |
| 		$result = @ftp_get($this->conn_id, $locpath, $rempath, $mode);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_download');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Rename (or move) a file
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @param	string
 | |
| 	 * @param	bool
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function rename($old_file, $new_file, $move = FALSE)
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		$result = @ftp_rename($this->conn_id, $old_file, $new_file);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$msg = ($move == FALSE) ? 'ftp_unable_to_rename' : 'ftp_unable_to_move';
 | |
| 
 | |
| 				$this->_error($msg);
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Move a file
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @param	string
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function move($old_file, $new_file)
 | |
| 	{
 | |
| 		return $this->rename($old_file, $new_file, TRUE);
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Rename (or move) a file
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function delete_file($filepath)
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		$result = @ftp_delete($this->conn_id, $filepath);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_delete');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Delete a folder and recursively delete everything (including sub-folders)
 | |
| 	 * containted within it.
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function delete_dir($filepath)
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Add a trailing slash to the file path if needed
 | |
| 		$filepath = preg_replace("/(.+?)\/*$/", "\\1/",  $filepath);
 | |
| 
 | |
| 		$list = $this->list_files($filepath);
 | |
| 
 | |
| 		if ($list !== FALSE AND count($list) > 0)
 | |
| 		{
 | |
| 			foreach ($list as $item)
 | |
| 			{
 | |
| 				// If we can't delete the item it's probaly a folder so
 | |
| 				// we'll recursively call delete_dir()
 | |
| 				if ( ! @ftp_delete($this->conn_id, $item))
 | |
| 				{
 | |
| 					$this->delete_dir($item);
 | |
| 				}
 | |
| 			}
 | |
| 		}
 | |
| 
 | |
| 		$result = @ftp_rmdir($this->conn_id, $filepath);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_delete');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Set file permissions
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string	the file path
 | |
| 	 * @param	string	the permissions
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function chmod($path, $perm)
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Permissions can only be set when running PHP 5
 | |
| 		if ( ! function_exists('ftp_chmod'))
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_chmod');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		$result = @ftp_chmod($this->conn_id, $perm, $path);
 | |
| 
 | |
| 		if ($result === FALSE)
 | |
| 		{
 | |
| 			if ($this->debug == TRUE)
 | |
| 			{
 | |
| 				$this->_error('ftp_unable_to_chmod');
 | |
| 			}
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		return TRUE;
 | |
| 	}
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * FTP List files in the specified directory
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @return	array
 | |
| 	 */
 | |
| 	function list_files($path = '.')
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		return ftp_nlist($this->conn_id, $path);
 | |
| 	}
 | |
| 
 | |
| 	// ------------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Read a directory and recreate it remotely
 | |
| 	 *
 | |
| 	 * This function recursively reads a folder and everything it contains (including
 | |
| 	 * sub-folders) and creates a mirror via FTP based on it.  Whatever the directory structure
 | |
| 	 * of the original file path will be recreated on the server.
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string	path to source with trailing slash
 | |
| 	 * @param	string	path to destination - include the base folder with trailing slash
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function mirror($locpath, $rempath)
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		// Open the local file path
 | |
| 		if ($fp = @opendir($locpath))
 | |
| 		{
 | |
| 			// Attempt to open the remote file path.
 | |
| 			if ( ! $this->changedir($rempath, TRUE))
 | |
| 			{
 | |
| 				// If it doesn't exist we'll attempt to create the direcotory
 | |
| 				if ( ! $this->mkdir($rempath) OR ! $this->changedir($rempath))
 | |
| 				{
 | |
| 					return FALSE;
 | |
| 				}
 | |
| 			}
 | |
| 
 | |
| 			// Recursively read the local directory
 | |
| 			while (FALSE !== ($file = readdir($fp)))
 | |
| 			{
 | |
| 				if (@is_dir($locpath.$file) && substr($file, 0, 1) != '.')
 | |
| 				{
 | |
| 					$this->mirror($locpath.$file."/", $rempath.$file."/");
 | |
| 				}
 | |
| 				elseif (substr($file, 0, 1) != ".")
 | |
| 				{
 | |
| 					// Get the file extension so we can se the upload type
 | |
| 					$ext = $this->_getext($file);
 | |
| 					$mode = $this->_settype($ext);
 | |
| 
 | |
| 					$this->upload($locpath.$file, $rempath.$file, $mode);
 | |
| 				}
 | |
| 			}
 | |
| 			return TRUE;
 | |
| 		}
 | |
| 
 | |
| 		return FALSE;
 | |
| 	}
 | |
| 
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Extract the file extension
 | |
| 	 *
 | |
| 	 * @access	private
 | |
| 	 * @param	string
 | |
| 	 * @return	string
 | |
| 	 */
 | |
| 	function _getext($filename)
 | |
| 	{
 | |
| 		if (FALSE === strpos($filename, '.'))
 | |
| 		{
 | |
| 			return 'txt';
 | |
| 		}
 | |
| 
 | |
| 		$x = explode('.', $filename);
 | |
| 		return end($x);
 | |
| 	}
 | |
| 
 | |
| 
 | |
| 	// --------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Set the upload type
 | |
| 	 *
 | |
| 	 * @access	private
 | |
| 	 * @param	string
 | |
| 	 * @return	string
 | |
| 	 */
 | |
| 	function _settype($ext)
 | |
| 	{
 | |
| 		$text_types = array(
 | |
| 							'txt',
 | |
| 							'text',
 | |
| 							'php',
 | |
| 							'phps',
 | |
| 							'php4',
 | |
| 							'js',
 | |
| 							'css',
 | |
| 							'htm',
 | |
| 							'html',
 | |
| 							'phtml',
 | |
| 							'shtml',
 | |
| 							'log',
 | |
| 							'xml'
 | |
| 							);
 | |
| 
 | |
| 
 | |
| 		return (in_array($ext, $text_types)) ? 'ascii' : 'binary';
 | |
| 	}
 | |
| 
 | |
| 	// ------------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Close the connection
 | |
| 	 *
 | |
| 	 * @access	public
 | |
| 	 * @param	string	path to source
 | |
| 	 * @param	string	path to destination
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function close()
 | |
| 	{
 | |
| 		if ( ! $this->_is_conn())
 | |
| 		{
 | |
| 			return FALSE;
 | |
| 		}
 | |
| 
 | |
| 		@ftp_close($this->conn_id);
 | |
| 	}
 | |
| 
 | |
| 	// ------------------------------------------------------------------------
 | |
| 
 | |
| 	/**
 | |
| 	 * Display error message
 | |
| 	 *
 | |
| 	 * @access	private
 | |
| 	 * @param	string
 | |
| 	 * @return	bool
 | |
| 	 */
 | |
| 	function _error($line)
 | |
| 	{
 | |
| 		$CI =& get_instance();
 | |
| 		$CI->lang->load('ftp');
 | |
| 		show_error($CI->lang->line($line));
 | |
| 	}
 | |
| 
 | |
| 
 | |
| }
 | |
| // END FTP Class
 | |
| 
 | |
| /* End of file Ftp.php */
 | |
| /* Location: ./system/libraries/Ftp.php */ |