我迁移到了WebAPI 2.2 RC(Microsoft.AspNet.WebApi -Version 5.2.0-rc),因为我在所有查询中只得到406(不可接受)作为状态响应,例如:
http://localhost:7923/api/Quotes(1)
OData服务配置
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
config.MapHttpAttributeRoutes();
config.EnableSystemDiagnosticsTracing();
config.MapODataServiceRoute("api", "api", CreateEdmModel());
}
private static IEdmModel CreateEdmModel()
{
var odataModelBuilder = new ODataConventionModelBuilder();
odataModelBuilder.EntitySet<Tag>("Tags");
odataModelBuilder.EntitySet<Author>("Authors");
EntitySetConfiguration<Quote> quoteEntitySetConfiguration = odataModelBuilder.EntitySet<Quote>("Quotes");
FunctionConfiguration getQuotesRandomFunction = quoteEntitySetConfiguration.EntityType.Collection.Function("Random");
getQuotesRandomFunction.Parameter<int>("count");
getQuotesRandomFunction.ReturnsCollectionFromEntitySet<Quote>("Quotes");
return odataModelBuilder.GetEdmModel();
}
}
QuotesController
public class QuotesController : ODataController
{
private WhatAQuoteDb db = new WhatAQuoteDb();
[ODataRoute("Default.Random(count={count})")]
[EnableQuery]
public IHttpActionResult GetQuotesRandom(int count)
{
return Ok(db.Quotes.OrderBy(quote => Guid.NewGuid()).Take(count));
}
// GET: odata/Quotes
[EnableQuery]
public IQueryable<Quote> GetQuotes()
{
return db.Quotes;
}
// GET: odata/Quotes(5)
[EnableQuery]
public SingleResult<Quote> GetQuote([FromODataUri] int key)
{
return SingleResult.Create(db.Quotes.Where(quote => quote.Id == key));
}
// PUT: odata/Quotes(5)
public async Task<IHttpActionResult> Put([FromODataUri] int key, Quote quote)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
if (key != quote.Id)
{
return BadRequest();
}
db.Entry(quote).State = EntityState.Modified;
try
{
await db.SaveChangesAsync();
}
catch (DbUpdateConcurrencyException)
{
if (!QuoteExists(key))
{
return NotFound();
}
else
{
throw;
}
}
return Updated(quote);
}
// POST: odata/Quotes
public async Task<IHttpActionResult> Post(Quote quote)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
db.Quotes.Add(quote);
await db.SaveChangesAsync();
return Created(quote);
}
// PATCH: odata/Quotes(5)
[AcceptVerbs("PATCH", "MERGE")]
public async Task<IHttpActionResult> Patch([FromODataUri] int key, Delta<Quote> patch)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
Quote quote = await db.Quotes.FindAsync(key);
if (quote == null)
{
return NotFound();
}
patch.Patch(quote);
try
{
await db.SaveChangesAsync();
}
catch (DbUpdateConcurrencyException)
{
if (!QuoteExists(key))
{
return NotFound();
}
else
{
throw;
}
}
return Updated(quote);
}
// DELETE: odata/Quotes(5)
public async Task<IHttpActionResult> Delete([FromODataUri] int key)
{
Quote quote = await db.Quotes.FindAsync(key);
if (quote == null)
{
return NotFound();
}
db.Quotes.Remove(quote);
await db.SaveChangesAsync();
return StatusCode(HttpStatusCode.NoContent);
}
// GET: odata/Quotes(5)/Author
[EnableQuery]
public SingleResult<Author> GetAuthor([FromODataUri] int key)
{
return SingleResult.Create(db.Quotes.Where(m => m.Id == key).Select(m => m.Author));
}
// GET: odata/Quotes(5)/Tags
[EnableQuery]
public IQueryable<Tag> GetTags([FromODataUri] int key)
{
return db.Quotes.Where(m => m.Id == key).SelectMany(m => m.Tags);
}
protected override void Dispose(bool disposing)
{
if (disposing)
{
db.Dispose();
}
base.Dispose(disposing);
}
private bool QuoteExists(int key)
{
return db.Quotes.Count(e => e.Id == key) > 0;
}
}
答案 0 :(得分:14)
我检查了您的解决方案,发现您使用了服务参考。
但是,添加服务引用并不支持OData V4,生成的代码中的版本为V3。
您可以尝试OData T4代码生成器来生成客户端代码。
查看以下博客:
<强> 更新 强>
我再次检查了你的解决方案,发现了问题:
您使用的ODataController是V3!
如果您需要V4版本,则需要更改控制器cs文件中的using命名空间
来自
using System.Web.Http.OData;
要
using System.Web.OData;
此外,还有一个问题是,当我启动项目时,以下模板无效。
[ODataRoute("Default.Random(count={count})")]
我认为你定义的随机函数是一个函数导入,你应该这样定义:
FunctionConfiguration getQuotesRandomFunction = odataModelBuilder.Function("Random");
并且函数import不应该添加名称空间,模板应该是:
[ODataRoute("Random(count={count})")]
如果您有其他问题,请告诉我。