Подтвердить что ты не робот

Действие MVC с дополнительными параметрами - что лучше?

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

public ActionResult Action(int? x) // get MVC to bind null when no parameter is provided
{
    if(x.HasValue)
    {
        // do something
    }
}

ИЛИ

public ActionResult Action(int? x = null) // C# optional parameter (virtual overload)
{
    if(x.HasValue)
    {
        // do something
    }
}
4b9b3361

Ответ 1

Я никогда не видел вторую сигнатуру действия на практике и не вижу никакой пользы от нее.

Первый, как правило, охватывает все сценарии:

  • Если параметр не отправлен (GET /somecontroller/action), значение аргумента x будет равно нулю внутри действия
  • Если передается x-параметр, но он не является допустимым целым числом (GET /somecontroller/action?x=abc), значение аргумента x будет равно null внутри действия, и модельное состояние будет недействительным
  • Если отправляется x-параметр и значение представляет действительное целое число (GET /somecontroller/action?x=123), то ему присваивается x.

В моих примерах я использовал запросы GET с параметрами строки запроса, но, очевидно, то же самое относится к другим глаголам HTTP, и если x был параметром маршрута.

Ответ 2

Вам нужно указать необязательное значение параметра, если оно будет чем-то другим, кроме null.

MVC3 автоматически установит null в качестве значения вашего параметра, если ничего не указано в перегрузке или в вызове Action.

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

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

Ответ 3

Лучшее решение Asp.net MVC - используйте селектор действия действий

Почему бы не упростить методы действий контроллера, удалив ненужную ветвь кода и получив такой код:

public ActionResult Index()
{
    // do something when there no id
}

[RequiresRouteValues("id")]
public ActionResult Index(int id)
{
    // do something when id is present
}

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

По моему мнению, это наилучшее решение этой проблемы, потому что:

  • Это упрощает код, удаляя ненужную ветку
  • Делает код более удобным для обслуживания (из-за меньшей сложности)
  • Расширяет структуру MVC Asp.net как можно и должна
  • Сохраняет типы параметров, как они должны быть, без необходимости их пропускания.
  • и др.

В любом случае. Все подробности об этой технике подробно описаны в связанной записи.