How to Copy one folder local file to SFTP server using PHP - php

This is my code to send single file from local to SFTP server. Single file successfully send.
I want to send one folder from local to SFTP server , but i dont know how to send one folder. i need help
<?php
$src = 'xxxxxxx';
$filename = 'test.txt';
$dest = 'xxxxxxxx'.$filename;
// set up sftp ssh-sftp connection
$connection = ssh2_connect('xxxxxx', 22);
ssh2_auth_password($connection, 'username', 'password');
// Create SFTP session
$sftp = ssh2_sftp($connection);
$sftpStream = #fopen('ssh2.sftp://'.$sftp.$dest, 'w');
try {
if (!$sftpStream) {
throw new Exception("Could not open remote file: $dest");
}
$data_to_send = #file_get_contents($src);
if ($data_to_send === false) {
throw new Exception("Could not open local file: $src.");
}
if (#fwrite($sftpStream, $data_to_send) === false) {
throw new Exception("Could not send data from file: $src.");
} else {
//Upload was successful, post-upload actions go here...
}
fclose($sftpStream);
} catch (Exception $e) {
error_log('Exception: ' . $e->getMessage());
fclose($sftpStream);
}
?>

ssh2_scp_send in php looks like just support sending file.
maybe these ways work:
1.compress folder, send the compressed file
2.use ssh2 to mkdir, then send each file iteratively
3.try with system() function to excute cmd line order "scp -r folder_path user#host:target_path"

Related

Trying to get all content of directory from one server to another using ssh2_scp_recv in php

The below script is working successfully.
Getting file from one server to another
if(ssh2_scp_recv($conn, '/var/www/html/captures/store/2016/04/HK/15721022890870/test/vcredist.bmp',
'/var/www/html/captures/store/2016/04/HK/15721022890870/test/vcredist.bmp')){
echo "\n recevied \n";
}else{
echo "\n not recevied\n";
}
But instead for fetching just a static file, I want to fetch folder with all its content inside.
With above example, the directory I would like to fetch to local server is "15721022890870"
/var/www/html/captures/store/2016/04/HK/15721022890870/
I have tried below code but doesn't work,
The remote server has directory, but the local server doesn't have, so I want to make directory then copy all its content inside
if(ssh2_scp_recv($conn, '/var/www/html/captures/store/2016/04/HK/15721022890870/',
'/var/www/html/captures/store/2016/04/HK/')){
echo "\n recevied done \n";
}else{
echo "\n not done \n";
}
<?php
$username = "your_username";
$password = "your_pass";
$url = 'your_stp_server_url';
// Make our connection
$connection = ssh2_connect($url);
// Authenticate
if (!ssh2_auth_password($connection, $username, $password)) throw new Exception('Unable to connect.');
// Create our SFTP resource
if (!$sftp = ssh2_sftp($connection)) throw new Exception('Unable to create SFTP connection.');
$localDir = '/path/to/your/local/dir';
$remoteDir = '/path/to/your/remote/dir';
// download all the files
$files = scandir('ssh2.sftp://' . $sftp . $remoteDir);
if (!empty($files)) {
foreach ($files as $file) {
if ($file != '.' && $file != '..') {
ssh2_scp_recv($connection, "$remoteDir/$file", "$localDir/$file");
}
}
}
?>
This is from server to computer but you can modify the $localDir

ftp_fget() returns Transfer Complete error

