ASP.NET MVC - TempData - Хорошая или плохая практика

Я использую метод AcceptVerbs, подробно описанный в сообщении блога Скотта Гу Preview 5, для работы с записями формы в ASP.NET MVC:

  • Пользователь получает пустую форму через GET
  • Пользователь отправляет заполненную форму через POST в то же действие
  • Действие проверяет данные, предпринимает соответствующие действия и перенаправляет на новое представление.

Так что мне не нужно использовать TempData. Тем не менее, теперь мне нужно добавить в этот процесс шаг «подтверждения», который, похоже, требует использования TempData.

По какой-то причине у меня есть отвращение к использованию TempData - это что-то, что нужно для этого.

Это действительно серьезная проблема, или я ее выдумываю?


person anonymous    schedule 22.12.2008    source источник
comment
Сделайте шаг подтверждения в виде диалогового окна JavaScript. Меньше обращений к серверу, и вы не столкнетесь с этой проблемой.   -  person ajma    schedule 19.02.2009


Ответы (8)


Я думаю, что временные данные - это механизм «запустил и забыл» для уведомления пользователя. Замечательно напоминать им о том, что они недавно сделали, но я также не решился бы сделать это обязательным шагом в каком-то пользовательском процессе. Причина в том, что если они обновят страницу, я считаю, что она исчезнет. Что ж, я думаю, я также не решаюсь использовать его, поскольку на самом деле не совсем ясно, насколько он надежен.

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

person Frank Schwieterman    schedule 25.12.2008

Нет нужды испытывать отвращение к TempData ... Но при неправильном использовании это, несомненно, может быть признаком плохого дизайна. Если вы используете URL-адреса RESTful, TempData - лучший способ передачи сообщений из ваших действий POST в действия GET. Учти это:

У вас есть форма по адресу URL Products / New. Форма Сообщает о продуктах / Create, которая проверяет форму и создает продукт. В случае успеха контроллер перенаправляет на URL-адрес Products / 1, а в случае ошибки перенаправляет обратно в продукты / New для отображения сообщений об ошибках.

Products / 1 - это просто стандартное действие GET для продукта, но мы хотели бы, чтобы отображалось сообщение о том, что вставка прошла успешно. TempData идеально подходит для этого. Добавьте сообщение в TempData в Post Controller и поместите логику if в представление, и все готово.

В случае сбоя я добавлял значения, введенные в formCollection, и набор сообщений об ошибках в TempData в действии публикации и перенаправлял на исходное действие Prodcuts / New. Я добавил логику в представление, чтобы заполнить входные данные формы ранее введенными значениями вместе с любыми сообщениями об ошибках. Мне это кажется красивым и чистым!

person JasonD    schedule 19.02.2009
comment
Зачем нужна эта дополнительная работа, если вы можете публиковать сообщения непосредственно в Products/New? Какое значение добавляет Products/Create? - person mpen; 11.12.2011
comment
@Mark, использование Products / Create предотвращает ситуацию, когда пользователь завершает действие посредством обратной передачи, а затем при более позднем обновлении (или закладке и возврате) случайно повторно завершает действие. Для получения дополнительной информации см. en.wikipedia.org/wiki/Post/Redirect/Get - person ehdv; 15.12.2011
comment
@ehdv: Но так ли это на самом деле? В случае успеха он перенаправляется на другую страницу, в случае неудачи он должен отображать ошибки формы, и никаких действий предпринимать не следует, так что никакого вреда. Это только предотвратит раздражение, если вы уверены, что хотите повторно опубликовать сообщение, чего я часто действительно хочу. Думаю, это зависит от вашего дизайна, так что я могу понять вашу точку зрения. - person mpen; 15.12.2011

Я думаю, вам следует подумать, прежде чем использовать TempData. TempData хранится в сеансе, и это может иметь последствия для вас, если:

  1. Вы сейчас не используете сеансы на своем сайте
  2. У вас есть система, которую необходимо масштабировать до высокой пропускной способности, т.е. вы предпочитаете вообще избегать состояния сеанса.
  3. Вы не хотите использовать файлы cookie (я не знаю, насколько хорошо MVC сейчас поддерживает сеансы без файлов cookie)

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

