Модераторы: skyboy, MoLeX, Aliance, ksnk
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Безопасно ли так принимать значение? 
V
    Опции темы
maxipub
Дата 28.7.2014, 17:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: нет
Всего: 1



Добрый день.

Еще один банальный вопрос, но все же...

Код
if (isset($_POST['param']) && in_array($_POST['param'], array('val_1', 'val_2', 'val_3')))
    require BASE_DIR.'inc/'.$_POST['param'].'.php';


Т.е. никоим образом не фильтровать переменную, просто проверять in_array, и если все ок, то прямо так и инклудить?

Возможно, есть какие-нибудь подводные камни, спецсимволы, которые in_array не уловит и т.д.?

Это сообщение отредактировал(а) maxipub - 28.7.2014, 17:05
PM MAIL   Вверх
Aliance
Дата 29.7.2014, 10:06 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


I ♥ <script>
****


Профиль
Группа: Модератор
Сообщений: 6418
Регистрация: 2.8.2004
Где: spb

Репутация: 14
Всего: 137



in_array будет равен простому сравнению (==) между всеми значениями массива с группировкой по или (||). Максимум что можно добавить - это тождественное сравнение (===), путем задания третьего аргумента согласно документации.
В итоге получаем что безопасности ничего не угрожает в данном коде.

Хотя я лично такой код не принял бы на ревью, предложив хотя бы такой вариант:
Код

if (isset($_POST['param'])) {
    switch ($_POST['param']) {
        case 'val_1':
        case 'val_2':
        case 'val_3':
            require BASE_DIR . 'inc/' . $_POST['param'] . '.php';
            break;
        default:
            throw new Exception('Wrong param');
            break;
    }
}

PM MAIL WWW ICQ Skype   Вверх
maxipub
Дата 29.7.2014, 16:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: нет
Всего: 1



Aliance, спасибо огромное, особенно за неточное сравнение! smile 

