“НЕ В” пункте в LINQ к Объектам

Внимание: примерный код этого ответа (например, примерный код вопроса) использует расширение PHP mysql, которое устарело в PHP 5.5.0 и полностью удалено в PHP 7.0.0.

Если вы используете последнюю версию PHP, опция mysql_real_escape_string, описанная ниже, больше не будет доступна (хотя mysqli::escape_string является современным эквивалентом). В настоящее время опция mysql_real_escape_string имеет смысл только для устаревшего кода на старой версии PHP.


У вас есть два варианта - экранирование специальных символов в вашем unsafe_variable или использование параметризованный запрос. Оба будут защищать вас от SQL-инъекций. Параметрированный запрос считается лучшей практикой, но для его использования потребуется переходить на более новое расширение mysql в PHP.

Мы рассмотрим нижнюю строку удара, которая будет первой.

//Connect

$unsafe_variable = $_POST["user-input"];
$safe_variable = mysql_real_escape_string($unsafe_variable);

mysql_query("INSERT INTO table (column) VALUES ('" . $safe_variable . "')");

//Disconnect

См. также информацию о функции mysql_real_escape_string .

Чтобы использовать параметризованный запрос, вам нужно использовать MySQLi , а не функции MySQL . Чтобы переписать ваш пример, нам понадобится что-то вроде следующего.

prepare("INSERT INTO table (column) VALUES (?)");

    // TODO check that $stmt creation succeeded

    // "s" means the database expects a string
    $stmt->bind_param("s", $unsafe_variable);

    $stmt->execute();

    $stmt->close();

    $mysqli->close();
?>

Ключевая функция, которую вы хотите прочитать, будет mysqli::prepare .

Также, как предложили другие, вы можете сочтет полезным / легче повысить уровень абстракции с помощью чего-то вроде PDO .

Обратите внимание, что случай вы спросили об этом довольно просто, и что более сложные случаи могут потребовать более сложных подходов. В частности:

  • Если вы хотите изменить структуру SQL на основе пользовательского ввода, параметризованные запросы не помогут, и требуемое экранирование не распространяется на mysql_real_escape_string. В этом случае вам лучше было бы пропускать вход пользователя через белый список, чтобы обеспечить доступ только «безопасных» значений.
  • Если вы используете целые числа от пользовательского ввода в состоянии и берете mysql_real_escape_string, вы столкнетесь с проблемой, описанной в Polynomial в комментариях ниже. Этот случай более сложный, поскольку целые числа не будут окружены кавычками, поэтому вы можете справиться, подтвердив, что пользовательский ввод содержит только цифры.
  • Есть, вероятно, другие случаи, о которых я не знаю. Вы можете найти , этот является полезным ресурсом для некоторых более тонких проблем, с которыми вы можете столкнуться.
46
задан meagar 22 May 2012 в 14:23
поделиться

2 ответа

Если Вы используете набор в оперативной памяти в качестве своего фильтра, вероятно, лучше использовать отрицание, Содержит (). Обратите внимание, что это может перестать работать, если список будет слишком длинным, то, в этом случае необходимо будет выбрать другую стратегию (см. ниже для использования стратегии полностью ориентированного на DB запроса).

   var exceptionList = new List<string> { "exception1", "exception2" };

   var query = myEntities.MyEntity
                         .Select(e => e.Name)
                         .Where(e => !exceptionList.Contains(e.Name));

, Если Вы исключаете на основе другого запроса базы данных с помощью Except, мог бы быть лучший выбор. (Вот ссылка к поддерживаемым расширениям Набора в LINQ к Объектам)

   var exceptionList = myEntities.MyOtherEntity
                                 .Select(e => e.Name);

   var query = myEntities.MyEntity
                         .Select(e => e.Name)
                         .Except(exceptionList);

, Это принимает сложный объект, в котором Вы исключаете определенные, зависящие некоторое свойство другой таблицы, и хотите названия объектов, которые не исключены. Если бы Вы хотели весь объект, то необходимо было бы создать исключения, поскольку экземпляры объекта классифицируют таким образом, что они удовлетворили бы оператор равенства по умолчанию (см. документы ).

92
ответ дан tvanfosson 26 November 2019 в 20:13
поделиться

Попытка:

from p in db.Products
where !theBadCategories.Contains(p.Category)
select p;

, Каков SQL-запрос, который Вы хотите перевести в запрос Linq?

14
ответ дан tvanfosson 26 November 2019 в 20:13
поделиться
Другие вопросы по тегам:

Похожие вопросы: