Sei que faz muito tempo que essa pergunta foi feita pela primeira vez, mas tenho uma resposta adicional que gostaria de compartilhar.
Tenho vários aplicativos Ruby que foram desenvolvidos por outro programador ao longo de vários anos e eles reutilizam as mesmas classes em diferentes aplicativos, embora possam acessar o mesmo banco de dados. Como isso viola a regra DRY, decidi criar uma biblioteca de classes para ser compartilhada por todos os aplicativos Ruby. Eu poderia ter colocado na biblioteca Ruby principal, mas isso ocultaria o código personalizado na base de código comum, o que eu não queria fazer.
Tive um problema em que havia um conflito de nome entre um nome já definido "profile.rb" e uma classe que estava usando. Esse conflito não foi um problema até que tentei criar a biblioteca de código comum. Normalmente, Ruby procura primeiro os locais do aplicativo e depois vai para os locais $ LOAD_PATH.
O application_controller.rb não conseguiu encontrar a classe que criei e gerou um erro na definição original porque não é uma classe. Como removi a definição de classe da seção app / models do aplicativo, Ruby não conseguiu encontrá-la e foi procurá-la nos caminhos de Ruby.
Portanto, modifiquei a variável $ LOAD_PATH para incluir um caminho para o diretório da biblioteca que estava usando. Isso pode ser feito no arquivo environment.rb no momento da inicialização.
Mesmo com o novo diretório adicionado ao caminho de pesquisa, Ruby estava gerando um erro porque preferencialmente pegava o arquivo definido pelo sistema primeiro. O caminho de pesquisa na variável $ LOAD_PATH pesquisa preferencialmente os caminhos Ruby primeiro.
Portanto, eu precisava alterar a ordem de pesquisa para que Ruby encontrasse a classe em minha biblioteca comum antes de pesquisar as bibliotecas integradas.
Este código fez isso no arquivo environment.rb:
Rails::Initializer.run do |config|
* * * * *
path = []
path.concat($LOAD_PATH)
$LOAD_PATH.clear
$LOAD_PATH << 'C:\web\common\lib'
$LOAD_PATH << 'C:\web\common'
$LOAD_PATH.concat(path)
* * * * *
end
Não acho que você possa usar qualquer uma das construções de codificação avançadas fornecidas antes neste nível, mas funciona muito bem se você quiser configurar algo no momento da inicialização em seu aplicativo. Você deve manter a ordem original da variável $ LOAD_PATH original quando ela for adicionada de volta à nova variável, caso contrário, algumas das classes principais do Ruby serão perdidas.
No arquivo application_controller.rb, eu simplesmente uso um
require 'profile'
require 'etc' #etc
e isso carrega os arquivos da biblioteca personalizada para todo o aplicativo, ou seja, não preciso usar os comandos require em todos os controladores.
Para mim, essa era a solução que eu procurava e pensei em adicioná-la a essa resposta para passar as informações adiante.
File.expand_path(File.dirname(__FILE__)).tap {|pwd| $LOAD_PATH.unshift(pwd) unless $LOAD_PATH.include?(pwd)}