拦截并覆盖linq的where子句
Intercept and override where clause of linq
我处于无法向方法添加新参数的情况,也无法更改 DataQuery 的逻辑 - 所以我只能更改具有与此类似构造的方法的内容,以及T.
IEnumerable<T> Get<T>(DataQuery<T> query) {
var collection = repo;
return query.Apply(repo).ToList();
}
我的问题是我想添加对检索分配给我的团队、我的公司或只有我的 Ts 的支持,但我无法从调用点访问 "me" 的任何上下文 - 他们在方法中的 UserContext 上可用。
DataQuery<T>.Apply()
允许我查询 Ts 属性,如 T.caseId <= 4
并将 return 包含案例 1-4 的列表。翻译成 source.Where(t => t.caseId <= 4)
我的想法是将以下字段添加到T
bool IsMineQuery
bool IsMyTeamQuery
bool IsMyCompanyQuery
然后拦截对 .Where(t => t.IsMineQuery == true)
或 .Where(t => t.IsMyTeamQuery == true)
的调用并将它们重写为 .Where(t => t.UserId == UserContext.UserId)
或 .Where(t => UserContext.TeamIds.Contains(t.TeamId))
但我不知道如何拦截调用。
我该如何实现?
于是折腾了一晚上终于有了突破
我必须制作自定义查询提供程序 - 我使用了本教程:https://msdn.microsoft.com/en-us/library/bb546158.aspx
那么我的控制器的形式是
IEnumerable<T> Get<T>(DataQuery<T> query) {
var collection = new MyQueryable(repo, UserContext);
return query.Apply(repo).ToList();
}
然后我更改了教程的 "InnerMostWhereFinder" 以确定我的查询是否已获得 IsMineQuery 或 IsMyTeamQuery 并将其替换为 UserContext.TeamIds.Contain(x => x.Team.Id)
很有魅力,但不是一个直接的解决方案。
我处于无法向方法添加新参数的情况,也无法更改 DataQuery 的逻辑 - 所以我只能更改具有与此类似构造的方法的内容,以及T.
IEnumerable<T> Get<T>(DataQuery<T> query) {
var collection = repo;
return query.Apply(repo).ToList();
}
我的问题是我想添加对检索分配给我的团队、我的公司或只有我的 Ts 的支持,但我无法从调用点访问 "me" 的任何上下文 - 他们在方法中的 UserContext 上可用。
DataQuery<T>.Apply()
允许我查询 Ts 属性,如 T.caseId <= 4
并将 return 包含案例 1-4 的列表。翻译成 source.Where(t => t.caseId <= 4)
我的想法是将以下字段添加到T
bool IsMineQuery
bool IsMyTeamQuery
bool IsMyCompanyQuery
然后拦截对 .Where(t => t.IsMineQuery == true)
或 .Where(t => t.IsMyTeamQuery == true)
的调用并将它们重写为 .Where(t => t.UserId == UserContext.UserId)
或 .Where(t => UserContext.TeamIds.Contains(t.TeamId))
但我不知道如何拦截调用。
我该如何实现?
于是折腾了一晚上终于有了突破
我必须制作自定义查询提供程序 - 我使用了本教程:https://msdn.microsoft.com/en-us/library/bb546158.aspx
那么我的控制器的形式是
IEnumerable<T> Get<T>(DataQuery<T> query) {
var collection = new MyQueryable(repo, UserContext);
return query.Apply(repo).ToList();
}
然后我更改了教程的 "InnerMostWhereFinder" 以确定我的查询是否已获得 IsMineQuery 或 IsMyTeamQuery 并将其替换为 UserContext.TeamIds.Contain(x => x.Team.Id) 很有魅力,但不是一个直接的解决方案。