I'm trying to download images from a remote FTP server and upload them to our own rackspace account. This goes fine for about 3000 images but then it crashes and gives me the following error:
exception with message 'ftp_fget(): Transfer complete.'
We've tried changing the code to use ftp_get(), to not use a temp file to store it in, but it always resulted in the same error. It always fails on the same files, if I were to delete a couple of files that were already downloaded and run the scripts again it has no problem downloading them... it just fails again once it hits those specific images on the FTP server. I've tried downloading those images manually from the server and it worked, it seems nothing is wrong with them.
This is basically the code that does it:
$this->handle = ftp_connect($ftpurl);
$loggedIn = ftp_login($this->handle, $ftpusername, $ftppassword);
if ($loggedIn === false) {
throw new Exception('Can\'t login to FTP server');
}
if ($this->handle === false) {
throw new Exception('Could not connect to the given url');
}
ftp_pasv($this->handle, true);
$fileList = ftp_nlist($this->handle, '.');
if (count($fileList) === 0) {
throw new Exception('No files found on FTP-server');
}
foreach($fileList as $filename) {
try {
$container->getObject($filename);
// Image already exists, rackspace has no convenient hasImage() function
} catch (Exception $ex) {
$temp = tmpfile();
ftp_fget($this->handle, $temp, $filename, FTP_BINARY);
//upload $tmp to rackspace
}
}
Any ideas what could be the issue here?

Uploading a file using WebDav protocol from Unix

