9

Estaba intentando implementar el jQgrid usando MvcjQgrid y obtuve esta excepción.El método 'OrderBy' se debe invocar antes del método 'Omitir' Excepción

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'. 

Aunque OrdeyBy se utiliza antes Método de salto ¿por qué está generando la excepción? ¿Cómo puede ser resuelto?

me encontré con la excepción en el controlador:

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 Método y CountJobDescription Método

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); 
     } 

Y Finalmente FilterJobDescription y 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

Pero no ordena siempre, solo si 'sortColumn ==" JobDescriptionID "', ¿verdad? – Slauma

+0

¿Importa? Por cierto, tengo varias otras declaraciones de pedido. – nebula

Respuesta

14

La excepción significa que siempre necesita una entrada ordenada si aplica Skip, también en el caso de que el usuario no haga clic en una columna para ordenar. Me imagino que no se especifica ninguna columna de clasificación cuando abre la vista de cuadrícula por primera vez antes de que el usuario pueda hacer clic en el encabezado de una columna. Para atrapar a este caso yo sugeriría definir algunos orden predeterminado que desea cuando se da ningún otro criterio de clasificación, por ejemplo:

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); 
} 

Editar

acerca de sus problemas de seguimiento de acuerdo con su comentario : No puede usar ToString() en una consulta LINQ to Entities. Y el siguiente problema sería que no puede crear una matriz string en una consulta. Yo sugeriría para cargar los datos de la base de datos con sus tipos nativos y luego convertir después para cuerdas (y a la matriz de cadenas) en la memoria:

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

Esa excepción ahora se ha ido. Pero se encuentra una nueva excepción en el controlador ya que 'LINQ to Entities no reconoce el método 'System.String ToString()', y este método no se puede traducir a una expresión store.Now cómo convertir' JobDescriptionID' y otros atributos en una cuerda, entonces? – nebula

+0

@aneal: ver mi edición. (En realidad no tiene nada que ver con su pregunta original.) – Slauma

3

que tenía el mismo tipo de problema después de su clasificación utilizando un código de Adam Anderson que aceptó una cadena de ordenación genérica en OrderBy.

Después de conseguir este excpetion, hice un montón de investigación y encontró esa solución muy inteligente:

var query = SelectOrders(companyNo, sortExpression); 

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

Espero que ayude!

SP

+0

Tengo esa implementación genérica en mi solución, intenté su solución pero no funcionó, por cierto, qué cambio actual haría –

+0

@vishal: aclare su último comentario ... – spilote

Cuestiones relacionadas