Работа с FTP в PHP
Протокол FTP – предназначен для передачи файлов на удаленный хост. В PHP функции для работы с FTP как правило всегда доступны и не требуется установка дополнительного расширения.
Как правило, при работе с FTP выполняются следующие действия:
- Соединение с удаленным FTP-сервером (функция ftp_connect ).
- Авторизация ( ftp_login ).
- Действия с файлами.
- Закрытие соединения ( ftp_close ).
Список директорий и файлов
Функция ftp_nlist ($ftp_stream, $directory) получает список имен файлов и директорий в виде массива, где $ftp_stream – идентификатор соединения с FTP-сервером, $directory – путь к директории (в примере переменная пуста – это соответствует домашней директории FTP-пользователя).
Результат:
Получить список с расширенной информацией поможет функция ftp_rawlist() .
Результат:
Для получения детальных данных о файлах в виде массива есть функция ftp_mlsd(), но она появилась в PHP 7 и не всегда работает, для более ранних версий PHP:
Результат:
Поверка наличия файла/директории
Специальных функций для проверки существования файлов и директорий нет, поэтому можно использовать следующие варианты:
Проверить наличие файла на FTP-сервере
Функция ftp_size() возвращает «-1» если файл не найден.
Поверить наличие директории
Функция ftp_chdir() изменяет текущую директорию на FTP-сервере, возвращает false в случае возникновения ошибки.
Размер файла/директории
Получить размер файла
Функция ftp_size() возвращает размер файла в байтах.
Получить размер FTP директории
К полученному результату можно применить функцию для конвертации байтов в килобайты и мегабайты.
Работа с файлами
В каждый PHP-документ можно включить файл с помощью инструкции include(). Её аргумент: путь к файлу. Этой инструкцией удобно пользоваться при наличии одинаковых кусков кода во многих PHP-программах. Содержимое включаемого файла обрабатывается как простой HTML-текст. Для того, чтобы содержимое этого файла обрабатывалось как PHP-программа, нужно обрамлять его открывающим и закрывающим тегами PHP.
Пример 1
Включаемый файл top.php с PHP-программой:
В данном случае результат будет тем же, если включаемый файл top.php содержит только строку HTML-текста:
Включаемые файлы могут возвращать значения подобно функциям. Использование оператора return прерывает выполнение этого файла так же, как и функции.
Пример 2
Включаемый файл top.php с PHP-программой:
Инструкцию include() можно использовать внутри цикла. В цикле include() выполняется при каждой итерации. Это можно использовать для включения нескольких файлов. Например:
Определение имени включаемого файла и его загрузка производятся повторно при каждом вызове . Это означает, что если содержание включаемого файла с момента предыдущего вызова изменилось, то загрузится новое содержание.
Оператор include() также можно включать в тело условного оператора.
Несмотря на сходство по внешнему виду с функцией, include() функцией не является, а представляет собой специальную конструкцию языка.
Для указания что файл нужно подключать только один раз используется оператор include_once()
Анализ файлов
PHP содержит множество функций, дающих информацию о файлах. Наиболее употребимыми являются:
- file_exists() — определяет существование файла. Например:
- is_file() — определяет, является ли исследуемый объект файлом. Например:
- is_dir() — определяет, является ли исследуемый объект каталогом. Например:
- is_readable() — определяет, доступен ли файл для чтения. Например:
- is_writable() — определяет, доступен ли файл для записи. Например:
- filesize() — определяет размер файла в байтах.
- filemtime() — определяет дату и время последнего изменения файла.
- fileatime() — определяет дату и время последнего обращения к файлу.
Время возвращается в формате Unix, т.е. представляет собой количество секунд, прошедших после 1 января 1970 г. В примере 2 это число преобразуется в понятный для человека формат с помощью функции date( ).
Пример 3
Внимание! С удаленными файлами эти функции не работают. Их можно применять только к локальной файловой системе.
Управление файлами
PHP содержит множество функций управления файлами. Наиболее употребимыми являются:
- touch() — создает пустой файл с заданным именем. Если такой файл уже существует, то функция изменит дату модификации. Например:
- copy() — копирует файл. Для копирования файлов в php применяется функция copy ($source, $result). Ей нужно передать лишь два параметра — источник $source и имя файла-копии — $result. Стоит отметить, что следует указывать полные адреса к файлам. Пример применения функции copy:
r | чтение. Указатель файла устанавливается на его начало |
r+ | чтение и запись. Указатель файла устанавливается на его начало |
w | запись. Указатель файла устанавливается на его начало. Все старое содержимое файла теряется. Если файл с указанным именем не существует, функция пытается его создать |
w+ | чтение и запись. Указатель файла устанавливается на его начало. Все старое содержимое файла теряется. Если файл с указанным именем не существует, функция пытается его создать |
a | запись. Указатель файла устанавливается на его конец. Если файл с указанным именем не существует, функция пытается его создать |
a+ | чтение и запись. Указатель файла устанавливается на его конец. Если файл с указанным именем не существует, функция пытается его создать |
Если открыть файл не удалось, то можно прервать выполнение программы. Например:
Пример 4
Пример 5
Пример 6
1 | Можно читать, нельзя писать |
2 | Нельзя ни читать, ни писать |
3 | Снятие блокировки |
Пример 7
Блокировка с помощью flock() не является абсолютной. С ней будут считаться только те программы, которые тоже используют эту функцию.
В PHP версии 4.3.0 появились новые удобные функции работы с файлами:
- file_get_contents() — прочитать весь файл или URL
- file_put_contents() — записать файл
Работа с каталогами
В PHP есть несколько функций для работы с каталогами:
-
mkdir() — создание каталога. Аргументы: путевое имя каталога и режим доступа. Режим доступа — восьмеричное число из трех цифр с ведущим нулем. Первая цифра — право доступа для владельца, вторая — для группы, третья — для всех остальных. В системе Windows режим доступа игнорируется. В системе UNIX определены следующие права доступа:
0 | Нет доступа |
1 | Доступ для запуска |
2 | Доступ для записи |
3 | Доступ для записи и запуска |
4 | Доступ для чтения |
5 | Доступ для чтения и запуска |
6 | Доступ для чтения и записи |
7 | Полный доступ |
Например, право полного доступа для владельца, чтения и запуска для группы и запуска для всех остальных:
Пример 8
Проверочное выражение цикла сработает не так, как хотелось бы, если в каталоге есть файл с именем «0». В таком случае имя «0» будет преобразовано в 0, что вызовет завершение цикла. Избежать подобного можно, если принять дополнительные меры безопасности, изменив проверочное выражение:
Помимо использования функция fgetc() fgets() fgetss(), Вы можете использовать
$file = file($filename). Она читает $filename в массив($file).
Передача файла с сервера. Скачать файл. DownLoad.
Ручной Download, или как скриптом открыть пользователю окошко сохранения файла. Чтобы в браузере открылся диалог «Сохранить файл» с названием файла file.dat, скрипт должен послать такие заголовки:
Готовый пример отправки файла с диска:
Не мешало бы также ссылаться на скрипт как http://. /download.php?file.dat, иначе браузеры, основанные на Mozilla, могут попытаться записать файл как file.dat.php. или указать атрибут download:
Примечание: Не используйте заголовок header(«Cache-Control: no-cache») в таких скриптах, большинство версий Internet Explorer не смогут скачать файл.
Следующий пример скрипта демонстрирует как организовать поддержку докачки:
Предполагается, что $cd — путь к файлу, $fn — имя файла
Функции для работы с каталогами
- chdir() — Сменить каталог boolean chdir (string str)
Изменяет текущий каталог PHP на указанный в качестве параметра str. Возвращает TRUE в случае успешного завершения, FALSE в случае возникновения ошибки
Изменяет корневой каталог текущего процесса на переданный в качестве параметра str. Возвращает TRUE в случае успешного завершения, FALSE в случае возникновения ошибки..
Замечание: Для Windows-платформ эта функция не реализована.
Закрывает поток, связанный с каталогом и переданный в качестве параметра catalog. Перед использованием данной функции, поток должен быть открыт с помощью функции opendir().
dir — Класс directory
Псевдо-объектно-ориентированный механизм для чтения каталога, переданного в параметре каталог. С момента открытия каталога становятся доступными два свойства класса. Свойство «handle» может быть использовано с другими функциями для работы с каталогами, например, с функциями readdir(), rewinddir() и closedir(). Свойство «path» содержит путь к открытому каталогу. Доступны три метода: read, rewind and close.
Пожалуйста, обратите внимание на способ, которым осуществляется проверка значения, возвращаемого методами класса dir() в примере, приведенном ниже. В этом примере проводится проверка значения на идентичность (выражения идентичны, когда они равны и являются одного типа — за более подробной информацией обратитесь к главе Операторы сравнения) значению FALSE, поскольку в ином случае, любой элемент каталога, чье имя может быть выражено как FALSE, остановит цикл.
Замечание: Порядок, в котором метод «read» возвращает элементы каталога, зависит от операционной системы.
Замечание: Также, PHP автоматически определяет внутренний класс Directory, что означает, что вы не сможете определять собственные классы с таким же именем.
Возвращает имя текущего рабочего каталога.
Возвращает дескриптор каталога для последующего использования с функциями closedir(), readdir() и rewinddir().
Если путь не существует или каталог, расположенный по указанному пути, не может быть открыт вследствие правовых ограничений или ошибок файловой системы, функция opendir() возвращает значение FALSE и генерирует сообщение PHP об ошибке уровня E_WARNING. Вы можете запретить вывод сообщения об ошибке, предварив имя функции opendir() символом ‘@’.
Начиная с версии PHP 4.3.0, параметр путь может также являться любым URL’ом, обращение к которому приводит к получению списка его файлов и каталогов. Однако, данный способ работает только при использовании url-упаковщика file://. В версии PHP 5.0.0 была добавлена поддержка url-упаковщика ftp://.
Возвращает имя следующего по порядку элемента каталога. Имена элементов возвращаются в порядке, зависящем от файловой системы.
Обратите внимание на способ проверки значения, возвращаемого функцией readdir() в приведенном ниже примере. В этом примере осуществляется проверка значения на идентичность (выражения идентичны, когда они равны и являются значениями одного типа — за более подробной информацией обратитесь к главе Операторы сравнения) значению FALSE, поскольку в ином случае, любой элемент каталога, чье имя может быть выражено как FALSE, остановит цикл (например, элемент с именем «0»).
Обратите внимание, что функция readdir() также возвращает элементы с именами, и, если вы не хотите получать эти значения, просто отбрасывайте их:
Сбрасывает поток каталога, переданный в параметре catalog таким образом, чтобы тот указывал на начало каталога
Возвращает массив, содержащий имена файлов и каталогов, расположенных по пути, переданном в параметре catalog. Если каталог не является таковым, функция возвращает логическое значение FALSE и генерирует сообщение об ошибке уровня E_WARNING.
По умолчанию, сортировка производится в алфавитном порядке по возрастанию. Если указан необязательный параметр order (равен 1), сортировка производится в алфавитном порядке по убыванию. Пример кода
ftp_get
ftp_get() загружает удалённый файл с FTP-сервера и сохраняет его локально.
Список параметров
Путь к локальному файлу (файл будет перезаписан, если уже существует).
Путь к удалённому файлу.
Режим передачи. Должен быть либо FTP_ASCII , либо FTP_BINARY .
Позиция начала загрузки в удалённом файле.
Возвращаемые значения
Возвращает true в случае успешного выполнения или false в случае возникновения ошибки.
Список изменений
Версия | Описание |
---|---|
8.1.0 | Параметр ftp теперь ожидает экземпляр FTP\Connection ; ранее ожидался ресурс (resource). |
7.3.0 | Теперь параметр mode опционален. Раньше он был обязательным. |
Примеры
Пример #1 Пример использования ftp_get()
// объявление переменных
$local_file = ‘local.zip’ ;
$server_file = ‘server.zip’ ;
// установка соединения
$conn_id = ftp_connect ( $ftp_server );
// вход с именем пользователя и паролем
$login_result = ftp_login ( $conn_id , $ftp_user_name , $ftp_user_pass );
// попытка скачать $server_file и сохранить в $local_file
if ( ftp_get ( $conn_id , $local_file , $server_file , FTP_BINARY )) <
echo «Произведена запись в $local_file \n» ;
> else <
echo «Не удалось завершить операцию\n» ;
>
// закрытие соединения
ftp_close ( $conn_id );
Смотрите также
- ftp_pasv() — Включает или выключает пассивный режим
- ftp_fget() — Скачивает файл с FTP-сервера и сохраняет его в предварительно открытом файле
- ftp_nb_get() — Скачивает файл с FTP-сервера в асинхронном режиме и сохраняет его в локальный файл
- ftp_nb_fget() — Скачивает файл с FTP-сервера в асинхронном режиме и сохраняет его в предварительно открытом файле
User Contributed Notes 18 notes
I tried to ftp a 7mb file today off my webserver.
I copied this example directly and it told me.
Port command successful
«there was a problem»
I thought it was because of the size.
But I guessed it might be cause of my firewall.
So I made the ftp connection passive:
.
$login_result = ftp_login ( $conn_id , $ftp_user_name , $ftp_user_pass );
ftp_pasv ( $conn_id , true );
?>
Ran the script again & it worked fine.
Hope this helps someone
Don’t want to use an intermediate file? Use ‘php://output’ as the filename and then capture the output using output buffering.
ob_start();
$result = ftp_get($ftp, «php://output», $file, FTP_BINARY);
$data = ob_get_contents();
ob_end_clean();
Don’t forget to check $result to make sure there wasn’t an error. After that, manipulate the $data variable however you want.
Here’s a quick function that figures out the correct mode to use based on a file’s extension.
<?php
function get_ftp_mode ( $file )
<
$path_parts = pathinfo ( $file );
if (!isset( $path_parts [ ‘extension’ ])) return FTP_BINARY ;
switch ( strtolower ( $path_parts [ ‘extension’ ])) <
case ‘am’ :case ‘asp’ :case ‘bat’ :case ‘c’ :case ‘cfm’ :case ‘cgi’ :case ‘conf’ :
case ‘cpp’ :case ‘css’ :case ‘dhtml’ :case ‘diz’ :case ‘h’ :case ‘hpp’ :case ‘htm’ :
case ‘html’ :case ‘in’ :case ‘inc’ :case ‘js’ :case ‘m4’ :case ‘mak’ :case ‘nfs’ :
case ‘nsi’ :case ‘pas’ :case ‘patch’ :case ‘php’ :case ‘php3’ :case ‘php4’ :case ‘php5’ :
case ‘phtml’ :case ‘pl’ :case ‘po’ :case ‘py’ :case ‘qmail’ :case ‘sh’ :case ‘shtml’ :
case ‘sql’ :case ‘tcl’ :case ‘tpl’ :case ‘txt’ :case ‘vbs’ :case ‘xml’ :case ‘xrc’ :
return FTP_ASCII ;
>
return FTP_BINARY ;
>
// sample usage
ftp_get ( $conn_id , $local_file , $server_file , get_ftp_mode ( $server_file ));
?>
ftp_sync is a way to walk the directory structure on the server and copy every directory and file to the same location locally.
<?php
$ftp_server = «ftp.example.com» ;
$conn_id = ftp_connect ( $ftp_server )
or die( «Couldn’t connect to $ftp_server » );
$login_result = ftp_login ( $conn_id , «user» , «pass» );
if ((! $conn_id ) || (! $login_result ))
die( «FTP Connection Failed» );
ftp_sync ( «DirectoryToCopy» ); // Use «.» if you are in the current directory
// ftp_sync — Copy directory and file structure
function ftp_sync ( $dir ) <
if ( $dir != «.» ) <
if ( ftp_chdir ( $conn_id , $dir ) == false ) <
echo ( «Change Dir Failed: $dir <BR>\r\n» );
return;
>
if (!( is_dir ( $dir )))
mkdir ( $dir );
chdir ( $dir );
>
$contents = ftp_nlist ( $conn_id , «.» );
foreach ( $contents as $file ) <
if ( $file == ‘.’ || $file == ‘..’ )
continue;
if (@ ftp_chdir ( $conn_id , $file )) <
ftp_chdir ( $conn_id , «..» );
ftp_sync ( $file );
>
else
ftp_get ( $conn_id , $file , $file , FTP_BINARY );
>
ftp_chdir ( $conn_id , «..» );
chdir ( «..» );
<?php
// define some variables
$folder_path = «YOUR FOLDER PATH» ;
$local_file = «LOCAL FILE PATH» ;
$server_file = «SERVER FILE PATH» ;
//— Connection Settings
$ftp_server = «IP ADDRESS» ; // Address of FTP server.
$ftp_user_name = «USERNAME» ; // Username
$ftp_user_pass = «PASSWORD» ; // Password
#$destination_file = «FILEPATH»;
// set up basic connection
$conn_id = ftp_connect ( $ftp_server );
// login with username and password
$login_result = ftp_login ( $conn_id , $ftp_user_name , $ftp_user_pass );
// try to download $server_file and save to $local_file
if ( ftp_get ( $conn_id , $local_file , $server_file , FTP_BINARY )) <
echo «Successfully written to $local_file \n» ;
> else <
echo «There was a problem\n» ;
>
// close the connection
ftp_close ( $conn_id );
?>
If you ran the example and see that it fail after 90sec (timeout).
Then try adding:
<?php
ftp_pasv ( $ftp_conn , true );
?>
If someone will try to download files to the same local file (some temporary file), like shown here:
<?php
foreach ( $files as $key => $path ) <
.
$result = ftp_get ( $ftpConnId , ‘temp.tmp’ , $path , FTP_BINARY );
.
>
?>
please take in consideration the fact that you will have big problems with downloading (getting) hole files. In other words ‘temp.tmp’ file always will have the same size equal to first downloaded file despite the real size of downloading file. I have not idea what is the reason!
If someone will think that problem is just in getting proper file size (which you will get using filssize() function) he will be mistaken. The download file’s size is not equal to source file’s size materially, that means fflush() function will not solve the problem (I have tried this as well).
Finally the solution was founded: before downloading a file you will need to delete local file if such exist (‘temp.tmp’). So working code will look like:
<?php
foreach ( $files as $key => $path ) <
.
if ( file_exists ( ‘temp.tmp’ )) <
unlink ( ‘temp.tmp’ );
>
$result = ftp_get ( $ftpConnId , ‘temp.tmp’ , $path , FTP_BINARY );
.
>
?>
Good luck in scripting 🙂
If you previously downloaded a file before (like a huge web log), and just want to get the remaining portion, do this:
$local_file_size = filesize($local_file_path);
$get_result = ftp_get($conn_id, $local_file_path, $remote_file_path, FTP_BINARY, $local_file_size);
This same code works regardless of wether the local file exists already or not. You should first test to make sure the local file is not bigger than the remote file.
On Windows (and possibly *NIX) you will get «[function.ftp-get]: failed to open stream: No such file or directory in. » errors if the local_file path contains directory paths that do not already exist.
Even with write permissions ftp_get can create the file but it will NOT automatically create the parent directories as you might expect.
I am using ftp_get function to download a file from the FTP server to my web server where my php script is running.
On the webserver, I want the file to be downloaded to a directory which has a structure as follows -> Data/Files/localfilename.exe
However, when I specify the above string in the $local_file_name parameter of ftp_get I get an error saying the file does not exist.
I am running a Windows Server and the php script is running from C:/xampp/htdocs/file.php
Is there any way where I can specify the path on the web server where the file is supposed to be downloaded ?
I’d suggest use ftp_fget() instead of ftp_get() since the latter only return TRUE or FALSE and there’s no obvious way to get the cause of failure.
Using ftp_fget, you have to pass a file handle as local file, so you have to do fopen() first. By way of this, you can find ‘Permission Denied’ problem when call fopen(). If you use ftp_get(), there’s no way to find this error cause.
In my case, I run httpd using ‘nobody’ and I create ftp local folder using ‘haha’. It tooks me long time to find the ‘Permission Denied’ problem at that time since I use ftp_get() then.
Remember to use the full server paths to the directories you are working on. Server paths are not the same as «ftp paths».
I was using the path displayed on my FTP client to download and upload files and I kept getting «Not found» or «Permission Denied» errors.
Php как скачать файл с сервера
In this article, we will see how to download & save the file from the URL in PHP, & will also understand the different ways to implement it through the examples. There are many approaches to download a file from a URL, some of them are discussed below:
Using file_get_contents() function: The file_get_contents() function is used to read a file into a string. This function uses memory mapping techniques that are supported by the server and thus enhances the performance making it a preferred way of reading the contents of a file.
Syntax:
Example 1: This example illustrates the use of file_get_contents() function to read the file into a string.