I need to transfer a file from my Unix machine to a Windows machine. Problem is i can transfer a file already created on my machine via ftp from unix to any machine. also i can open webdav connection create new file and save it there.
What i am unable to do is to write my code to upload my file fro my local location using webdav.
i tried using pear client but due to lack of documentation, i am still not able to achieve the task .
Here is my attempt:
include("/usr/share/pear/HTTP/WebDAV/Client.php");
global $filename, $logger;
try {
/* $client = new HTTP_WebDAV_Client();
$user="username";
$pass = "pwd";
$dir = "webdavs://".$user.":".$pass."#hostname/";
var_dump($client->stream_open($dir."test4.txt","w",null,$path));
$client->stream_write("HELLO WORLD! , I am great ");
$client->stream_close();
$client->dir_opendir($dir,array());
var_dump($client->dirfiles);
$req =new HTTP_Request($dir);
$req->setBasicAuth($user, $pass);
$req->setMethod(HTTP_REQUEST_METHOD_POST);
$result = $req->addFile('file_upload_field', $filename);
if (PEAR::isError($result)) {
echo $result->getMessage();
} else {
$response = $req->sendRequest();
if (PEAR::isError($response)) {
echo $response->getMessage();
} else {
echo $req->getResponseBody();
}
}*/
$ftp_server = "hostname-ftp";
//$ftp_server = "hostname-webdav";
$connection = ftp_connect($ftp_server);
ftp_login($connection, 'user', 'pwd);
ftp_put($connection, $filename, $filename, FTP_BINARY);
unlink($filename);
} catch(Exception $e){
$message = "There was a problem while uploading" . $filename;
$logger->error($message);
}
It was a togh call, but i figured it out. I am adding my code snippet so it may be helpful for someone. Instead of uploading the file, i converted that file into data stream and then copied that data stream to my call that writes stream on webdav server.
try {
$filecsv = file_get_contents($filename);
$client = new HTTP_WebDAV_Client_Stream();
$user="user";
$pass = "pass";
$dir = "webdavs://".$user.":".$pass."#hostname/";
$client->stream_open($dir."db_user_exports.csv","w",null,$path);
$client->stream_write($filecsv);
$client->stream_close();
unlink($filename);
} catch(Exception $e){
$message = "There was a problem while uploading" . $filename;
$logger->error($message);
}

ssh2_connect causes Error 324 (net::ERR_EMPTY_RESPONSE):

While trying to list the files present in a remote sftp location using php, I get this error:
Error 324 (net::ERR_EMPTY_RESPONSE):
The server closed the connection without sending any data. On my another lamp server the same code works fine. Please point where I am missing something if you can help please. Thanks in advance.
function listBuildFiles() {
global $sftp_host, $sftp_username, $sftp_password, $sftp_path;
$connection = ssh2_connect($sftp_host);
// Authenticate
if (!ssh2_auth_password($connection, $sftp_username, $sftp_password)) {
throw new Exception('Unable to connect.');
}
// Create our SFTP resource
if (!$sftp = ssh2_sftp($connection)) {
throw new Exception('Unable to create SFTP connection.');
}
/**
* Now that we have our SFTP resource, we can open a directory resource
* to get us a list of files. Here we will use the $sftp resource in
* our address string as I previously mentioned since our ssh2://
* protocol allows it.
*/
$files = array();
$dirHandle = opendir("ssh2.sftp://$sftp$sftp_path");
$i=0;
// Properly scan through the directory for files, ignoring directory indexes (. & ..)
while (false !== ($file = readdir($dirHandle))) {
if ($file != '.' && $file != '..') {
$files[$i] = $file;
$i++;
}
}
echo '<select name="buildName">';
echo '<option>Please Select a build</option>';
foreach ($files as $filename) {
echo "<option value=\"$filename\">$filename</option>";
}
echo '</select>';
ssh2_exec($connection, "exit");
Thanks,
Ujjwal
Just to make sure there is no problem on the server side you can open a console and try a raw ssh connection in verbose mode:
ssh -v youruser#yourhost.com
this traces all the interactions between server and client, maybe gives you some clue from the server side.
With phpseclib, a pure PHP SFTP implementation, you can see the full logs of what's going on. Example:
<?php
include('Net/SFTP.php');
define('NET_SSH2_LOGGING', NET_SSH2_LOG_COMPLEX);
$sftp = new Net_SFTP('www.domain.tld');
if (!$sftp->login('username', 'password')) {
exit('Login Failed');
}
// puts a three-byte file named filename.remote on the SFTP server
$sftp->put('filename.remote', 'xxx');
echo $ssh->getLog();
print_r($ssh->getErrors());
?>
The developer of phpseclib is pretty proactive about providing support too so if you can't figure it out from the logs or error messages (s)he probably can.

php FTP Wrapper writes empty files (0 Byte), FTP Extension doesn't

On a server with PHP 5.2.17 running, using any function which makes use of the built in ftp wrapper to upload a file, creates an empty file on the server:
file_put_contents() returns with the accurate number of bytes
copy() also returns with true
Both create the file, but it's empty.
When trying with ftp_put() from the FTP extension, both in binary and ascii mode, it works well.
On my workstation with PHP 5.3.10 it somehow works also with the wrapper.
In code:
$source = '/tmp/testfile';
$target = 'ftp://user:pass#example.com/testfile';
copy($source, $target);
gives no error or warning, but leaves an empty file on the server.
$source = '/tmp/testfile';
$target = 'testfile';
$ftp = ftp_connect('example.com');
ftp_login($ftp, 'user', 'pass');
ftp_put($ftp, $target, $source, FTP_ASCII);
ftp_close($ftp);
works in every respect.
thanks for any suggestion!
Have you tried SSH2 libs? Some sample implementation below:
public function uploadSFTP($host_name, $port, $user, $publicSshKeyPath, $privateSshKeyPath, $remoteFile, $localFile, $fileOperation = 'w')
{
$ssh_conn = ssh2_connect($host_name, $port);
if (ssh2_auth_pubkey_file($ssh_conn, $user, $publicSshKeyPath, $privateSshKeyPath))
{
$sftp_conn = ssh2_sftp($ssh_conn);
$inputfileStream = #fopen('ssh2.sftp://' . $sftp_conn . $remoteFile, $fileOperation);
try
{
if (!$inputfileStream)
throw new Exception('Could open remote file for writing: ' . $remoteFile);
$localFileContents = #file_get_contents($localFile);
if ($localFileContents === FALSE)
throw new Exception('Could not open local file for reading :' . $localFile);
if (#fwrite($inputfileStream, $localFileContents) === FALSE)
throw new Exception('Could not SFTP file');
}
catch (Exception $e)
{
// Do something...
}
fclose($sftpInfileStream);
}
}

Categories