Refinements arrived to Ruby trunk here. The purpose of Refinements is to make monkey patching safer, extending core classes but limiting its effects to a particular area of code.
Shugo Maeda wrote …
"Refinements are similar to Classboxes. However, Refinements doesn't support local rebinding as mentioned later. In this sense, Refinements might be more similar to selector namespaces, but I'm not sure because I have never seen any implementation of selector namespaces. In Refinements, a Ruby module is used as a namespace (or classbox) for class extensions. Such class extensions are called refinements. For example, the following module refines Fixnum."
You can read the long story here https://bugs.ruby-lang.org/issues/4085
So let’s see how Refinements work in practice
Basically instead of doing …
class Object def blank? respond_to?(:empty?) ? empty? : !self end end puts "".blank? puts "hi".blank? puts nil.blank? puts .blank? puts .blank?
and polluting all the objects, you can do …
module Blank refine Object do def blank? respond_to?(:empty?) ? empty? : !self end end end class A using Blank puts "".blank? # => true puts "hi".blank? # => false puts nil.blank? # => true puts .blank? # => true puts .blank? # => false end
and monkey patch in a controlled way. You can also check that you won’t be polluting all the objects in your system by checking …
class B puts "".blank? puts "hi".blank? puts nil.blank? puts .blank? puts .blank? end
This will raise an undefined method `blank?’ for String (NoMethodError).
Refinements has been committed to ruby by Shugo Maeda, but it may be reverted for Ruby 2.0. The Ruby Core is asking for feedback, so, what are the use cases you see Refinements is good for you?
You can learn more about Refinements reading Refinements in practice, a blog post from Yehuda Katz