应用服务移动应用 - “无法在类型'Backend.DataObjects.Game'上找到名为'updatedAt'的属性。”

时间:2016-10-26 02:41:57

标签: c# azure xamarin.forms azure-mobile-services

我正在尝试将Azure Mobile Apps与Xamarin Forms客户端和.net后端一起使用。我正在使用MikeCodesDotNet / App-Service-Helpers来帮助我开始在客户端。我尝试的第一个实体是一个简单的游戏实体。

当客户端加载时,它会使GET请求获得游戏,但它使用updatedAt,似乎服务器需要UpdatedAt。

请求是: ?http://192.168.0.105/Backend/tables/Game $滤波器=(updatedAt%如20Ge%20datetimeoffset%271970-01-01T00:00:00.0000000%2B00:00%27)及$的OrderBy = updatedAt&安培; $跳过= 0&安培; $顶部= 50&安培; __ includeDeleted =真

失败

{ $ id:“1”, 消息:“ URI中指定的查询无效。无法在类型'Backend.DataObjects.Game'上找到名为'updatedAt'的属性。”, exceptionMessage:“无法在类型'AthelinkBackend.DataObjects.Game'上找到名为'updatedAt'的属性。”, exceptionType:“Microsoft.Data.OData.ODataException”, stackTrace:“在Microsoft.Data.OData.Query的Microsoft.Data.OData.Query.EndPathBinder.BindEndPath(EndPathToken endPathToken,BindingState状态)中的Microsoft.Data.OData.Query.EndPathBinder.GeneratePropertyAccessQueryForOpenType(EndPathToken endPathToken,SingleValueNode parentNode)。 Microsoft.Data.OData.Query.OrderByBinder.BindOrderBy(BindingState state,IEnumerable`1 orderByTokens)中的Microsoft.Data.OData.Query.OrderByBinder.ProcessSingleOrderBy(BindingState状态,OrderByClause thenBy,OrderByToken orderByToken)中的MetadataBinder.Bind(QueryToken标记) System.Web.Http.OData.Query.Validators上的System.Web.Http.OData.Query.OrderByQueryOption.get_OrderByClause()中的Microsoft.Data.OData.Query.ODataUriParser.ParseOrderByImplementation(String orderBy,IEdmType elementType,IEdmEntitySet entitySet) System.Web.Http.OData.Query.OrderByQueryOption.Validate中的.OrderByQueryValidator.Validate(OrderByQueryOption orderByOption,ODataValidationSettings validationSettings)(ODataValidationSettings在System.Web.Http的System.Web.Http.OData.Query.ODataQueryOptions.Validate(ODataValidationSettings validationSettings)的System.Web.Http.OData.Query.Validators.ODataQueryValidator.Validate(ODataQueryOptions选项,ODataValidationSettings validationSettings)中的validationSettings。 System.Web.Http.OData.EnableQueryAttribute.OnActionExecuted(HttpActionExecutedContext actionExecutedContext)上的System.Web.Http.OData.EnableQueryAttribute.ExecuteQuery(对象响应,HttpRequestMessage请求,HttpActionDescriptor actionDescriptor)中的OData.EnableQueryAttribute.ValidateQuery(HttpRequestMessage请求,ODataQueryOptions queryOptions) “ }

在Chrome中,但我在GET vars中使用UpdatedAt运行相同,但它正确完成。

我不知道如何解决此问题,或者客户端问题或服务器问题。

在客户端:

namespace GamesClient.Models
{
    public class Game : AppServiceHelpers.Models.EntityData
    {
        public string Name { get; set; }
        public string Type { get; set; }
    }
}

在服务器上:

namespace Backend.DataObjects
{
    public class Game : EntityData
    {
        public string Name { get; set; }
        public string Type { get; set; }

        public virtual Collection<Participant> Participants { get; set; }
    }
}

namespace Backend.Controllers
{
    [AllowAnonymous]
    public class GameController : TableController<Game>
    {
        protected override void Initialize(HttpControllerContext controllerContext)
        {
            base.Initialize(controllerContext);
            MobileServiceContext context = new MobileServiceContext();
            DomainManager = new EntityDomainManager<Game>(context, Request, Services);
        }

        // GET tables/Game
        public IQueryable<Game> GetAllGame()
        {
            return Query(); 
        }

        // GET tables/Game/48D68C86-6EA6-4C25-AA33-223FC9A27959
        public SingleResult<Game> GetGame(string id)
        {
            return Lookup(id);
        }

        // PATCH tables/Game/48D68C86-6EA6-4C25-AA33-223FC9A27959
        public Task<Game> PatchGame(string id, Delta<Game> patch)
        {
             return UpdateAsync(id, patch);
        }

        // POST tables/Game
        public async Task<IHttpActionResult> PostGame(Game item)
        {
            Game current = await InsertAsync(item);
            return CreatedAtRoute("Tables", new { id = current.Id }, current);
        }

        // DELETE tables/Game/48D68C86-6EA6-4C25-AA33-223FC9A27959
        public Task DeleteGame(string id)
        {
             return DeleteAsync(id);
        }

    }
}

更新#1

我已检查过数据库,看起来表格正在正确创建。我甚至可以从Xamarin客户端进行POST / INSERT,它可以正常工作。

Database tables and data in the Games table

我真的认为它是GET请求过滤器中的UpdatedAt和updatedAt大小写之间的问题。

(1)来自Xamarin客户端的GET(使用updatedAt):

$滤波器=(的 updatedAt %如20Ge%20datetimeoffset%271970-01-01T00:00:00.0000000%2B00:00%27)及$的OrderBy = updatedAt &安培; $跳过= 0&安培; $顶部= 50&安培; __ includeDeleted =真

导致上面的错误消息

(2)从Chrome获取GET(更改请求使用UpdatedAt):

$滤波器=(的 UpdatedAt %如20Ge%20datetimeoffset%271970-01-01T00:00:00.0000000%2B00:00%27)及$的OrderBy = UpdatedAt &安培; $跳过= 0&安培; $顶部= 50&安培; __ includeDeleted =真

导致正确的回复

[
{
$id: "1",
id: "46d3db2c-c8d4-4a15-8724-d7ce95611a63",
type: "football ",
name: "game1"
},
{
$id: "2",
id: "02d02477-2618-4eda-90ad-34e4117ed423",
type: "basketball ",
name: "game2"
}
]

在服务器端,我的游戏是Microsoft的一个孩子.WindowsAzure.Mobile.Service.EntityData

在客户端,Game对象是EntityData类的子对象,具有以下UpdatedAt属性定义

[Microsoft.WindowsAzure.MobileServices.UpdatedAt]
public DateTimeOffset UpdatedAt { get; set; }

另外,请告诉我哪些日志可以提供帮助,谢谢!

2 个答案:

答案 0 :(得分:1)

对我有用的解决方案是在您的移动客户端上设置以下属性。

var client = new MobileServiceClient(...);
client.SerializerSettings.CamelCasePropertyNames = false;

这可以防止在odata查询中将您的属性名称序列化为驼峰大小。

答案 1 :(得分:0)

看起来数据库表未正确设置。这可能有很多原因。其中一个比较常见的是你从TodoItem表开始,发布了(创建了TodoItems数据库表),然后更新了服务器后端以创建新表,它就失败了。这是因为创建数据库(初始模式创建)是为您完成的,但更新不是。您需要使用代码优先迁移来正确更新数据库(就像任何其他基于Entity Framework的服务一样)。可能还有其他事情发生 - 不幸的是,您提供的日志没有显示任何内容。

如果可以,请清除数据库,然后从空白数据库开始。

另外,请阅读本书 - http://aka.ms/zumobook