I prefer to let my code and my tools remember stuff for me. Rails and similarly-magical Ruby systems have too high a (human) memory overhead for my taste. Hard to jump in and out of if it's not the main thing you do every day.
I know in my projects I use some techniques which if you continued to work on the project you would really appreciate how many problems it solves but it seems crazy to my coworkers. Luckily it's a small gem and I'm the one who works on it but still.
To metaprogramming! The cause of -- and solution to -- all of life's problems.
def my_method
super_result = super
...
(do something with super_result, or simply after super has been called)
...
super_result <== to make sure your method returns the result of super
end
you can just do this: def my_method
super.tap{|result| (do something with/after result) } <== will still return the result of super
endlike many other features on the fringe of a language it's important to understand when it's appropriate to use
also - there are few better buzzes writing code than doing something neat, skinny and appropriate with those Ruby features
I sometimes fantasise about a world where what you describe is just... how we write software. I really wish i could use my colleagues libraries instead of digging into their source code.
As far as the metaprogramming is encapsulated in a module with a good API and serves to make business code easier to read, it can be extremely helpful.
i wish there were more of these (ruby) metaprogramming articles, since there is a lot of ingenuity going on under the covers.
it's just like jargon in specialized fields - so much is packed into so few symbols. it allows those who understand it to express more complex ideas more easily but also serves as a barrier to those unfamiliar with the jargon.
That said, the article is about something quite minimal in terms of metaprogramming: subclassing a class (Module), which would itself not be defined as metaprogramming at all, and then defining some methods on it in an initializer. I don't find this very convoluted at all: you're creating a prototype for a module which can be configured to use in a variety of contexts.
I wrote this article after having used this pattern in a very practical context (designing Mobility) to solve a very concrete problem: abstracting storage solutions (backends) from the interface for translating content. I found it to be a very concise and elegant solution in this context. I think a project like Rails would benefit in several places by adopting this pattern since it would actually simplify a lot of the code which already uses anonymous modules (basically the same mechanism) but in a very hard-to-understand way.
Comparisons to other languages like Clojure and Elixir bring with them a whole slew of other questions, since the languages are entirely different. I'd prefer to focus on Ruby itself and what the alternatives are within this language, and for the use case discussed I strongly believe Module Builder is the optimal solution, not a "mess" at all.
This is quite nice. It avoid some of the issues that other metaprograming techniques will land you, and the associated debugging hell.
Nicely written too.