9

我試圖用MvcjQgrid實施jQgrid和我得到這個例外。方法「排序依據」必須在方法之前被稱爲「跳過」異常

System.NotSupportedException was unhandled by user code 
    Message=The method 'Skip' is only supported for sorted input in LINQ to Entities. The method 'OrderBy' must be called before the method 'Skip'. 

雖然之前使用OrdeyBy Skip方法,爲什麼它會產生異常?它如何解決?

我遇到控制器例外:

public ActionResult GridDataBasic(GridSettings gridSettings) 
     {   
      var jobdescription = sm.GetJobDescription(gridSettings); 
      var totalJobDescription = sm.CountJobDescription(gridSettings); 

      var jsonData = new 
      { 
       total = totalJobDescription/gridSettings.PageSize + 1, 
       page = gridSettings.PageIndex, 
       records = totalJobDescription, 
       rows = (
        from j in jobdescription 
        select new 
        { 
         id = j.JobDescriptionID, 
         cell = new[] 
        { 
         j.JobDescriptionID.ToString(), 
         j.JobTitle, 
         j.JobType.JobTypeName, 
         j.JobPriority.JobPriorityName, 
         j.JobType.Rate.ToString(), 
         j.CreationDate.ToShortDateString(), 
         j.JobDeadline.ToShortDateString(), 

        } 
        }).ToArray() 
      }; 
      return Json(jsonData, JsonRequestBehavior.AllowGet); 
     } 

GetJobDescription方法CountJobDescription方法

public int CountJobDescription(GridSettings gridSettings) 
     { 
      var jobdescription = _dataContext.JobDescriptions.AsQueryable(); 

      if (gridSettings.IsSearch) 
      { 
       jobdescription = gridSettings.Where.rules.Aggregate(jobdescription, FilterJobDescription); 
      } 
      return jobdescription.Count(); 
     } 

     public IQueryable<JobDescription> GetJobDescription(GridSettings gridSettings) 
     { 
      var jobdescription = orderJobDescription(_dataContext.JobDescriptions.AsQueryable(), gridSettings.SortColumn, gridSettings.SortOrder); 

      if (gridSettings.IsSearch) 
      { 
       jobdescription = gridSettings.Where.rules.Aggregate(jobdescription, FilterJobDescription); 
      } 

      return jobdescription.Skip((gridSettings.PageIndex - 1) * gridSettings.PageSize).Take(gridSettings.PageSize); 
     } 

最後FilterJobDescription和OrderJobDescription

private static IQueryable<JobDescription> FilterJobDescription(IQueryable<JobDescription> jobdescriptions, Rule rule) 
     { 
      if (rule.field == "JobDescriptionID") 
      { 
       int result; 
       if (!int.TryParse(rule.data, out result)) 
        return jobdescriptions; 
       return jobdescriptions.Where(j => j.JobDescriptionID == Convert.ToInt32(rule.data)); 

      } 

// Similar Statements 

      return jobdescriptions; 
     } 



private IQueryable<JobDescription> orderJobDescription(IQueryable<JobDescription> jobdescriptions, string sortColumn, string sortOrder) 
     { 
      if (sortColumn == "JobDescriptionID") 
       return (sortOrder == "desc") ? jobdescriptions.OrderByDescending(j => j.JobDescriptionID) : jobdescriptions.OrderBy(j => j.JobDescriptionID); 

      return jobdescriptions; 
     } 
+0

但是你不總是訂購,只有'sortColumn ==「JobDescriptionID」',你呢? – Slauma 2012-07-21 15:51:13

+0

重要嗎?順便說一下,我還有其他幾個訂單陳述。 – nebula 2012-07-21 15:57:50

回答

14

例外意味着,如果您應用Skip,並且在用戶未單擊列進行排序的情況下,則您總是需要需要排序的輸入。我可以想象,在用戶甚至可以單擊列標題之前,當您首次打開網格視圖時,沒有指定排序列。根據您的評論

switch (sortColumn) 
{ 
    case "JobDescriptionID": 
     return (sortOrder == "desc") 
      ? jobdescriptions.OrderByDescending(j => j.JobDescriptionID) 
      : jobdescriptions.OrderBy(j => j.JobDescriptionID); 

    case "JobDescriptionTitle": 
     return (sortOrder == "desc") 
      ? jobdescriptions.OrderByDescending(j => j.JobDescriptionTitle) 
      : jobdescriptions.OrderBy(j => j.JobDescriptionTitle); 

    // etc. 

    default: 
     return jobdescriptions.OrderBy(j => j.JobDescriptionID); 
} 

編輯

關於你的後續問題:爲了趕上這種情況下,我會建議定義一些默認的排序,你希望在沒有給出其他排序標準,例如:您不能在LINQ to Entities查詢中使用ToString()。接下來的問題是你不能在查詢中創建一個string數組。我建議他們的本地類型加載從數據庫中的數據,然後再把轉換爲字符串(和字符串數組)內存:

rows = (from j in jobdescription 
     select new 
     { 
      JobDescriptionID = j.JobDescriptionID, 
      JobTitle = j.JobTitle, 
      JobTypeName = j.JobType.JobTypeName, 
      JobPriorityName = j.JobPriority.JobPriorityName, 
      Rate = j.JobType.Rate, 
      CreationDate = j.CreationDate, 
      JobDeadline = j.JobDeadline 
     }) 
     .AsEnumerable() // DB query runs here, the rest is in memory 
     .Select(a => new 
     { 
      id = a.JobDescriptionID, 
      cell = new[] 
      { 
       a.JobDescriptionID.ToString(), 
       a.JobTitle, 
       a.JobTypeName, 
       a.JobPriorityName, 
       a.Rate.ToString(), 
       a.CreationDate.ToShortDateString(), 
       a.JobDeadline.ToShortDateString() 
      } 
     }) 
     .ToArray() 
+0

這個異常現在已經消失。但是在控制器中遇到新的異常,因爲「LINQ to Entities不能識別方法'System.String ToString()'方法,並且此方法不能轉換爲存儲表達式。」現在如何轉換'JobDescriptionID'和其他屬性成字符串呢? – nebula 2012-07-21 16:35:54

+0

@aneal:看我的編輯。 (它實際上與你的原始問題無關。) – Slauma 2012-07-21 17:13:00

3

我有同樣類型的問題使用一些代碼排序後亞當·安德森接受了在排序依據通用的排序字符串。

得到這個錯誤時拋出後,我做了很多的研究,發現非常巧妙的解決辦法:

var query = SelectOrders(companyNo, sortExpression); 

return Queryable.Skip(query, iStartRow).Take(iPageSize).ToList(); 

希望幫助!

SP

+0

我在我的解決方案中使用了這個通用實現,嘗試了你的修復,但它沒有工作,順便說一下,當前的變化會怎麼做 – 2016-03-08 10:16:01

+0

@vishal:請澄清你最後的評論... – spilote 2016-04-13 18:11:25