Я просмотрел все сообщения об этом и не имел успеха. Я могу позвонить в контроллер OData
и посмотреть данные, полученные, отображенные и упакованные. Метод контроллера выходит, и я получаю 406 - Not Acceptable
. Я только с помощью System.Web.OData
имен (OData Version v4.0.30319) и, используя Postman
, я вручную установить Content
и Accept
заголовки «приложения/JSON» не повезлоWeb API OData Controller возвращает «406 - недопустимо» при сопоставлении результатов
Может быть, я пропустил что-то за последние 2 часа, читая сообщения всех по аналогичным проблемам. Любые указатели будут оценены.
UPDATE: Проблема, как представляется, в Mapper кода (Automapper
), как указывалось на Игорь ниже. Похоже, есть обязательство вернуть объект базы данных (EF), а не сопоставленный класс. С этими знаниями я нашел этот пост SO, но он не предлагает решения: ApiController vs ODataController when exposing DTOs. Должны ли мы заставлять возвращать объекты базы данных или отображать результаты? Если это так, для меня это прерыв.
Контроллер:
[EnableQuery]
[HttpGet]
public async Task<IHttpActionResult> Get()
{
var list = await db.ConfigSets.ToListAsync();
Mapper.CreateMap<ConfigSet, ConfigSetDTO>();
var configSetDTOs = Mapper.Map<List<ConfigSet>, List<ConfigSetDTO>>(list);
return Ok(configSetDTOs); //IT LOOKS GOOD HERE!
}
WebApiConfig:
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
config.MapHttpAttributeRoutes();
config.EnableCors();
// OData - must be before config.Routes when using a prefix. In this case "api"
config.MapODataServiceRoute("odata", "api", GetEdmModel(), new DefaultODataBatchHandler(GlobalConfiguration.DefaultServer));
config.EnsureInitialized();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
private static IEdmModel GetEdmModel()
{
var builder = new ODataConventionModelBuilder();
builder.Namespace = "Services";
builder.ContainerName = "DefaultContainer";
builder.EntitySet<ConfigSet>("Configuration");
var edmModel = builder.GetEdmModel();
return edmModel;
}
}
Я не уверен, что возвращает «Mapper.Map», но что бы это ни было, он должен реализовывать «IQueryable» или их общий. Пробовали ли вы тестировать его с помощью жесткого кодированного экземпляра «List», а в 'return' call do return' Ok (myList.AsQueryable()); '? Это должно помочь вам сузить область проблемы, общую конфигурацию или данные или формат данных, которые вы пытаетесь вернуть. –
Igor
@ Igor..Mapper - Automapper. Я пробовал этот код без него и того, что вы предложили, и получил тот же результат. –
Думаю, я это вижу. 'Строитель.EntitySet («Конфигурация»); 'обозначает, что ожидаемый тип, который должен быть возвращен методом Get(), имеет тип' ConfigSet', но вы возвращаете тип 'ConfigSetDTO'. Чтобы убедиться, что это действительно проблема, попробуйте вернуть жесткий кодированный список экземпляров 'ConfigSet', но вызовите' AsQueryable() 'в методе' Ok'. Т.е.; 'return Ok (myConfigSetList.AsQueryable());' –
Igor