person John Rayner    schedule 23.12.2008
comment
TempData не обязательно хранить в сеансе, хотя это поставщик по умолчанию - вероятно, поэтому его нет в методической документации. Также существует провайдер куки, как пример того, как написать собственный провайдер. - person FinnNk; 09.07.2010

У меня есть метод GetModel, который сначала проверяет TempData ["модель"] и возвращает его. В противном случае GetModel загружает соответствующие данные из базы данных.

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

person Todd Smith    schedule 22.12.2008
comment
Да, я столкнулся с этим: (1) проверить, существует ли запись, если она действительна, перенаправить на страницу (2) загрузить запись для отображения для пользователя. Таким образом, база данных подвергается проверке и отображению. Я почти использую для этого TempData, но мне хотелось проверить мнения. Мне нравится, что ваш метод сдерживает это. - person anonymous; 22.12.2008
comment
В этом случае было бы лучше использовать правильный механизм кеширования. - person nicodemus13; 21.03.2014

Ознакомьтесь с бессессионными контроллерами в MVC3. Оказалось, что использование сеанса предотвращает параллельное выполнение запросов одного пользователя и, таким образом, приводит к снижению производительности.

Поскольку tempdata по умолчанию использует сеанс, вы не сможете использовать эту функцию. Вы можете переключиться на использование файлов cookie для временных данных, но это немного неудобно (по крайней мере, для меня). Тем не менее, все еще чище, чем viewstate, так что, может быть, это не такой уж большой отказ.

person aaimnr    schedule 13.12.2010
comment
Вы правы в отношении контроллеров без сеанса, а TempData использует сеанс. НО ЖДАТЬ! Сессия - это НЕ плохо, и вы можете смешивать и сочетать бессессионный с контроллерами сеанса. Вам действительно нужны контроллеры Session_less_, когда вы делаете много вызовов AJAX на сервер (из браузера). Когда вы просто попадаете на одну страницу за раз ... вам не нужно быть без сеанса. На самом деле, это НЕ должно дать вам никакой пользы ... потому что вы обращаетесь к серверу только ОДИН РАЗ. Так что можно смешивать и сочетать. - person Pure.Krome; 03.03.2011

Почему у вас такое отвращение? Эта штука просто делает свое дело и делает это хорошо :)

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

person maxnk    schedule 22.12.2008

Это похоже на использование ViewData, то есть, вероятно, это не угроза безопасности. Но я бы предпочел использовать ViewData, чем TempData. Здесь можно найти сравнение: http://www.squaredroot.com/2007/12/20/mvc-viewdata-vs-tempdata/.

В зависимости от дизайна вы всегда можете сохранить пользователя / корзину или то, что вам нужно, во временных данных в базе данных и просто иметь поле «IsReady», которое указывает, завершено оно или нет, что делает его расширяемым на будущее, если вы хотите принять помните, что люди могут закрыть свои браузеры.

person Filip Ekberg    schedule 22.12.2008
comment
Примечание: статья, на которую вы ссылаетесь, была актуальной для своего времени, но верна только для MVC1. TempData значительно изменилась в MVC2. - person mikemanne; 21.10.2011
comment
@mikemanne, да. Но ответ датирован концом 2008 года. Но, может быть, ответ следует обновить? - person Filip Ekberg; 22.10.2011

Все хорошие ответы, вы смотрели на это для передачи сообщений.

TempData и Session - не лучшая идея для архитектур RESTful, поскольку большинство сеансов хранятся в памяти. Поэтому, когда вы хотите использовать ферму серверов, сеанс пользователя будет существовать на одном сервере, а их следующий запрос может быть отправлен на другой сервер.

При этом взгляните на использование TempData для передачи сообщений здесь.

http://jameschambers.com/2014/06/day-14-bootstrap-alerts-and-mvc-framework-tempdata/

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

person Warren    schedule 12.05.2015