我有一些实体拥有的数据只能供某些用户访问。
public class Foo
{
public virtual Bar { get; set; }
...
}
public class Bar
{
public string Secret { get; set; }
...
}
例如,Bar.Secret
只能由UserA
访问,而不能由UserB
访问。
我可以这样:
public class BarsController : ODataController
{
[EnableQuery]
public IHttpActionResult Get()
{
if (User.Identity.Name != "UserA")
return Unauthorized();
return _db.Bars();
}
}
除此之外,这是一个糟糕的实施。它不包括此控制器:
public class FoosController : ODataController
{
[EnableQuery]
public IHttpActionResult Get()
{
return _db.Foos();
}
}
可以使用/odata/Foos?$expand=Bars
调用,然后我可以查看Bar.Secret
。我不能只在$expand
上停用Foo
,因为该查询对UserA
完全合法,也是必需的。
是否有办法让OData针对涉及所请求实体的某个谓词验证查询。
像
这样的东西public class SecureEnableQueryAttribute : EnableQueryAttribute
{
public bool ValidateResult(IEnumerable<T> entities)
{
return entities.All(x => x.Secret == UserA.Secret);
}
}
答案 0 :(得分:1)
您可以在执行查询之前验证查询选项,如果用户无权检索请求的数据,则会失败。为此,请从EnableQueryAttribute
派生并覆盖ValidateQuery
。
public class SecureEnableQueryAttribute : EnableQueryAttribute
{
public virtual void ValidateQuery(HttpRequestMessage request, ODataQueryOptions queryOptions)
{
base.ValidateQuery(request, queryOptions);
// Insert custom logic, possibly looking at queryOptions.SelectExpand
// or queryOptions.RawValues.
}
}