Установка свойства чтения источника данных сетки пользовательского интерфейса Kendo с помощью обработчика в ASP.NET Core MVC с помощью Razor Pages

Я использую Kendo UI для пакета ASP.NET Core MVC с веб-приложением Razor Pages, поэтому я пытаюсь использовать технику обработчика для операций сервера сетки.

@(Html.Kendo().Grid<CustomerViewModel>()
        .Name("CustomersGrid")
        .Columns(columns =>
        {
            columns.Bound(x => x.CustomerId).Title("Student ID");
            columns.Bound(x => x.CustomerName).Title("Name");
        })
        .Pageable()
        .Sortable()
        .DataSource(dataSource => dataSource
            .Ajax()
            .PageSize(20)
            .ServerOperation(true)
            .Read(read => read.Url("/Customers?handler=Read")))
         )

Я заглянул на вкладку сети, и он делает правильный POST для http://localhost:5000/Customers?handler=Read, однако я не дохожу до точки останова и получаю код состояния 400.

В коде страницы бритвы за методом Action называется OnPostReadAsync.

Есть идеи, почему это не работает? В дополнение к .Url также пытался использовать read.Action и read.Route в свойстве .Read объекта DataSource.

Вот класс с методом действия:

public class IndexModel : PageModel
{
    private readonly ICustomerRepository _customerRepository;
    private readonly IMapper _mapper;

    public IndexModel(ICustomerRepository customerRepository, IMapper mapper)
    {
        _customerRepository = customerRepository;
        _mapper = mapper;
    }

    public IList<CustomerViewModel> Customers { get; set; }

    public async Task<IActionResult> OnPostReadAsync([DataSourceRequest] DataSourceRequest request)
    {
        // THIS IS WHERE I WANT IT TO GO FOR READ

        var customersFromDb = await _customerRepository.FilterAsync();
        return new JsonResult(_mapper.Map<IList<Customer>, IList<CustomerViewModel>>(customersFromDb).ToDataSourceResult(request));
    }
}

person Blake Rivell    schedule 12.12.2018    source источник
comment
мы можем увидеть класс для метода Action?   -  person Jazb    schedule 12.12.2018
comment
@JohnB Я добавил это.   -  person Blake Rivell    schedule 12.12.2018
comment
Разве вы не должны вызывать метод в контроллере вместо метода в вашей модели? Это будет Post метод в вашем Customers контроллере   -  person Jonathan    schedule 12.12.2018
comment
@Jonathan Я использую Razor Pages, и это все усложняет. Вы должны использовать параметр строки запроса обработчика.   -  person Blake Rivell    schedule 12.12.2018
comment
Ах я вижу. Я не знаком с Razor Pages   -  person Jonathan    schedule 12.12.2018
comment
Опять же, я не знаком с Razor Pages, но только что просмотрел часть документации. Разве ваш URL /Customers?handler=read не будет искать OnPostReadAsync действие в модели Customers? Но у вас это есть в модели Index? Кроме того, вы уверены, что POST отправляете этот запрос, а не отправляете GET?   -  person Jonathan    schedule 12.12.2018


Ответы (2)


Возможно, вы уже делаете это, но я не видел этого в вашем коде. Помните, что для Razor Pages требуется маркер защиты от подделки. Вы можете вставить его в свою разметку следующим образом:

@inject Microsoft.AspNetCore.Antiforgery.IAntiforgery Xsrf

И я добавил эту функцию, чтобы установить ее в dataSource запросах сетки:

$(function () {
    const requestVerificationToken = '@Xsrf.GetAndStoreTokens(HttpContext).RequestToken';
    const beforeSend = req => req.setRequestHeader('RequestVerificationToken', requestVerificationToken);
    const grid = $("#grid").getKendoGrid();
    grid.dataSource.transport.options.create.beforeSend = beforeSend;
    grid.dataSource.transport.options.update.beforeSend = beforeSend;
    grid.dataSource.transport.options.destroy.beforeSend = beforeSend;
});

Без этого токена все PageModel пользовательские обработчики вернут 400 ошибок.

Ссылка: Предотвратить перекрестное Атаки подделки запросов сайта (XSRF / CSRF) в ASP.NET Core

person crgolden    schedule 24.01.2019

Для меня использование POST для получения данных неправильно. Если вы хотите использовать GET, добавьте .Type (HttpVerbs.Get) к вашему методу Read:

.DataSource(data =>
{
    data.Ajax()
      .Events(events => events.Error("grid_error"))
      .Read(read => read.Url("./Groups?handler=Read").Type(HttpVerbs.Get));
      //.Sort(sort => sort.Add("Name").Ascending())
      //.PageSize(20);
})

И оставьте свой обычный метод Ajax, но соглашение ожидает OnGet плюс значение, указанное handler = ...

public IActionResult OnGetRead([DataSourceRequest] DataSourceRequest request)
{
    var result = db.Queryable<IdentityRole>();
    return new JsonResult(result.ToDataSourceResult(request));
}

Стиль TagHelper похож:

<datasource type="DataSourceTagHelperType.Ajax" custom-type="AndyB.Identity.IdentityRole">
  <transport>
    <read url="./Groups?handler=Read" type="Get" />
  </transport>
  <sorts>
    <sort field="Name" direction="ascending" />
  </sorts>
</datasource>

Не используйте для вставки, обновления или удаления, продолжайте использовать POST

person AndyB    schedule 22.06.2019