ТаблицейБлоками.PHP chmod – установка и чтение прав доступа в Unix системах с помощью PHP |
Последняя модификация: 10.08.2014 г
Страница загружена с адреса: http://webdesign.site3k.ru/consulting/php_chmod.html
Функция chmod языка PHP может вызвать неожиданное затруднение. Понятный и простой, на первый взгляд, синтаксис:
chmod(filename, attrib);
в котором filename определяет имя файла или каталога, для которого трубуется изменить атрибут (режим доступа), а attrib – режим, который требуется установить, имеет ряд скрытых особенностей.
Первой из них, является, конечно же, сетевая система прав доступа, утанавливающая отдельно права для владельца файла, группы, к которой он относится и всех остальных пользователей. Права, обычно представляются строками:
drwxr-x--x -rw-r--r--
Первый символ описывает тип элемента: дефис "-" означает файл, символ "d" означает каталог. Дальнейшие девять символов описывают права доступа:
r – read право на чтение w – write право на запись x – execute право на выполнение*
*право на выполнение для каталога означает возможность просмотреть его содержимое (войти в каталог).
Первые три символа из девяти устанавливают права доступа для владельца, вторые три - для группы, третьи - для всех пользователей. Каждый набор символов r, w, x показывает текущие установленные права доступа для каждой категории пользователей. Если вместо символа стоит дефис, то соответствующее право отсутствует.
Однако, PHP команда chmod не признает указание прав доступа в виде текстовой строки. Права доступа для нее обятельно должны указываться в виде числа от 0 до 7, для каждого типа пользователей. Чтобы понять, как преобразовываются числовые значения в текстовые и, наоборот, полезно представить текстовыу строку в виде битовой маски для однозначности которой необходимо строгое соблюдение порядка атрибутов: 1 группа цифр относится к владельцу файла, вторая к его группе, третья – к остальным пользоватлям. Кроме того, необходимо соблюдать последовательность прав: 1 право чтения, 2 – право записи, 3 – право выполнения.
При соблюдении этих условий, приведенные выше строки
drwxr-x--x -rw-r--r--
Можно представить как набор двоичных данных:
100.0.111.101.001 1.0.0.110.100.100
(Это фактический набор атрибутов, с точки зрения PHP команды chmod важны лиш последние три набора в каждой строке).
Единица в последних трех группах каждой строки означает наличие права (истину), ноль – его отсутствие (ложь).
Преобразование данного представления в десятиричный формат дает более привычное числовое представление:
Двоичное | Десятичное | Физический смысл значения |
---|---|---|
000 | 0 | ничего не разрешает (только удалять) |
001 | 1 | доступ на выполнение (x) |
010 | 2 | доступ на запись (w) |
100 | 4 | доступ на чтение (r) |
Побитовое сложение (сдвиг) значений прав для каждой группы пользователей позволяет сократить десятиричную запись до одного числа в каждой группе:
Двоичное сложение | Десятичнное сложение | Физический смысл |
---|---|---|
001+010=011 | 1+2=3 | доступ на выполнение и запись (-wx) |
001+100=101 | 1+4=5 | доступ на выполнение и чтение (r-x) |
010+100=110 | 2+4=6 | доступ на чтение и запись (rw-) |
001+010+100=111 | 1+2+4=7 | доступ на чтение, запись и выполнение (rwx) |
Таким образом маска атрибутов для вышеуказаного примера (показаны только последние три группы, имеющие значение для прав доступа):
В текстовом формате имеет вид:
rwx.r-x.--x rw-.r--.r--
В двоичном:
111.101.001 110.100.100
А в десячичном, приобретает вид:
7.5.1 6.4.4
Именно в таком виде, только без разделяющих точек, и принимает PHP команда chmod значение атрибутов, корорые следует установить.
Но, и это не все! Нельзя просто вписать в PHP-скрипт команду
chmod('myscript.php', 755);
Чтобы сделать файл myscript.php выполняемым: Команда chmod принимает значение прав только в 8-ричном формате! Ну что тут поделаеш – разработчики PHP специально усложняли нам жизнь, чтобы наши мозги не атрофировались. ☺
Чтобы команда chmod нормально выполнялась, ей нужно указать преобразование в 8-ричный формат, поставив перед значением прав ноль:
chmod('myscript.php', 0755);
Вы думаете это все?
Позвольте! Зачем так упрощать себе жизнь? Разработчики PHP позаботились о том, чтобы эта статья не закончилась так просто.
Добавление ноля перед атрибутами хорошо действует, когда вы заранее знаете, какой нужен атрибут. А если нужно сделать так, чтобы права выставлялись формой на HTML-странице? К примеру, вы хотите создать систему управления файлами?
Допустим, из формы приходит переменная $attrib, содержащая значение прав доступа, типа 755. Вы думаете что, приклеете к ним ноль:
chmod('myscript.php', '0'.$attrib);
и, все у вас получится?
Ага, размечтались. Разработчики PHP не позаботились об автоматическом преобразовании десятичного числа в восмиричное, будут они вам строки преобразовывать?
Нет, конечно. Самим придется потрудиться:
chmod('myscript.php',octdec($attrib));
вставляя функцию octdec преобразования числа (или строки, имеющей числовае значение) в восьмиричный формат. Или используя функцию eval:
eval("chmod('myscript.php',0$attrib);");
Да, теперь все заработает. Но только на запись! Попробуйте считать атрибуты функией fileperms и не опплеваться: она вернет все в том же восьмиричном формате! Лично я теряюсь в интерпритации таких значений. Для нормального восприятия, их приходтся предварительно преобразовывать функцией decoct в десятиричный формат, а затем, из полученного результата брать последние 3 символа:
substr( decoct(fileperms('myscript.php')), strlen(decoct(fileperms('myscript.php')))-3, strlen(decoct(fileperms('myscript.php'))) );
Только так можно получить нормальные числовые атрибуты.
$perms=decoct(fileperms('myscript.php')); $len=strlen($perms); if ($len==5){ // вместо длины можно использовать is_dir() и другие методы $attrib='d';// каталог }else{ $attrib='-';// файл } // 1 метод: Вычисление через двоичное преобразование for($i=$len-3; $i < $len; $i++){ @$attrib2=decbin(substr($perms,$i,1)); if (substr($attrib2,0,1)==1){ $attrib.='r'; }else{ $attrib.='-'; } if (substr($attrib2,1,1)==1){ $attrib.='w'; }else{ $attrib.='-'; } if (substr($attrib2,2,1)==1){ $attrib.='x'; }else{ $attrib.='-'; } } // 2 метод: Прямое вычисление (закомментирован) //for($i=$len-3; $i < $len; $i++){ // switch (substr($perms,$i,1)) { // case 0: // $attrib.='---'; // break; // case 1: // $attrib.='--x'; // break; // case 2: // $attrib.='-w-'; // break; // case 3: // $attrib.='-wx'; // break; // case 4: // $attrib.='r--'; // break; // case 5: // $attrib.='r-x'; // break; // case 6: // $attrib.='rw-'; // break; // case 7: // $attrib.='rwx'; // break; // } //}
Но числовой формат во многих случаях окажется удобней буквенного (сравните 755 и -rwxr-xr-x, что быстрее понимается?).
Вот теперь на языке PHP можно создавать файловые менеджеры и системы управления файлами (однако изменить атрибуты в файлах, загруженых по ftp, может не позволить сервер из-за принадлежности к разным группам).
< Предыдущая (Экспорт и импорт) PHP chmod Следующая (Web 2.0)>