Object#with_options
Posted on January 24, 2007
Fonte :the { buckblogs :here }, por Jamis
Em Named, explicit routes eu mencionei Object#with_options de passagem, somente para descobrir depois que este método super útil não consta na documentação da API do Rails! Desde então corrigi essa situação no trunk, mas o método é útil o suficiente (particularmente em conjunto com routing) que achei que valeria a pena blogar a respeito.
O ponto doloroso que inspirou o método é esse: suponha que você tem um punhado de chamadas de métodos, todos aceitando um hash de opções como último parâmetro, e muitos deles compartilhando um ou mais das mesmas opções. Definições de Routes são o exemplo canônico disso:
:controller => “message”, :action => “create”
map.delete_message “/msg/delete/:id”,
:controller => “message”, :action => “delete”
map.message “/msg/:id”,
:controller => “message”, :action => “get”
# etc, etc, etc
Feio! E definitivamente não muito DRY também. Uma maneira de resolver isso é definir uma variável separada que contém o hash de opções em comum, e usar Hash#merge para adicionar a diferença em cada chamada:
map.create_message “/msg/create/:id”,
common.merge(:action => “create”)
map.delete_message “/msg/delete/:id”,
common.merge(:action => “delete”)
map.message “/msg/:id”,
common.merge(:action => “get”)
# etc, etc, etc
Melhor, mas ainda não muito DRY. Object#with_options é a resposta de Rails a esse padrão:
msg.create_message “/msg/create/:id”,
:action => “create”
msg.delete_message “/msg/delete/:id”,
:action => “delete”
msg.message “/msg/:id”,
:action => “get”
# etc, etc, etc
end
Ah! A duplicação foi embora! Muito melhor.
Embora eu pessoalmente use isso primariamente para definição de routes, isso pode ser usado em qualquer lugar onde aparecem hashes de opções como último parâmetro … o que descreve a maioria das interfaces no Rails. Tem um punhado de associações em um model, todos os quais declarados dependentes de um pai?
with_options :dependent => :destroy do |parent|
parent.has_many :authors
parent.has_many :posts
parent.has_many :themes
end
end
Coisa boa! (E mais um exemplo do poder dos blocos no Ruby. Para os curiosos, vocês podem ler a implementação do with_options no projeto ActiveSupport do Rails, aqui e aqui. Tudo dito, isso tem menos de 30 linhas de código, então é fácil de pegar. (Parabéns a Sam Stephenson) pela bela implementação.
blog comments powered by Disqus
Archives
- February 12(2)
- December 11(1)
- November 11(4)
- October 11(6)
- September 11(5)
- August 11(1)
- July 11(5)
- May 11(4)
- April 11(11)
- March 11(4)
- February 11(3)
- January 11(4)
- December 10(9)
- November 10(2)
- October 10(10)
- September 10(4)
- August 10(6)
- July 10(14)
- June 10(16)
- May 10(8)
- April 10(14)
- March 10(9)
- February 10(6)
- January 10(14)
- December 09(10)
- November 09(10)
- October 09(7)
- September 09(19)
- August 09(4)
- July 09(12)
- June 09(7)
- May 09(12)
- April 09(11)
- March 09(9)
- February 09(9)
- January 09(12)
- December 08(14)
- November 08(20)
- October 08(15)
- September 08(18)
- August 08(25)
- July 08(13)
- June 08(21)
- May 08(29)
- April 08(27)
- March 08(12)
- February 08(32)
- January 08(31)
- December 07(27)
- November 07(30)
- October 07(25)
- September 07(28)
- August 07(16)
- July 07(15)
- June 07(16)
- May 07(7)
- April 07(13)
- March 07(8)
- February 07(9)
- January 07(24)
- December 06(17)
- November 06(17)
- October 06(15)
- September 06(38)




