Publicado por Levy Carneiro Jr. em 25 de March de 2009

Técnicas de Ruby Reveladas: Autoload

monster-with-torch.jpgTem um monte de coisas em Ruby que, ou eu nunca percebi, percebi mas esqueci, ou não entendi a utilidade. Adicione a isso todos os truques e técnicas legais de Ruby que tenho visto ultimamente no código de várias pessoas no Github e... nós precisamos de uma nova série aqui: Técnicas de Ruby Reveladas!

Nota: não estou prometendo que você já não sabe tudo que eu "revelar". Vários de vocês são muito melhores do que eu e conhecem todos os cantos obscuros do Ruby. Eu só vou jogar um facho de luz em coisas que eu não vejo sendo usadas muito, e que acho legais.

Autoload - Carregue coisas somente quando é necessário

Eu estava olhando o código do Thin e percebi que ao invés de usar require, Marc-Andre Cournoyer estava usando um método chamado autoload para carregar os componentes do thin. Sendo mais específico:

autoload :Command,            'thin/command'
autoload :Connection,         'thin/connection'
autoload  :D aemonizable,       'thin/daemonizing'
autoload :Logging,            'thin/logging'

Isto me deixou intrigado, então fui ao Google e me deparei com um pequeno demo de autoload feito pelo Mike Subelsky. O autoload funciona de forma similar ao require, mas ele só carrega o arquivo especificado quando uma constante que você escolher é acessada/usada pela primeira vez. Esta constante normalmente seria o nome da classe fornecida pelo outro arquivo-fonte (mas isso não é obrigatório, como o Mike demonstra).

Digamos que você tenha um arquivo chamado mylibrary.rb contendo o seguinte código:

puts "Fui carregado!"

class MyLibrary
end

Agora, de dentro do irb, vamos usar require para carregar a "biblioteca":

irb(main):001:0> require 'mylibrary'
Fui carregado!
=> true

Como o require já roda direto, o método puts é executado imediatamente. Então vamos reiniciar irb e ver o que acontece se usarmos o autoload dessa vez:

irb(main):001:0> autoload :MyLibrary, 'mylibrary'
=> nil
irb(main):002:0> MyLibrary.new
Fui carregado!
=> #<MyLibrary:0x0b1jef>

O método puts não é executado até tentarmos usar MyLibrary. O autoload evitou o carregamento de mylibrary.rb até nós realmente precisarmos dele.

Tomarás cuidado com vossas threads...

Uma pesquisa mais detalhada no Google me levou a discussões interessantes sobre o autoload. Em dezembro de 2008, um grupo de astros do Ruby tiveram uma discussão sobre alguns problemas do autoload relativo a threads. Acontece que, mesmo que muitos projetos tenham adotado o autoload recentemente, existem algumas preocupações sobre o quão thread-safe é o autoload. A solução proposta é ter um mutex entre todos os autoloads, mas eu ainda não identifiquei se isso já foi tentado com sucesso por alguém.

Houve também uma discussão similar no início de 2008, iniciada pelo Yehuda Katz (famoso pelo Merb) que eu recomendo que você leia se threading vai ser importante para você. Ele parece indicar que grandes problemas só aparecem em situações de concorrência extrema, mas o problema está lá mesmo assim. Parecem haver problemas similares com o require também, então eu vou tomar a abordagem "cruzar a ponte quando eu chegar a ela"... ;)

2 Comentários para “Técnicas de Ruby Reveladas: Autoload”

  1. #1
    Leandro Silva Disse:

    Opa! Legal, hein? Gostei da "série" proposta... :)

  2. #2
    Alan Rafael Disse:

    A "mandrakaria" do Ruby enfim serão revelados.

Deixe um Comentário