Mysql
 sql >> Base de Dados >  >> RDS >> Mysql

A consulta não retorna resultados somente quando ORDER BY adicionado


Isso parece ser um bug no MySQL, sobre o qual eu preenchi um relatório . Eu reduzi para o seguinte caso de teste, que se esperaria retornar um único registro (mas não retorna):
CREATE TABLE t (x INT NULL);  -- table with nullable column
INSERT INTO  t VALUES (0);    -- but non null data

SELECT   a.x                  -- select our nullable column
FROM     t a, (SELECT NULL) b -- joining it with anything at all

WHERE    EXISTS (             -- but filter on a subquery
           SELECT *
           FROM   (SELECT NULL) c -- doesn't really matter what
           HAVING a.x IS NOT NULL -- provided there is some correlated condition
                                  -- on our nullable column in the HAVING clause
         )

ORDER BY RAND()               -- then perform a filesort on the outer query

Veja em sqlfiddle .

No seu caso, você pode fazer várias coisas para corrigir isso:

  1. Evite a subconsulta correlacionada reescrevendo como uma junção:
    SELECT   *
    FROM     people AS p LEFT JOIN (people_stages AS s NATURAL JOIN (
               SELECT   person_id, MAX(created) created
               FROM     people_stages
               GROUP BY person_id
             ) t) ON s.person_id = p.id
    ORDER BY p.last_name
    

  2. Se você deseja manter a subconsulta correlacionada (que geralmente pode gerar um desempenho ruim, mas geralmente é mais fácil de entender), use WHERE em vez de HAVING :
    SELECT   * 
    FROM     people AS p LEFT JOIN people_stages AS s ON s.person_id = p.id
    WHERE    s.created = (
               SELECT MAX(created)
               FROM   people_stages
               WHERE  person_id = s.person_id
             )
    ORDER BY p.last_name
    

  3. Se você não conseguir alterar a consulta, verá que fazer o people_stages.person_id coluna não anulável contornará o problema:
    ALTER TABLE people_stages MODIFY person_id BIGINT UNSIGNED NOT NULL
    

    Parece que ter um índice nessa coluna (o que seria necessário para efetuar uma restrição de chave estrangeira) também pode ajudar:
    ALTER TABLE people_stages ADD FOREIGN KEY (person_id) REFERENCES people (id)
    

  4. Alternativamente, pode-se remover people_stages.person_id da lista de seleção, ou ajuste a estratégia de modelo de dados/indexação/consulta para evitar uma classificação de arquivos (pode não ser prático neste caso, mas eu os mencionei aqui para completar).