валидация данных
Найдено: 1 запись
Песочница →
Обработка заполняемой пользователем формы: как уменьшить сложность кода?
Работая над написанием административного, да и пользовательского интерфейса, я не раз ловил себя на мысли — а все ли я делаю так, чтобы при минимуме усилий обеспечить оптимальное качество?
Сегодня хотелось бы обсудить вопрос обработки ошибок ввода форм в веб-приложениях. Как, вы все еще всецело доверяете вводимым пользователем данным и считаете сидящее по ту сторону монитора существо священной коровой? Не бойтесь, это пройдет после первой же атаки, если принципы контроля ввода не станут вам ясны раньше. Впрочем, к делу.
Программирую я на PHP, поэтому примеры серверного кода будут на этом языке.
Представим, что мы решили дополнить свой проект формой для заказа обратного звонка. Мало ли — линии часто перегружены, клиент хочет почувствовать свою весомость, мода такая… ну в общем надо. Быстро накидываем простейший html, пишем обработчик — данные красиво легли в базу, в общем — практически готово. Осталось сделать самую малость — написать обработку ошибок. (Конечно, порядок разработки весьма условен). Каким образом можно это проверить введенную пользователем информацию на правильность и уведомить его о результате?
В случае с правильно заполненной формой работы минимум. А вот если пользователь допустил ошибку и данные некорректны, вы вынуждены снова сгенерировать страницу и отправить ее пользователю. При этом крайне желательно значения всех заполненных полей сохранить, что увеличивает ваш код.
Рассмотрим базовую обработку ошибок (считаем что пользовательские данные уже прошли основные проверки и фильтрации):
Нам хочется привнести некоторые удобства для клиента. И на помощь нам приходит…
Функция alert использована лишь в качестве учебного примера, по статистике часть пользователей закроет его не читая, потому что выводится оно в дизайне ОС и не воспринимается как часть веб-страницы.
Еще раз обращу внимание на то, что серверная проверка все равно необходима.
Каждый раз, когда меня просят рассказать зачем это нужно, я вспоминаю примерно год 2004, когда я, начинающий веб-разработчик, познакомился по переписке со славным парнем с Украины, бывшим тогда автором собственной CMS. Пытаясь перенимать опыт, я как-то поинтересовался у него, как он производит обработку ошибок. Выяснилось, что делает он это только при помощи JavaScript. Пришлось уже самому делиться опытом о том, что можно сохранить страницу на компьютер, подменить адрес обработчика формы и отправить данные без валидации. И если валидации не будет уже на сервере, некорректные данные будут восприняты как нормальные, а дальше все будет зависеть от логики приложения. Позже в процессе работы я часто встречал подобные уязвимости. Вывод напрашивается сам собой — если веб-приложение пишется без понимания особенностей взаимодействия браузера клиента и сервера, результат может быть разным.
Проходит время, сложность форм растет и я обращаю свой взор на следующую технологию.
Теперь проверка для удобства вынесена в отдельный метод и немного дополнена, в результате получаем примерно такой код:
Далее в браузере клиента мы можем показать тот же самый алерт или вывести сообщение любым другим удобным для нас способом. Юзабилити на высоте — не требуется перезагрузка страницы, удобство дальнейшей поддержки кода тоже — вся обработка ошибок собрана в одном месте.
Пока форма состоит из небольшого количества полей, не так сложно при добавлении очередного поля модифицировать вывод после приема ошибочных данных. А если данных много? В этом случае есть желание облегчить себе работу и отказаться от такой полной поддержки старых браузеров, убрав вывод данных и получив вот такой код:
Мы существенно упростили себе работу по дальнейшей поддержке кода, при этом сознательно отказавшись от полной поддержки устройств с отключенным JavaScript. Чем-то пришлось жертвовать в угоду собственному удобству. Но такой подход не оправдан, если упор идет на качество разработки.
На данный момент я продолжаю экспериментировать с проверками данных. Все еще ищу идеальное решение, которое было бы еще более оптимальным. С удовольствием выслушаю критику и обсужу все аспекты различных подходов с читателями.
Сегодня хотелось бы обсудить вопрос обработки ошибок ввода форм в веб-приложениях. Как, вы все еще всецело доверяете вводимым пользователем данным и считаете сидящее по ту сторону монитора существо священной коровой? Не бойтесь, это пройдет после первой же атаки, если принципы контроля ввода не станут вам ясны раньше. Впрочем, к делу.
Программирую я на PHP, поэтому примеры серверного кода будут на этом языке.
Представим, что мы решили дополнить свой проект формой для заказа обратного звонка. Мало ли — линии часто перегружены, клиент хочет почувствовать свою весомость, мода такая… ну в общем надо. Быстро накидываем простейший html, пишем обработчик — данные красиво легли в базу, в общем — практически готово. Осталось сделать самую малость — написать обработку ошибок. (Конечно, порядок разработки весьма условен). Каким образом можно это проверить введенную пользователем информацию на правильность и уведомить его о результате?
В случае с правильно заполненной формой работы минимум. А вот если пользователь допустил ошибку и данные некорректны, вы вынуждены снова сгенерировать страницу и отправить ее пользователю. При этом крайне желательно значения всех заполненных полей сохранить, что увеличивает ваш код.
Рассмотрим базовую обработку ошибок (считаем что пользовательские данные уже прошли основные проверки и фильтрации):
<?php $errors = array(); if ( empty($person) || empty($phone) || empty($question) ) { $errors[] = 'Не заполнены обязательные поля'; } if ( count($errors) ) { $template->assign_switch('errors', 1); $template->vars(array( 'ERRORS' => implode(' ', $errors), 'PERSON' => $person, 'PHONE' => $phone, 'QUESTION' => $question ) ); $template->send(); } ?>
Нам хочется привнести некоторые удобства для клиента. И на помощь нам приходит…
JavaScript
<script language="text/javascript"> <!-- // function form_submit() { if ( ( document.forms['callback'].person.value == '' ) || ( document.forms['callback'].phone.value == '' ) || ( document.forms['callback'].question.value == '' ) ) { alert('Не заполнены обязательные поля'); } return; } // --> </script>
Функция alert использована лишь в качестве учебного примера, по статистике часть пользователей закроет его не читая, потому что выводится оно в дизайне ОС и не воспринимается как часть веб-страницы.
Еще раз обращу внимание на то, что серверная проверка все равно необходима.
Каждый раз, когда меня просят рассказать зачем это нужно, я вспоминаю примерно год 2004, когда я, начинающий веб-разработчик, познакомился по переписке со славным парнем с Украины, бывшим тогда автором собственной CMS. Пытаясь перенимать опыт, я как-то поинтересовался у него, как он производит обработку ошибок. Выяснилось, что делает он это только при помощи JavaScript. Пришлось уже самому делиться опытом о том, что можно сохранить страницу на компьютер, подменить адрес обработчика формы и отправить данные без валидации. И если валидации не будет уже на сервере, некорректные данные будут восприняты как нормальные, а дальше все будет зависеть от логики приложения. Позже в процессе работы я часто встречал подобные уязвимости. Вывод напрашивается сам собой — если веб-приложение пишется без понимания особенностей взаимодействия браузера клиента и сервера, результат может быть разным.
Проходит время, сложность форм растет и я обращаю свой взор на следующую технологию.
AJAX
Теперь проверка для удобства вынесена в отдельный метод и немного дополнена, в результате получаем примерно такой код:
<?php $errors = array(); if ( empty($person) || empty($phone) || empty($question) ) { $errors[] = 'Не заполнены обязательные поля'; } $ajax = isset($_REQUEST['ajax']); if ( count($errors) ) { if ( empty($ajax) ) { $template->assign_switch('errors', 1); $template->vars(array( 'ERRORS' => implode(' ', $errors), 'PERSON' => $person, 'PHONE' => $phone, 'QUESTION' => $question ) ); $template->send(); } else { $ajax_handler->send(array( 'errors' => 1, 'error_text' => implode(' ', $errors), ) ); } } else { $ajax_handler->send(array( 'errors' => 0, 'error_text' => '', ) ); } ?>
Далее в браузере клиента мы можем показать тот же самый алерт или вывести сообщение любым другим удобным для нас способом. Юзабилити на высоте — не требуется перезагрузка страницы, удобство дальнейшей поддержки кода тоже — вся обработка ошибок собрана в одном месте.
Вредный совет
Пока форма состоит из небольшого количества полей, не так сложно при добавлении очередного поля модифицировать вывод после приема ошибочных данных. А если данных много? В этом случае есть желание облегчить себе работу и отказаться от такой полной поддержки старых браузеров, убрав вывод данных и получив вот такой код:
<?php if ( count($errors) ) { if ( empty($ajax) ) { header('Location: form.php?error_code=1'); exit(); } } ?>
Мы существенно упростили себе работу по дальнейшей поддержке кода, при этом сознательно отказавшись от полной поддержки устройств с отключенным JavaScript. Чем-то пришлось жертвовать в угоду собственному удобству. Но такой подход не оправдан, если упор идет на качество разработки.
Заключение
На данный момент я продолжаю экспериментировать с проверками данных. Все еще ищу идеальное решение, которое было бы еще более оптимальным. С удовольствием выслушаю критику и обсужу все аспекты различных подходов с читателями.
17.11.2011 16:10+0400