ЗЫ: а для общего развития, не могли бы подсказать, почему switch? Там ведь только неточное. Да и в in_array массив можно передавать переменной (из конфига или в некую функцию), вроде бы гибче и лаконичней? smile 
PM MAIL   Вверх
ndbn
Дата 30.7.2014, 09:14 (ссылка) |  (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 6
Регистрация: 17.9.2010

Репутация: нет
Всего: нет



А я бы написал вот так, хотя вопрос не в этом.
Код

<?php
 //....
  $acceptable = array(
    'val_1',
    'val_2',
    'val_3',
  );  
  $param = filter_input( INPUT_POST, 'param');
  if($param && in_array($param, $acceptable)
  {
    $filepath = BASE_DIR . 'inc' . DIRECTORY_SEPARATOR . $param . '.php';
    if(file_exists($filepath))
    {        
        require_once $filepath;
    }
  } 


после того, как узнал о существовании функции filter_input уже не могу её не применять
PM MAIL   Вверх
maxipub
  Дата 30.7.2014, 10:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: нет
Всего: 1



ndbn, а что именно filter_input выполняет в вашем примере?

Вообще, не хочется разводить флуд, но какое-то странное решение... file_exists + require_once как минимум smile 

И вообще, в моем конкретном случае суть не в валидации данных, а в возможности как раз упустить ее, если in_array (как мы уже выяснили) корректно будет принимать что угодно. Ведь конкретное множество доступных значений строго определено.
PM MAIL   Вверх
Aliance
Дата 30.7.2014, 11:41 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


I ♥ <script>
****


Профиль
Группа: Модератор
Сообщений: 6418
Регистрация: 2.8.2004
Где: spb

Репутация: 14
Всего: 137



Цитата(maxipub @  29.7.2014,  17:50 Найти цитируемый пост)
а для общего развития, не могли бы подсказать, почему switch? Там ведь только неточное. 

а я его люблю, он нагляднее smile а точное в данном случае не сильно важно, потому что в любом случае мы ожидаем строку, строка же и будет приходить всегда. но даже если бы это было не так - можно было бы воспользоваться приведением к нужному типу в теле switch

Цитата(maxipub @  29.7.2014,  17:50 Найти цитируемый пост)
Да и в in_array массив можно передавать переменной (из конфига или в некую функцию), вроде бы гибче и лаконичней? 

а вот с этой точки зрения вы правы, просто в исходном примере ни слова о конфиге не было, поэтому я предложил свою альтернативу.
PM MAIL WWW ICQ Skype   Вверх
ndbn
Дата 30.7.2014, 13:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 6
Регистрация: 17.9.2010

Репутация: нет
Всего: нет



maxipub
Цитата

а что именно filter_input выполняет в вашем примере?

Вырежет служебные символы, если не указывать третий параметр, то по-умолчанию он равен FILTER_DEFAULT или FILTER_UNSAFE_RAW.

Цитата

какое-то странное решение... file_exists + require_once как минимум

Процитирую справку
Цитата

require идентично include() за исключением того, что при ошибке оно также выдаст фатальную ошибку уровня E_COMPILE_ERROR. Другими словами, она остановит выполнение скрипта, тогда как include() только выдала бы предупреждение E_WARNING, которое позволило бы скрипту продолжить выполнение.


Цитата

Ведь конкретное множество доступных значений строго определено. 

Всякое бывает, маловероятно, но вполне реально, что обнаружится баг, например "при передаче в первом параметре функции in_array байта 0x02 она всегда возвращает TRUE"(повторюсь, это для примера). Я считаю, что лучше перебдеть.
PM MAIL   Вверх
maxipub
  Дата 30.7.2014, 16:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: нет
Всего: 1



Цитата(ndbn @  30.7.2014,  13:50 Найти цитируемый пост)
Процитирую справку

Так в том то и дело! Когда программист использует require, подразумевается что без данного инклуда продолжение выполнение скрипта недопустимо. Вы же своей конструкцией require превратили зачем-то в include. smile 

Цитата(ndbn @  30.7.2014,  13:50 Найти цитируемый пост)
вполне реально

А для filter_input значит это не "вполне реально"? smile Не вижу разницы.
PM MAIL   Вверх
s0lman
Дата 30.7.2014, 18:51 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Белый и лохматый
**


Профиль
Группа: Участник
Сообщений: 637
Регистрация: 1.11.2007
Где: Ukraine

Репутация: 9
Всего: 29



Цитата(maxipub @  30.7.2014,  09:10 Найти цитируемый пост)
file_exists 

Лишнее обращение к файловой системе (по дефолту). Стараюсь не использовать без крайней надобности.


--------------------
Когда я уже выучусь на волшебника? :(
PM   Вверх
baldina
Дата 30.7.2014, 22:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 3433
Регистрация: 5.12.2007
Где: Москва

Репутация: 26
Всего: 101



Цитата(ndbn @  30.7.2014,  13:50 Найти цитируемый пост)
вполне реально, что обнаружится баг

если обнаружится баг в программе (или тем паче в исполняемой системе), нужно от него избавляться, конкретно. а попытка учесть возможные баги...  user posted image

Цитата(maxipub @  30.7.2014,  10:10 Найти цитируемый пост)
какое-то странное решение... file_exists + require_once

 smile 

maxipub, имхо и так все достаточно безопасно, но уж если подходить параноидально, то единственная потенциальная проблема (в реальности её нет) - подстановка другого файла, использование относительного пути и тп штучки. filter тут бесполезен.
для устранения паранойййи надо обеспечить формирование пути на основе эталонного массива, а не внешних данных, т.е.
Код

$key = array_search ($param, $files);
if ($key !== false)
  include PATH . $files[$key] . '.php';


Это сообщение отредактировал(а) baldina - 30.7.2014, 22:31
PM MAIL   Вверх
ndbn
Дата 31.7.2014, 08:37 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 6
Регистрация: 17.9.2010

Репутация: нет
Всего: нет



Цитата(maxipub @  30.7.2014,  16:22 Найти цитируемый пост)
Когда программист использует require, подразумевается что без данного инклуда продолжение выполнение скрипта недопустимо. Вы же своей конструкцией require превратили зачем-то в include.

Моя конструкция лишь позволяет предотвратить вываливание ошибки пользователю. Даже если пользователь передал правильное имя файла, сам файл может отсутствовать по тем или иным причинам и заметить это в большом проекте может быть достаточно затруднительно.
В include я ничего не превращал, разница между require и include в том, что второй генерирует warning, тем не менее не вижу смысла выводить его конечному пользователю.

Цитата(maxipub @  30.7.2014,  16:22 Найти цитируемый пост)
А для filter_input значит это не "вполне реально"?  Не вижу разницы. 

Да, баг может быть где угодно, зачем пристегиваться в автомобиле, если в случае ДТП всё равно есть шанс умереть smile


Цитата(s0lman @  30.7.2014,  18:51 Найти цитируемый пост)
Стараюсь не использовать без крайней надобности. 

ИМХО, прием части имени подключаемого php файла от пользователя как раз такая крайняя необходимость.

Цитата(baldina @  30.7.2014,  22:22 Найти цитируемый пост)
а попытка учесть возможные баги...

У вас виден большой опыт в разработке больших проектов.

Ладно, срачу не быть smile
PM MAIL   Вверх
maxipub
Дата 31.7.2014, 09:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 517
Регистрация: 22.10.2009

Репутация: нет
Всего: 1



Цитата(baldina @  30.7.2014,  22:22 Найти цитируемый пост)
для устранения паранойййи надо обеспечить формирование пути на основе эталонного массива, а не внешних данных, т.е.

Ну так в первом посте in_array не катит разве?

Ладно, всем спасибо, вопрос решен.
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "PHP"
Aliance
IZ@TOP
skyboy
SamDark
MoLeX

Новичкам:

  • PHP редакторы собираются и обсуждаются здесь
  • Электронные книги по PHP, документацию можно найти здесь
  • Интерпретатор PHP, полную документацию можно скачать на PHP.NET

Важно:

  • Не брезгуйте пользоваться тегами [code=php]КОД[/code] для повышения читабельности текста/кода.
  • Перед созданием новой темы воспользуйтесь поиском и загляните в FAQ
  • Действия модераторов можно обсудить здесь

Внимание:

  • Темы "ищу скрипт", "подскажите скрипт" и т.п. будут переноситься в форум "Web-технологии"
  • Темы с именами: "Срочно", "помогите", "не знаю как делать" будут УДАЛЯТЬСЯ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, IZ@TOP, skyboy, SamDark, MoLeX, awers.

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | PHP: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.1547 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.