2012-04-04 21 views
9

Tengo el siguiente SP que estoy usando para paginar una lista de artículos de noticias. Como puede adivinar, @count es el número de filas a devolver, @start es el índice para seleccionar filas de (ordenadas por consulta interna), @orderby indica la columna por ordenar, y @orderdir indica si ordenar una dirección o la otro. Mi consulta original fue here, antes de agregar el parámetro @orderdir.DESC y ASC como un parámetro en el procedimiento almacenado

ALTER PROCEDURE [mytable].[news_editor_paginate] 
    @count int, 
    @start int, 
    @orderby int, 
    @orderdir int 
AS 
BEGIN 
    SET NOCOUNT ON; 
    SELECT TOP (@count) * FROM 
    ( 
     SELECT ne.*,n.publishstate, 
      (CASE WHEN @orderdir = 1 THEN 
       ROW_NUMBER() OVER (
        ORDER BY      
         CASE WHEN @orderby = 0 THEN ne.[time] END DESC, 
         CASE WHEN @orderby = 1 THEN ne.lastedit END DESC,  
         CASE WHEN @orderby = 2 THEN ne.title END ASC 
        ) 
      WHEN @orderdir = 2 THEN 
       ROW_NUMBER() OVER (
        ORDER BY      
         CASE WHEN @orderby = 0 THEN ne.[time] END ASC,  
         CASE WHEN @orderby = 1 THEN ne.lastedit END ASC, 
         CASE WHEN @orderby = 2 THEN ne.title END DESC 
        ) 
       END 
      ) AS num 
      FROM news_edits AS ne 
      LEFT OUTER JOIN news AS n 
      ON n.editid = ne.id 
     ) 
    AS a 
    WHERE num > @start 
END 

Ahora bien, nada en realidad va mal, pero el parámetro @orderby no funciona. Si proporciono 1 como el parámetro @orderdir, me dará exactamente los mismos resultados que si proporciono 2 como ese parámetro.

Respuesta

15

El número de fila no se evalúa en cada fila, sin embargo, las declaraciones de casos son para que se quede con el Rownum sin importar el caso.

Tal vez puedas probar:

  ROW_NUMBER() OVER (
       ORDER BY      
        CASE WHEN @orderby = 0 AND @orderdir = 1 THEN ne.[time] END DESC,  
        CASE WHEN @orderby = 0 AND @orderdir = 2 THEN ne.[time] END ASC,  
        CASE WHEN @orderby = 1 AND @orderdir = 1 THEN ne.lastedit END DESC, 
        CASE WHEN @orderby = 1 AND @orderdir = 2 THEN ne.lastedit END ASC, 
        CASE WHEN @orderby = 2 AND @orderdir = 1 THEN ne.title END ASC 
        CASE WHEN @orderby = 2 AND @orderdir = 2 THEN ne.title END DESC 
       ) 
+1

Sí que trabajaba exactamente lo que quería, parece tan obvio ahora que lo has anotado Gracias, tengo que esperar para marcar esto como la respuesta. –

+0

Sin sudar. Arañé mi cabeza sobre esto varias veces antes cuando salió row_number. – Gats

1

Esto funciona muy bien para mí - (en el que, para por, dirección, Offset ha podido recuperar)

 -- parameters 

     @orderColumn int , 
     @orderDir varchar(20), 
     @start int , 
     @limit int 


     select * from items 
     WHERE  (items.status = 1) 
     order by 

     CASE WHEN @orderColumn = 0 AND @orderdir = 'desc' THEN items.[category] END DESC,  
     CASE WHEN @orderColumn = 0 AND @orderdir = 'asc' THEN items.[category] END ASC,  
     CASE WHEN @orderColumn = 1 AND @orderdir = 'desc' THEN items.[category] END DESC, 
     CASE WHEN @orderColumn = 1 AND @orderdir = 'asc' THEN items.[category] END ASC, 
     CASE WHEN @orderColumn = 2 AND @orderdir = 'desc' THEN items.[category] END DESC, 
     CASE WHEN @orderColumn = 2 AND @orderdir = 'asc' THEN items.[category] END ASC 

     OFFSET @start ROWS FETCH NEXT @limit ROWS ONLY 
Cuestiones relacionadas