1

在我的VS LIGHTSWITCH 2013門戶應用程序中,我允許用戶創建鏈接到其他內部應用程序的切片。當新瓷磚創建名稱爲「TileTitle +」的角色時,將創建用戶「」。這樣我就可以根據用戶角色顯示和隱藏切片。然而,當試圖過濾查詢過濾器方法中的瓦片實體時,我得到一些關於不能使用IsInRole方法的錯誤。表達式樹引發錯誤

一些挖後,我決定給表達式樹一試,這就是我想出了:

partial void TileLinks_Filter(ref Expression<Func<TileLink, bool>> filter) 
{ 
    ParameterExpression p = Expression.Parameter(typeof(TileLink), "e"); 
    MemberExpression ti = Expression.Property(p, "Title"); 
    MethodInfo m2 = typeof(string).GetMethod("Concat", new[] { typeof(string), typeof(string) }); 


    Type t = this.Application.User.GetType(); 
    MethodInfo m = t.GetMethod("IsInRole"); 

    Expression filterExpression = Expression.IsTrue(Expression.Call(Expression.Call(m2, ti, Expression.Constant(" User")), m)); 

    filter = Expression.Lambda<Func<TileLink, bool>>(filterExpression, p); 

    // e => this.Application.User.IsInRole(e.Title + " User"); 
    // this is what I would like to do 
} 

然而,這並不工作,我離開了這個非常奇怪的錯誤消息。

Method 'Boolean IsInRole(System.String)' declared on type 'System.Security.Claims.ClaimsPrincipal' cannot be called with instance of type 'System.String' 

請幫我按照動態生成的角色過濾我的數據!

回答

0

你已經在Expression.Call的外部調用中反轉了你的論點。如果你打破了你的代碼了一下,你最終與此:

var titlePlusUser = Expression.Call(m2, ti, Expression.Constant(" User")); 
var isInRole = Expression.Call(titlePlusUser, m); // <<-- !!! 
Expression filterExpression = Expression.IsTrue(isInRole); 

這指示它使用e.Title + "User"作爲對象實例調用IsInRole上。

相反,您需要生成另一個表達式,該表達式知道如何獲得this.Application.User,並將該表達式作爲第一個參數傳遞。

var isInRole = Expression.Call(applicationUser, m, titlePlusUser);