Чтобы объяснить поведение, 3-й аргумент MapRoute (мой акцент)
Объект, который содержит значения по умолчанию route values.
Указав new { controller = "Product", action = "List", page = 1 }
, вы определяете значение маршрута для page
(даже если оно не является сегментом в вашем определении URL) и присваиваете ему значение по умолчанию 1
.
Теперь, когда вы переходите к ../chess?page=2
, он соответствует вашему маршруту Default23
, и значение 'chess' присваивается сегменту {category}
, но ничего не назначается page
, потому что для * нет сегмента 1022 * (это значение строки запроса).
Когда ваш метод List(string category, int page = 1)
выполняется, DefaultModelBinder
оценивает значения для привязки в следующем порядке
- Ранее связанные параметры действия, когда действие является дочерним
Действие
- Значения формы
- Тело запроса JSON (ajax-вызовы)
- Данные маршрута
- Параметры строки запроса
- Прикрепленные файлы
Для GET 1, 2, 3 и 6 не применимы, поэтому DefaultModelBinder
сначала оценивает данные маршрута (RouteData.Values
) и находит значение "chess" для category
(из URL) , Он также находит значение «1» для page
(поскольку вы определили для него значение по умолчанию в определении маршрута).
На данный момент у вас есть category="chess", page=1
.
Затем DefaultModelBinder
оценивает строковые параметры запроса (Request.QueryString
) и находит значение "2" для page
, но, поскольку page
уже установлено, его игнорируют. По умолчанию DefaultModelBinder
связывает первое найденное совпадение и игнорирует все последующие совпадения (если не привязано к свойству IEnumerable
).
Итак, на данный момент (конец процесса привязки) у вас все еще есть category="chess", page=1
.