Выход из MySQL Query - PullRequest
       8

Выход из MySQL Query

0 голосов
/ 08 ноября 2011

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

У меня вся строка запроса экранируется одновременно.Это плохая практика или это действительно имеет значение?

Вот запрос:

"INSERT INTO bio_manager_pubs(userid,category,citation,date,link,requests) VALUES ( ".     
$userid.",'".
$_POST['category']."', '".
htmlentities($_POST['pub'])."',
FROM_UNIXTIME(".strtotime($_POST['date'])."),'".
$_POST['link']."',
0)"

В запросе:

  • ИД пользователя и запросы являются целыми числами
  • Ссылка и категория - это Tiny Text (не уверен, что это уместно, но максимум 255 символов, поэтому будет ли лучше VarChar?)
  • Дата - это дата (лучше переформатировать с помощью php или переформатировать с помощью mysql?)
  • Цитата - это текстовое поле

Есть идеи?

Спасибо

РЕДАКТИРОВАТЬ: Ответ на этотВопрос был опубликован четыре раза там, где проблема заключалась в том, что я избегал всего запроса.

То, что было пропущено, вызвало некоторую путаницу в коде, окружающем запрос.Это было примерно так:

$db->query($query)

Вот где запрос функции:

public function query($SQL)
{
    $this->SQL = $this->mysqli->real_escape_string($SQL);
    $this->result = $this->mysqli->query($SQL);

    if ($this->result == true)
    {
        return true;
    }
    else
    {
        printf("<b>Problem with SQL:</b> %s\n", $this->SQL);
        exit;
    }
}

Я только что нашел класс, который немного упростил жизнь в небольших проектах и ​​застрял в нем.Теперь проблема, с которой я сталкиваюсь - это удаление $this->mysqli->real_escape_string($SQL); и добавление escape-символов в других местах кода.

Ответы [ 6 ]

1 голос
/ 08 ноября 2011

Я считаю, что считается плохой практикой создавать весь запрос, а затем избегать всего этого. Вы должны очищать входные данные, как только они вводят код, а не после того, как вы начали использовать их для построения взаимодействий с базой данных.

Вы хотите очистить каждый вход, вроде как:

$category = mysql_real_escape_string($_POST['category'])

И тогда вы будете использовать локальные переменные, а не входные данные, для построения ваших команд SQL.

Кроме того, вы можете посмотреть что-то вроде PDO для доступа к данным, который управляет множеством деталей для вас.

1 голос
/ 08 ноября 2011

Я действительно не вижу никакой дезинфекции ваших данных $ _POST, и на самом деле нет необходимости запускать htmlentities перед тем, как вставить их в базу данных, что нужно делать, когда вы берете эти данные и отображаете их на странице. Обязательно продезинфицируйте свои посты !! Использование mysql_real_escape_string () или предпочтительно PDO с подготовленными инструкциями.

Если вы выполняете mysql_real_escape_string () для всего этого запроса, после того как вы его построите, то это то, что его нарушает.

Используйте его для отдельных записей и / или приведенных переменных, которые должны быть только числами от целых чисел.

Вот что бы я изменил в вашем случае:

$posted = $_POST;

foreach($posted as &$value)
    $value = mysql_real_escape_string($value);

$date = strtotime($posted['date']);


$q = "INSERT INTO bio_manager_pubs(userid,category,citation,date,link,requests) VALUES
(
'{$userid}',
'{$posted['category']}',
'{$posted['pub'])}', 
FROM_UNIXTIME({$posted['date']}),
'{$posted['link']}',
'0'
)";
0 голосов
/ 08 ноября 2011

Отключите magic_quotes_gpc и используйте подготовленные операторы.

С отключенным magic_quotes_gpc вы не получите автоматического экранирования ввода - и magic_quotes_gpc все равно не рекомендуется.

Используйте подготовленные операторы привязки параметров, чтобы избежать внедрения SQL вместо экранирования символов. Я лично предлагаю использовать PDO или MDB2 для общения с вашей базой данных, но вы также можете делать подготовленные заявления с драйвером mysqli. Обратите внимание, что драйвер mysql также находится в блоке прерывания, поэтому вскоре вам придется использовать либо mysqli, либо слой абстракции, такой как MDB2.

Готов поспорить, что magic_quotes_gpc - ваша проблема.

0 голосов
/ 08 ноября 2011

Ну, для начала вам следует избегать использования данных из внешних источников непосредственно в запросе, поэтому я бы переписал код, чтобы не использовать $ _POST в вашем запросе.Еще лучше, если вы можете использовать PDO или подобное, чтобы избежать ваших данных.И я бы не стал конвертировать текст с htmlentities перед тем, как вставить его в вашу базу данных.Это лучше делать после того, как вы извлечете их из базы данных, поскольку сможете использовать эти данные в других (не HTML) выходных контекстах.magic_quotes on?

Попробуйте что-то вроде этого

if (get_magic_quotes_gpc()) {
    $category = stripslashes($_POST['category']);
    $pub = stripslashes($_POST['pub']);
    $link = stripslashes($_POST['link']);
} else {
    $category = $_POST['category'];
    $category = $_POST['category'];
    $category = $_POST['category'];
}
$category = mysql_escape_string( $category );
$pub = mysql_escape_string( $pub );
$link = mysql_escape_string( $link );
$sql = "
   INSERT INTO bio_manager_pubs(userid,category,citation,date,link,requests) VALUES (      
   ".  $userid.",
   '$category', 
   '$pub',
   FROM_UNIXTIME(".strtotime($_POST['date'])."),
   '$link',
   0
)";
0 голосов
/ 08 ноября 2011

Вместо того, чтобы экранировать весь SQL-запрос (что может привести к поломке), просто экранируйте ввод пользователя:

$userid = mysql_real_escape_string($userid);
$cat    = mysql_real_escape_string($_POST['category']);
$pub    = mysql_real_escape_string($_POST['pub']);
$date   = strtotime($_POST['date']);
$link   = mysql_real_escape_string($_POST['link']);
$query  = "INSERT INTO bio_manager_pubs(userid,   category,  citation,  date,   link,   requests)"
                             ." VALUES ($userid, '$cat',    '$pub',     $date, '$link', 0       );";
0 голосов
/ 08 ноября 2011

Я думаю, вам нужно заключить каждый из ваших входных данных в mysql_real_escape_string (только один раз!), А не весь запрос. Кроме того, это выглядит нормально для меня.

"INSERT INTO bio_manager_pubs(userid,category,citation,date,link,requests) VALUES ( ".     
mysql_real_escape_string($userid).",'".
mysql_real_escape_string($_POST['category'])."', '".
mysql_real_escape_string(htmlentities($_POST['pub']))."',
FROM_UNIXTIME(".mysql_real_escape_string(strtotime($_POST['date']))."),'".
mysql_real_escape_string($_POST['link'])."',
0)"
...