我正在使用 Azure 移动应用服务作为移动应用后端/服务器。
当应用服务身份验证处于"关闭"状态时,客户端可以将项插入到远程表中。 (我使用 portal.azure 打开和关闭应用服务身份验证)。
但是,启用应用服务身份验证似乎会阻止 PushAsync 在表控制器中调用关联的 Post 方法。我知道,因为我输入了代码,每当请求在表控制器中输入方法时,这些代码都会写入应用程序日志。
当应用服务身份验证关闭时,我可以看到 PostItem 中的跟踪打印代码写入应用日志,然后是 GetAll 跟踪打印代码。
当应用服务身份验证处于打开状态时,PostItem 方法中的跟踪打印代码未写入,这应该意味着未调用 PostItem。但是,GetAll 跟踪打印代码仍写入应用日志。
用户已通过身份验证,因为用户已使用 MobileServiceClient.LoginAsync 登录
有谁知道我如何调试和/或解决这个问题?
更新 1
这是表控制器
[Authorize]
public class ItemController : TableController<Item>
{
protected override void Initialize(HttpControllerContext controllerContext)
{
base.Initialize(controllerContext);
MobileServiceContext context = new MobileServiceContext();
DomainManager = new EntityDomainManager<Item>(context, Request);
}
// GET tables/Item
public async Task<IQueryable<Item>> GetAllItem()
//public IQueryable<Item> GetAllItem()
{
// Initialize variable
string userGUID = "";
// Retrieve credentials of requester
AzureActiveDirectoryCredentials userCreds = await User.GetAppServiceIdentityAsync<AzureActiveDirectoryCredentials>(Request);
System.Diagnostics.Trace.TraceInformation("Get All Item Controller");
// If usercreds is not null, retrieve requester's GUID
if (userCreds != null) userGUID = userCreds.ObjectId;
//Retrieve items that match user's aad id AND item that is not deleted
var query = Query().Where(item => !item.Deleted && item.RequesterId.Equals(userGUID, System.StringComparison.OrdinalIgnoreCase));
// return query;
return Query();
}
// GET tables/Item/48D68C86-6EA6-4C25-AA33-223FC9A27959
public SingleResult<Item> GetItem(string id)
{
return Lookup(id);
}
// PATCH tables/Item/48D68C86-6EA6-4C25-AA33-223FC9A27959
public Task<Item> PatchItem(string id, Delta<Item> patch)
{
return UpdateAsync(id, patch);
}
// POST tables/Item
public async Task<IHttpActionResult> PostItem(Item item)
{
System.Diagnostics.Trace.TraceInformation("Post Item Controller");
AzureActiveDirectoryCredentials userCreds = await User.GetAppServiceIdentityAsync<AzureActiveDirectoryCredentials>(Request);
// Set requester id for item
item.RequesterId = userCreds.ObjectId;
// Save item to db
Item current = await InsertAsync(item);
return CreatedAtRoute("Tables", new { id = current.Id }, current);
}
// DELETE tables/Item/48D68C86-6EA6-4C25-AA33-223FC9A27959
public Task DeleteItem(string id)
{
return DeleteAsync(id);
}
}
更新 2
在PostItem中,我将检索请求者凭据的代码放在try-catch中。
// POST tables/Item
public async Task<IHttpActionResult> PostItem(Item item)
{
// Initialize variable
string userId = "";
System.Diagnostics.Trace.TraceInformation("Post Item Controller");
AzureActiveDirectoryCredentials userCreds = null;
// Retrieve credentials of requester
try
{
userCreds = await User.GetAppServiceIdentityAsync<AzureActiveDirectoryCredentials>(Request);
}
catch(Exception e)
{
System.Diagnostics.Trace.TraceInformation(e.Message);
}
if (userCreds != null) System.Diagnostics.Trace.TraceInformation("user creds is null");
else System.Diagnostics.Trace.TraceInformation("user creds is not null");
// If usercreds is not null, retrieve requester's id
if (userCreds != null) userId = userCreds.ObjectId;
// Set requester id for item
item.RequesterId = userId;
// Save item to db
Item current = await InsertAsync(item);
return CreatedAtRoute("Tables", new { id = current.Id }, current);
}
我收到的错误消息是:"IPrincipal的声明必须包含'iss'声明。
我有一个理论 - 尝试使用"https"而不是"http"创建MobileServiceClient
。身份验证要求"iss"和"aud"与当前请求的URL完全匹配,我怀疑您的请求实际上没有正确进行身份验证。
但这并不能解释如果你在控制器上[Authorize]
了所有测试,请求是如何通过的——这一直存在吗?如果请求未经验证,我希望您来自客户端的呼叫会得到 401。