MySQL игнорирует ограничение NOT NULL - PullRequest
9 голосов
/ 24 марта 2010

Я создал таблицу с ограничениями NOT NULL для некоторых столбцов в MySQL. Затем в PHP я написал скрипт для вставки данных с запросом на вставку. Когда я опускаю один из столбцов NOT NULL в этом операторе вставки, я ожидаю сообщение об ошибке от MySQL, и я ожидаю, что мой скрипт потерпит неудачу. Вместо этого MySQL вставляет пустые строки в поля NOT NULL. В других пропущенных полях данные имеют значение NULL, что нормально. Может кто-нибудь сказать мне, что я здесь не так сделал?

Я использую эту таблицу:

CREATE TABLE IF NOT EXISTS tblCustomers (
  cust_id int(11) NOT NULL AUTO_INCREMENT,
  custname varchar(50) NOT NULL,
  company varchar(50),
  phone varchar(50),
  email varchar(50) NOT NULL,
  country varchar(50) NOT NULL,
  ...
  date_added timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP,
  PRIMARY KEY (cust_id)
) ;

А это оператор вставки:

$sql = "INSERT INTO tblCustomers (custname,company) 
        VALUES ('".$customerName."','".$_POST["CustomerCompany"]."')";
$res = mysqli_query($mysqli, $sql);

Или используя переменные связывания:

$stmt = mysqli_prepare($mysqli, "INSERT INTO tblCustomers (custname,company, email, country) VALUES (?, ?, ?, ?)");

mysqli_stmt_bind_param($stmt, 'ssss', $customerName, $_POST["CustomerCompany"], $_POST["CustomerEmail"], $_POST["AddressCountry"]);
mysqli_stmt_execute($stmt);
mysqli_stmt_close($stmt);

Ответы [ 3 ]

16 голосов
/ 24 марта 2010

Если вы уверены, что не используете явные значения по умолчанию, проверьте строгий режим:

SELECT @@GLOBAL.sql_mode;
SELECT @@SESSION.sql_mode;

Тип данных MySQL Значения по умолчанию

Начиная с MySQL 5.0.2, если столбец определение не содержит явного Значение DEFAULT, MySQL определяет значение по умолчанию следующее:

Если столбец может принимать значение NULL как значение, столбец определяется с явное предложение DEFAULT NULL. Это так же, как и до 5.0.2.

Если столбец не может принимать значение NULL в качестве значение, MySQL определяет столбец с нет явного предложения DEFAULT. Для данных запись, если вставить или заменить заявление не включает в себя значение для столбец или наборы операторов UPDATE столбец в NULL, MySQL обрабатывает столбец в соответствии с режимом SQL в эффект в то время:

  • Если режим строгого SQL не включен, MySQL устанавливает для столбца значение неявное значение по умолчанию для столбца тип данных.

  • Если включен строгий режим, возникает ошибка для транзакционных таблиц и заявление откатывается. За нетранзакционные таблицы, ошибка происходит, но если это произойдет для второй или последующий ряд многострочный оператор, предыдущий строки будут вставлены.

Режимы SQL сервера

4 голосов
/ 24 марта 2010

То, что вы делаете неправильно, строит ваш запрос, используя строки вместо параметров связывания.

Помимо уязвимости SQL-инъекции, нулевые значения преобразуются в пустые строки еще до того, как база данных их видит.

$x = null;
print_r("VALUES ('$x', 42)");

Выходы:

VALUES ('', 42)

Другими словами, вы вставляете пустую строку, а не NULL. Чтобы вставить NULL, вам нужно было бы написать это:

VALUES (NULL, 42)

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

1 голос
/ 24 марта 2010

Я согласен с Марком Байерсом - ваш php неверен для вашего поведения.

Re: Отметить комментарий к параметрам привязки, проверить PDO в PHP

Если вы по-прежнему не хотите использовать параметры, попробуйте следующее:


if (isset($customerName) && $customerName != '')
{
  $c = '\'' . $customerName . '\'';
} else {
  $c = 'null';
}

if (isset($_POST['CustomerCompany']) && $_POST['CustomerCompany'] != '')
{
  $cc = '\'' . $_POST['CustomerCompany'] . '\'';
} else {
  $cc = 'null';
}

$sql = 'INSERT INTO tblCustomers (custname,company) 
        VALUES ('.$c.','.$cc.')';

Редактировать: Рассматривали ли вы просто проверку в своем PHP-коде, чтобы убедиться, что значения не являются пустыми / пустыми? Таким образом, вы могли бы вообще избежать поездки в базу данных (основываясь на моей интерпретации вашего комментария)? Не совсем ответ на поведение MySQL, но может решить вашу проблему.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...