Как изменить параметр в Request в C#?


10 0

Как изменить параметр в Request в C#? Проблема в том, что MS сделала этот параметр только для чтения.

Интересно, а нафига Microsoft сделала параметры Request только для чтения. Вот реально не вижу смысла защищать их от изменения пользователям. В PHP перед выполнением сценария я могу пройтись по всем значениям $_GET, $_POST и $_COOKIES и экранировать их так, чтобы никакая зараза не проникла в мои сценарии.

У меня в каждом сценарии вызывается функции подключения к базе данных. В этой же функции я экранирую все, что может вызывать опасность. Например, $_GET параметры экранируются так:

 foreach ($_GET as $inx => $val) {
 $_GET[$inx] = htmlspecialchars($_GET[$inx]);
 $_GET[$inx] = ini_get(magic_quotes_gpc)?$_GET[$inx]:addslashes($_GET[$inx]); 
}
 

Я это уже описывал в книге PHP глазами хакера. Такая защита еще не 100% безопасность, но позволяет уже более спокойно обращаться к параметрам в массиве $_GET.

В C# я такого сделать не могу, потому что там Request["параметр"] не изменямы и только для чтения. Не знаю почему и зачем это нужно было делать. В C# мне приходится постоянно думать о том, что значениям доверять нельзя и нужно обязательно экранировать значения, что совершенно неудобно и больше способствует совершению ошибок. Чтобы не делать ошибок, я написал класс Helper, который состоит из статических методов типа GetInt или GetString:

public static string GetString(string name, string defValue) {
  if (Request[name] == null)
    return defValue;
  return HttpUtility.HtmlEncode(Request[name]);
}

Подобным же макаром работают методы GetInt и GetDate. Таким образом, мне достаточно удобно преобразовывать данные из параметров, а так же защищать строки от XSS ошибок. Главное не забывать везде использовать свой хелпер и никогда не выплевывать на страницу значение Request без проверки.

И все же возможность изменять Request была бы на много удобнее, потому что можно было бы только один раз пройтись по всем параметрам и все исправить. Да и с unit тестами это помогало бы. Ведь при работе с тестами request не существует и приходится его как-то выдумывать и имитировать. Но как было бы удобнее просто создать Request программно.

Или если пользователь не передал какой-то параметр, было бы просто зашибительски взять и создать его как значение по умолчанию в Request.

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


Понравилось? Кликни Лайк, чтобы я знал, какой контент более интересен читателям. Заметку пока еще никто не лайкал и ты можешь быть первым


Комментарии

Zhenya

01 Февраля 2012

А что за параметр defValue? Предполагается,что если не пройдет проверка его вывести?


Антон Иванов

01 Февраля 2012

Интересно, а "Extension method" работает для Request, что то типа Request.getString("") получится замутить? Помоему будет чуть чуть удобнее.


Михаил Фленов

01 Февраля 2012

Если параметр не существует, не передан пользователем, то вернуть значение по умолчанию.

Меня устраивает и отдельный класс


Ник

01 Февраля 2012

$_GET[$inx] = ini_get(magic_quotes_gpc)?$_GET[$inx]:addslashes($_GET[$inx]);

а что делает эта строка?


Михаил Фленов

01 Февраля 2012

Если не включен параметр magic_quotes_gpc, то экранировать одинарные кавычки самостоятельно с помощью addslashes


Ancort

01 Февраля 2012


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

Ваш покорный слуга считает это не очень хорошей практикой. Хотя в Пыхе она и удобна, сам пользовался. Экранировать данные лучше перед занесением в базу. И использовать, наверно, mysql_real_escape_string а не addslashes какой-нибудь.
magic_quotes_gpc - какой даун придумал эту опцию?
В NET мне вручную не приходилось данные экранировать. Может я недостаточно времени уделял вопросу проверки данных? Но кавычки нормально обрабатываются, при попытке передать теги в запросе будет выброшено исключение: потенциально опасные данные.


Михаил Фленов

01 Февраля 2012

Ваш покорный слуга считает это не очень хорошей практикой.


Что плохого?


Но кавычки нормально обрабатываются, при попытке передать теги в запросе будет выброшено исключение: потенциально опасные данные.


Да зачем оно мне нужно это исключение. Отключать его нужно на фиг. А что если пользователю действительно нужно передать < в запросе, что ему теперь ручками писать %lt;? Самая тупая опция в .NET, которую нужно отключать. Хотя я сам иногда не отключаю, потому что забываю сам иногда экранировать параметры.


Денис

05 Февраля 2012

Миша, ты на чем больше предпочитаешь писать сайты, на php или asp.net mvc? Твое мнение, по скорости работы они примерно одинаковы, или что-то быстрее?


Михаил Фленов

05 Февраля 2012

PHP для меня проще и удобнее, но mvc с синтаксисом razor мне очень понравился. Если делать что-то крупное, то я бы выбрал mvc. Жаль, что MonoDevelop до сих пор не поддерживает Razor. Говорят, можно стыбрить какую-то DLL с VS и после некоторых махинаций она начинает работать в MonoDevelop, но жду родной интеграции.


Sat

07 Февраля 2012

а нафига Microsoft сделала параметры Request только для чтения


C# позиционируется как компилируемый язык. Более того, в эту поделку были включены идеи Н.Вирта о безопасном программировании как таковом.
Массивы же довольно не управляемые структуры, более того часто использующиеся в программировании. Предполагаю, что MS намеряно запретила изменять этот массив данных во избежании подобных ошибок в Delphi
Пример:

type
  str = array [0..2] of char;
  str2 = array [0..4] of char;
var
  a :  str;
  b : str2;

procedure Append(var res,app: array of char);
begin
  MOVE(app,res,5); //<-- Так нельзя,размер res не совпадает с размером app
end;

begin
  a:='aaa';
  b:='bbbbb';
  Append(a,b);
  ShowMessage(a+' '+IntToStr(Length(b)));
end.

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

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

По этому наверно и в С# придёться делать всё через клоаку...


Добавить Комментарий

Еще что-нибудь

Хотите найти еще что-то интересное почитать? Можно попробовать отфильтровать заметки на блоге по категориям.

О блоге

Программист, автор нескольких книг серии глазами хакера и просто блогер. Интересуюсь безопасностью, хотя хакером себя не считаю

Обратная связь

Без проблем вступаю в неразборчивые разговоры по e-mail. Стараюсь отвечать на письма всех читателей вне зависимости от страны проживания, вероисповедания, на русском или английском языке.

Пишите мне