├── README.md └── application ├── controllers └── sftp_test.php ├── language └── english │ └── sftp_lang.php └── libraries └── Sftp.php /README.md: -------------------------------------------------------------------------------- 1 | # CodeIgniter sFTP Library 2 | 3 | A CodeIgniter sFTP Library - Allows communication to a sFTP server via the CodeIgniter framework. 4 | 5 | 6 | ## Contributors 7 | 8 | Many thanks to; 9 | 10 | [Jlil](https://github.com/jlil) 11 | 12 | [tunelko](https://github.com/tunelko) 13 | 14 | [AchrafSoltani](https://github.com/AchrafSoltani) 15 | 16 | [lavluda](https://github.com/lavluda) 17 | 18 | [kjj1](https://github.com/kjj1) 19 | 20 | Ian Grice 21 | 22 | 23 | 24 | ## Requirements 25 | 26 | 1. PHP 5+ 27 | 2. CodeIgniter for 2.x 28 | 3. ssh2 extension for PHP (which in turn needs libssh2) 29 | 30 | 31 | 32 | ## Usage 33 | 34 | Have a look at `application/controllers/sftp_test.php` for an example of how to connect 35 | to a remote sFTP server, as well as a few demo commands you can run. 36 | 37 | 38 | 39 | ## libssh2 & ssh2 installation on OSX 10.9 40 | 41 | Here's an updated guide to installing this extension on OSX 10.9 (Mavericks). 42 | 43 | I'm using the default OSX PHP install (5.4.24) that comes pre-installed. This guide also assumes you're using [Homebrew](http://brew.sh/) as a package manager, and have wget installed. 44 | 45 | This is very similar to the process on this [gist](https://gist.github.com/brennanneoh/1403250). 46 | 47 | 1) Install libssh2; 48 | 49 | `brew install libssh2` 50 | 51 | 2) Install ssh2; 52 | 53 | `wget http://pecl.php.net/get/ssh2-0.11.3.tgz` 54 | 55 | `tar -zxvf ssh2-0.11.3.tgz` 56 | 57 | `cd ssh2-0.11.3` 58 | 59 | `phpize` 60 | 61 | `./configure` 62 | 63 | `make` 64 | 65 | 3) Copy your newly compiled extension (ssh2.so) into your PHP extensions directory. 66 | 67 | `sudo cp modules/ssh2.so /usr/lib/php/extensions/no-debug-non-zts-20100525` 68 | 69 | 4) Add the extension to the php.ini. Just add the following text to the php.ini file; 70 | 71 | `extension=ssh2.so` 72 | 73 | 6) Restart apache and run php info to see if the extension has been loaded; 74 | 75 | `php -i | grep ssh2` 76 | 77 | 78 | You should be good to go from here! 79 | 80 | The main thing is that libssh2, ssh2 and php are all the same architecture (32 or 64bit). -------------------------------------------------------------------------------- /application/controllers/sftp_test.php: -------------------------------------------------------------------------------- 1 | load->library('sftp'); 11 | 12 | } 13 | 14 | 15 | //-----------------------------------------------------------------------------------> 16 | // private functions 17 | //-----------------------------------------------------------------------------------> 18 | 19 | //-----------------------------------------------------------------------------------> 20 | // end private functions 21 | //-----------------------------------------------------------------------------------> 22 | 23 | function index() { 24 | 25 | /* 26 | The sFTP config. These are the credentials you use to connect to the remote sFTP server. 27 | These can also be stored in a seperate config file to save having to enter them in all 28 | the time. 29 | 30 | If 'debug' is set to TRUE, then if the library encounters and error, the error will be displayed 31 | using the error values with the language file supplied (application/language/english/sftp_lang.php). 32 | If it's set to FALSE, it will gracefully error with no error messages. 33 | */ 34 | 35 | $sftp_config['hostname'] = 'your.sftp-domain.com'; 36 | $sftp_config['username'] = 'your_sftp_username'; 37 | $sftp_config['password'] = 'your_sftp_password'; 38 | $sftp_config['debug'] = TRUE; 39 | 40 | // Actually try and connect to the remote server... 41 | $this->sftp->connect($sftp_config); 42 | 43 | /* 44 | Some example commands you can run (look in the actual library file for more info). 45 | */ 46 | 47 | /* 48 | upload: This will upload a file from your local filesystem to the remote filesystem. 49 | It will also overwrite any file that's on the remote server of the same name. 50 | */ 51 | $success = $this->sftp->upload("/var/www/cgi-bin/data/test.csv","/tmp/test.csv"); 52 | 53 | 54 | /* 55 | download: This will download a file from the remote filesystem to the local filesystem. 56 | It will also overwrite any file that's on the local filesystem of the same name. 57 | */ 58 | $success = $this->sftp->download("/tmp/test.csv", "/var/www/cgi-bin/data/test.csv"); 59 | 60 | 61 | /* 62 | mkdir: This will create a directory on the remote filesystem. 63 | */ 64 | $success = $this->sftp->mkdir("/tmp/test/"); 65 | 66 | 67 | /* 68 | rename: This will rename a file on the remote filesystem. 69 | */ 70 | $success = $this->sftp->rename("/tmp/test/test.csv", "/tmp/test/test2.csv"); 71 | 72 | 73 | /* 74 | delete_file: This will remove a file on the remote filesystem. 75 | */ 76 | $success = $this->sftp->delete_file("/tmp/test/test2.csv"); 77 | 78 | 79 | /* 80 | delete_dir: This will remove a diretory on the remote filesystem. 81 | */ 82 | $success = $this->sftp->delete_dir("/tmp/test/"); 83 | 84 | 85 | /* 86 | list_files: This will list all files in a diretory on the remote filesystem. 87 | */ 88 | $success = $this->sftp->list_files("/tmp/test/", TRUE); 89 | 90 | 91 | // Output is the method was successful! 92 | print_r($success); 93 | } 94 | //-----------------------------------------------------------------------------------> 95 | } 96 | ?> -------------------------------------------------------------------------------- /application/language/english/sftp_lang.php: -------------------------------------------------------------------------------- 1 | 0) 47 | { 48 | $this->initialize($config); 49 | } 50 | 51 | log_message('debug', "SFTP Class Initialized"); 52 | } 53 | 54 | // -------------------------------------------------------------------- 55 | 56 | /** 57 | * Initialize preferences 58 | * 59 | * @access public 60 | * @param array 61 | * @return void 62 | */ 63 | function initialize($config = array()) 64 | { 65 | foreach ($config as $key => $val) 66 | { 67 | if (isset($this->$key)) 68 | { 69 | $this->$key = $val; 70 | } 71 | } 72 | 73 | // Prep the hostname 74 | $this->hostname = preg_replace('|.+?://|', '', $this->hostname); 75 | } 76 | 77 | // -------------------------------------------------------------------- 78 | 79 | /** 80 | * SFTP Connect 81 | * 82 | * @access public 83 | * @param array the connection values 84 | * @return bool 85 | */ 86 | function connect($config = array()) 87 | { 88 | if (count($config) > 0) 89 | { 90 | $this->initialize($config); 91 | } 92 | 93 | // Open up SSH connection to server with supplied credetials. 94 | $this->conn = @ssh2_connect($this->hostname, $this->port); 95 | 96 | // Try and login... 97 | if ( ! $this->_login()) 98 | { 99 | if ($this->debug == TRUE) 100 | { 101 | $this->_error('sftp_unable_to_login_to_ssh'); 102 | } 103 | return FALSE; 104 | } 105 | 106 | // Once logged in successfully, try to open SFTP resource on remote system. 107 | // If successful, set this resource as a global variable. 108 | if (FALSE === ($this->conn_sftp = @ssh2_sftp($this->conn))) 109 | { 110 | if ($this->debug == TRUE) 111 | { 112 | $this->_error('sftp_unable_to_open_sftp_resource'); 113 | } 114 | return FALSE; 115 | } 116 | 117 | return TRUE; 118 | } 119 | 120 | // -------------------------------------------------------------------- 121 | 122 | /** 123 | * SFTP Login 124 | * 125 | * @access private 126 | * @return bool 127 | */ 128 | function _login() 129 | { 130 | if ($this->login_via_key) { 131 | if (@ssh2_auth_pubkey_file($this->conn, $this->username, $this->public_key_url, $this->private_key_url, $this->password)) { 132 | return true; 133 | } else { 134 | if ($this->debug == TRUE) 135 | { 136 | $this->_error('sftp_unable_to_connect_with_public_key'); 137 | } 138 | return false; 139 | } 140 | } else { 141 | return @ssh2_auth_password($this->conn, $this->username, $this->password); 142 | } 143 | } 144 | 145 | // -------------------------------------------------------------------- 146 | 147 | /** 148 | * Validates the connection ID 149 | * 150 | * @access private 151 | * @return bool 152 | */ 153 | function _is_conn() 154 | { 155 | if ( ! is_resource($this->conn_sftp)) 156 | { 157 | if ($this->debug == TRUE) 158 | { 159 | $this->_error('sftp_no_connection'); 160 | } 161 | return FALSE; 162 | } 163 | return TRUE; 164 | } 165 | 166 | // -------------------------------------------------------------------- 167 | 168 | /** 169 | * Scans a directory from a given path 170 | * 171 | * @access private 172 | * @return array 173 | */ 174 | 175 | function _scan_directory($dir, $recursive = FALSE) 176 | { 177 | $tempArray = array(); 178 | $handle = opendir($dir); 179 | 180 | // List all the files 181 | while (false !== ($file = readdir($handle))) { 182 | if (substr("$file", 0, 1) != "."){ 183 | if(is_dir($file) && $recursive){ 184 | // If its a directory, interate again 185 | $tempArray[$file] = $this->_scan_directory("$dir/$file"); 186 | } else { 187 | $tempArray[] = $file; 188 | } 189 | } 190 | } 191 | 192 | closedir($handle); 193 | return $tempArray; 194 | } 195 | // -------------------------------------------------------------------- 196 | 197 | 198 | /** 199 | * Create a directory 200 | * 201 | * @access public 202 | * @param string 203 | * @return bool 204 | */ 205 | function mkdir($path = '') 206 | { 207 | if ($path == '' OR ! $this->_is_conn()) 208 | { 209 | return FALSE; 210 | } 211 | 212 | $result = @ssh2_sftp_mkdir($this->conn_sftp, $path); 213 | 214 | if ($result === FALSE) 215 | { 216 | if ($this->debug == TRUE) 217 | { 218 | $this->_error('sftp_unable_to_makdir'); 219 | } 220 | return FALSE; 221 | } 222 | 223 | return TRUE; 224 | } 225 | 226 | // -------------------------------------------------------------------- 227 | 228 | /** 229 | * Upload a file to the server 230 | * 231 | * @access public 232 | * @param string 233 | * @param string 234 | * @return bool 235 | */ 236 | function upload($locpath, $rempath) 237 | { 238 | if ( ! $this->_is_conn()) 239 | { 240 | return FALSE; 241 | } 242 | 243 | if ( ! file_exists($locpath)) 244 | { 245 | if ($this->debug == TRUE) 246 | { 247 | $this->_error('sftp_no_source_file'); 248 | } 249 | return FALSE; 250 | } 251 | 252 | $sftp = $this->conn_sftp; 253 | $stream = @fopen("ssh2.sftp://$sftp$rempath", 'w'); 254 | 255 | if ($stream === FALSE) 256 | { 257 | if ($this->debug == TRUE) 258 | { 259 | $this->_error('sftp_unable_to_upload'); 260 | } 261 | return FALSE; 262 | } 263 | 264 | $data_to_send = @file_get_contents($locpath); 265 | 266 | if (@fwrite($stream, $data_to_send) === false) 267 | { 268 | if ($this->debug == TRUE) 269 | { 270 | $this->_error('sftp_unable_to_send_data'); 271 | } 272 | return FALSE; 273 | } 274 | 275 | @fclose($stream); 276 | 277 | return TRUE; 278 | } 279 | 280 | // -------------------------------------------------------------------- 281 | 282 | /** 283 | * Download a file to the server 284 | * 285 | * @access public 286 | * @param string 287 | * @param string 288 | * @return bool 289 | */ 290 | function download($rempath, $locpath) 291 | { 292 | if ( ! $this->_is_conn()) 293 | { 294 | return FALSE; 295 | } 296 | 297 | $sftp = $this->conn_sftp; 298 | 299 | $stream = @fopen("ssh2.sftp://$sftp$rempath", 'r'); 300 | 301 | if ($stream === FALSE) 302 | { 303 | if ($this->debug == TRUE) 304 | { 305 | $this->_error('sftp_unable_to_download'); 306 | } 307 | return FALSE; 308 | } 309 | 310 | $contents = null; 311 | 312 | while (!feof($stream)) 313 | { 314 | $contents .= @fread($stream, $this->buffer_size); 315 | } 316 | 317 | $result = file_put_contents($locpath, $contents); 318 | @fclose($stream); 319 | return $result; 320 | } 321 | 322 | // -------------------------------------------------------------------- 323 | 324 | /** 325 | * Force Download a remote file in a browser 326 | * 327 | * @access public 328 | * @param string 329 | * @return bool 330 | */ 331 | 332 | function force_download($rempath) 333 | { 334 | if ( ! $this->_is_conn()) 335 | { 336 | return FALSE; 337 | } 338 | 339 | $sftp = $this->conn_sftp; 340 | $stream_path = "ssh2.sftp://$sftp$rempath"; 341 | 342 | $stream = @fopen($stream_path, 'r'); 343 | 344 | if ($stream === FALSE) 345 | { 346 | if ($this->debug == TRUE) 347 | { 348 | $this->_error('sftp_unable_to_download'); 349 | } 350 | return FALSE; 351 | } 352 | 353 | header('Content-Type: application/octet-stream'); 354 | header("Content-Transfer-Encoding: Binary"); 355 | header("Content-disposition: attachment; filename=\"".basename($stream_path)."\""); 356 | header('Content-Length: ' . filesize($stream_path)); 357 | readfile($stream_path); 358 | } 359 | 360 | // -------------------------------------------------------------------- 361 | 362 | /** 363 | * Rename a file 364 | * 365 | * @access public 366 | * @param string 367 | * @param string 368 | * @param bool 369 | * @return bool 370 | */ 371 | function rename($old_file, $new_file, $move = FALSE) 372 | { 373 | if ( ! $this->_is_conn()) 374 | { 375 | return FALSE; 376 | } 377 | 378 | $result = @ssh2_sftp_rename($this->conn_sftp, $old_file, $new_file); 379 | 380 | if ($result === FALSE) 381 | { 382 | if ($this->debug == TRUE) 383 | { 384 | $this->_error('ftp_unable_to_rename'); 385 | } 386 | return FALSE; 387 | } 388 | 389 | return TRUE; 390 | } 391 | 392 | // -------------------------------------------------------------------- 393 | 394 | /** 395 | * Delete a file 396 | * 397 | * @access public 398 | * @param string 399 | * @return bool 400 | */ 401 | function delete_file($filepath) 402 | { 403 | if ( ! $this->_is_conn()) 404 | { 405 | return FALSE; 406 | } 407 | 408 | $sftp = $this->conn_sftp; 409 | $result = unlink("ssh2.sftp://$sftp$filepath"); 410 | 411 | if ($result === FALSE) 412 | { 413 | if ($this->debug == TRUE) 414 | { 415 | $this->_error('sftp_unable_to_delete'); 416 | } 417 | return FALSE; 418 | } 419 | 420 | return TRUE; 421 | } 422 | 423 | // -------------------------------------------------------------------- 424 | 425 | /** 426 | * Delete a folder and recursively delete everything (including sub-folders) 427 | * containted within it. 428 | * 429 | * @access public 430 | * @param string 431 | * @return bool 432 | */ 433 | function delete_dir($filepath) 434 | { 435 | if ( ! $this->_is_conn()) 436 | { 437 | return FALSE; 438 | } 439 | 440 | // Add a trailing slash to the file path if needed 441 | $filepath = preg_replace("/(.+?)\/*$/", "\\1/", $filepath); 442 | 443 | $result = @ssh2_sftp_rmdir($this->conn_id, $filepath); 444 | 445 | if ($result === FALSE) 446 | { 447 | if ($this->debug == TRUE) 448 | { 449 | $this->_error('sftp_unable_to_delete'); 450 | } 451 | return FALSE; 452 | } 453 | 454 | return TRUE; 455 | } 456 | 457 | // -------------------------------------------------------------------- 458 | 459 | /** 460 | * FTP List files in the specified directory 461 | * 462 | * @access public 463 | * @param string 464 | * @param bool 465 | * @return array 466 | */ 467 | function list_files($path = '.', $recursive = FALSE) 468 | { 469 | if ( ! $this->_is_conn()) 470 | { 471 | return FALSE; 472 | } 473 | 474 | $sftp = $this->conn_sftp; 475 | $dir = "ssh2.sftp://$sftp$path"; 476 | 477 | $directory = $this->_scan_directory($dir, $recursive); 478 | 479 | sort($directory); 480 | 481 | return $directory; 482 | } 483 | 484 | // ------------------------------------------------------------------------ 485 | 486 | /** 487 | * Upload data from a variable 488 | * 489 | * @access private 490 | * @param string 491 | * @param string 492 | * @return bool 493 | */ 494 | function upload_from_var($data_to_send, $rempath) 495 | { 496 | 497 | if ( ! $this->_is_conn()) 498 | { 499 | return FALSE; 500 | } 501 | 502 | $sftp = $this->conn_sftp; 503 | 504 | $stream = @fopen("ssh2.sftp://$sftp$rempath", 'w'); 505 | 506 | if ($stream === FALSE) 507 | { 508 | if ($this->debug == TRUE) 509 | { 510 | $this->_error('sftp_unable_to_upload'); 511 | } 512 | return FALSE; 513 | } 514 | 515 | if (@fwrite($stream, $data_to_send) === false) 516 | { 517 | if ($this->debug == TRUE) 518 | { 519 | $this->_error('sftp_unable_to_send_data'); 520 | } 521 | return FALSE; 522 | } 523 | 524 | @fclose($stream); 525 | 526 | return TRUE; 527 | } 528 | 529 | // ------------------------------------------------------------------------ 530 | 531 | /** 532 | * Display error message 533 | * 534 | * @access private 535 | * @param string 536 | * @return bool 537 | */ 538 | function _error($line) 539 | { 540 | $CI =& get_instance(); 541 | $CI->lang->load('sftp'); 542 | show_error($CI->lang->line($line)); 543 | } 544 | 545 | } 546 | // END Sftp Class 547 | 548 | /* End of file Sftp.php */ 549 | /* Location: ./system/application/libraries/Sftp.php */ 550 | --------------------------------------------------------------------------------