Pergunta

Estou executando um banco de dados MySQL localmente para o desenvolvimento, mas a implantação de Heroku que usa Postgres. Heroku lida com quase tudo, mas meus maiúsculas e minúsculas declarações como se tornar sensível a maiúsculas. Eu poderia usar declarações iLike, mas meu banco de dados MySQL local não pode lidar com isso.

O que é a melhor maneira de escrever uma consulta insensível caso, que é compatível com o MySQL e PostgreSQL? Ou eu preciso para escrever declarações como e iLike separadas, dependendo do DB meu aplicativo está falando?

Foi útil?

Solução

select * from foo where upper(bar) = upper(?);

Se você definir o parâmetro para maiúsculas no chamador, você pode evitar a segunda chamada de função.

Outras dicas

A moral desta história é: não use uma pilha de software diferente para o desenvolvimento e produção. Nunca.

Você só vai acabar com os erros que você não pode reproduzir em dev; seu teste será inútil. Só não fazê-lo.

Usando um motor de banco de dados diferente é fora de questão - haverá muito mais casos em que se comporta de forma diferente do que apenas SIMILAR (também, você tem verificado os agrupamentos em uso pelos bancos de dados Eles são idênticos em todos os casos Se não? , você pode esquecer ORDER BY em colunas varchar trabalhando o mesmo)

Use Arel:

Author.where(Author.arel_table[:name].matches("%foo%"))

matches usará o operador ILIKE para Postgres, e LIKE para tudo o resto.

Em postgres, você pode fazer isso:

SELECT whatever FROM mytable WHERE something ILIKE 'match this';

Eu não tenho certeza se existe um equivalente para o MySQL, mas você sempre pode fazer isso, que é um pouco feio, mas deve funcionar tanto em MySQL e PostgreSQL:

SELECT whatever FROM mytable WHERE UPPER(something) = UPPER('match this');

Existem várias respostas, nenhum dos quais é muito satisfatório.

  • BAIXA (bar) = LOWER trabalho em MySQL e PostgreSQL, mas é provável que executar terrivelmente no MySQL (?): MySQL não vai usar seus índices por causa da função INFERIOR. Em Postgres você pode adicionar um índice funcional (em BAIXA (bar) ), mas MySQL não suporta isso.
  • MySQL vai (a menos que você tenha definido uma agrupamento ) fazer a correspondência de maiúsculas e minúsculas automaticamente, e usar seus índices. ( bar =? ).
  • A partir do seu código fora do banco de dados, manter bar e bar_lower campos, onde bar_lower contém o resultado de menor (bar) . (Isto pode ser possível utilizando gatilhos de banco de dados, também). (Veja a discussão desta solução no Drupal ). Esta é desajeitado, mas que, pelo menos, executar da mesma maneira em praticamente todos os banco de dados.

REGEXP é maiúsculas e minúsculas (a não ser utilizado com binário), e pode ser usado, como assim ...

    SELECT id FROM person WHERE name REGEXP 'john';

... para coincidir com 'John', 'JOHN', 'John', etc.

Se você estiver usando PostgreSQL 8.4 você pode usar o Citext módulo para criar casos de campos de texto insensíveis.

Você também pode considerar verificar o searchlogic plugin, que faz o COMO / ILIKE interruptor para você.

Você também pode usar ~ * em postgres se você quer combinar uma substring dentro de um bloco. ~ Corresponde subsequência maiúsculas e minúsculas, ~ * caso subsequência insensível. É uma operação lenta, mas eu poderia encontrá-lo útil para pesquisas.

Select * from table where column ~* 'UnEvEn TeXt';
Select * from table where column ~ 'Uneven text';

Ambos iria bater em "Algum texto desigual aqui" Apenas o primeiro teria atingido em "algum texto DESIGUAL aqui"

A conversão para superior é melhor, pois abrange sintaxe compatível para os 3 Rails mais usados ??backends de banco de dados. PostgreSQL, MySQL e SQLite todos apoiar esta sintaxe. Tem a (menor) desvantagem que você tem para maiúsculas a sua cadeia de pesquisa na aplicação ou na cadeia condições, tornando-o um pouco mais feio, mas acho que a compatibilidade que você ganho torna proveitoso.

Ambos MySQL e SQLite3 ter um operador LIKE maiúsculas e minúsculas. Apenas PostgreSQL tem um operador LIKE caso-sensível e específica de um-PostgreSQL (por manual) operador ILIKE para pesquisas de maiúsculas e minúsculas. Você pode especificar ILIKE insead de LIKE em suas condições sobre a aplicação Rails, mas esteja ciente de que a aplicação deixará de trabalho sob MySQL ou SQLite.

Uma terceira opção poderia ser a de verificar qual o motor de banco de dados que você está usando e modificar a seqüência de pesquisa em conformidade. Isso pode ser melhor feito por invadir / monkeypatching adaptadores de conexão de ActiveRecord e ter o adaptador PostgreSQL modificar a string de consulta para substituir "Like" para "ILIKE" execução da consulta antes. Esta solução é, contudo, o mais complicado e à luz das maneiras mais fáceis como maiúscula ambos os termos, eu acho que isso não é porque achamos o esforço (embora você começar a abundância de pontos de brownie para fazê-lo desta forma).

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top