Asp.Net MVC Beta: предыдущие данные RouteData переопределяют текущие данные RouteData?

У меня есть что-то похожее на следующий метод:

    public ActionResult Details(int id)
    {
        var viewData = new DetailsViewData
        {
            Booth = BoothRepository.Find(id),
            Category = ItemType.HotBuy
        };
        return View(viewData);
    }

и следующий маршрут:

routes.MapRoute("shows","shows/{controller}/{action}/{id}", new {id = 0});

Все работало нормально до бета-версии, когда у меня был Preview 3. Теперь метод будет правильно заполнять id при первом выполнении действия. Однако второй раз контроллер ModelState содержит значение идентификатора последнего использования. Это вызывает ActionInvoker использовать его в параметре метода вместо Route значение.

Поэтому, если я дважды вызову действие для двух разных сущностей, результат будет таким:

www.mysite.com/shows/Booth/Details/1  => Details(1)
www.mysite.com/shows/Booth/Details/2  => Details(1)  //from ModelState["id"]

Из моего быстрого сканирования с помощью Reflector кажется, что сначала он привязывает параметры к ModelState, а затем к Routes. Тем не менее, я никогда не публиковал ничего от модели. Насколько я могу сказать, ModelState не должен содержать ничего.

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

РЕДАКТИРОВАТЬ: я обнаружил, что эта проблема на самом деле является признаком того, что, как представляется, ошибка с DefaultValueProvider, если вы создаете экземпляр контроллера из контейнера IoC, который существует в течение всего времени жизни приложения Asp.Net. Что происходит, когда DefaultValueProvider использует Первый ControllerContext передается контроллеру и никогда не обновляет его, пока контроллер не будет воссоздан. Это заставляет старые RouteData использоваться для параметров метода вместо текущих RouteData.

4 ответа

Решение

Мне трудно сказать, что вы ожидаете и что происходит от вашего поста. Возможно, в вашем методе BoothRepository.Find есть ошибка, которая каждый раз возвращает одно и то же?

ModelBinder не должен влиять на этот метод, потому что параметром метода действия является простой тип, int.

Были ли оба этих запроса GET? Если у вас все еще есть проблемы, можете ли вы попытаться создать простейшее возможное воспроизведение и отправить его по электронной почте в philha - microsoft dot com?

РЕДАКТИРОВАТЬ: Проблема в конечном итоге заключалась в том, что разработчик пытался повторно использовать провайдер значений в запросах (имея в виду, что Castle Windsor управляет жизненным циклом контроллеров). В настоящее время нет поддержки для повторного использования экземпляров контроллера в запросах, как это было бы с IHttpHandler, который имеет свойство IsReusable. В общем, повторное использование контроллеров в разных запросах требует от вас гораздо больше работы.:)

Проблема в LifeStyle, я полностью упустил из виду тот факт, что он был определен, что означает, что по умолчанию контроллеры будут использовать образ жизни Singleton. Установка LifeStyle на Transient для всех контроллеров решит эту проблему.

Если вы используете spring.net, измените синглтон контроллера на "false"

Это распространенная проблема при использовании поведения Singleton с контейнером IoC, таким как Spring.NET или Windsor. Контроллеры не должны иметь одноэтапное поведение, потому что ControllerContext для каждого запроса, очень похоже на HttpContext.

Другие вопросы по тегам