MasterRoot24 MasterRoot24 - 7 months ago 17
Ruby Question

How do I extend this Ruby module?

I'm trying to utilise the Gmail gem in a gem that I'm building. From the source, you can see that the gem defines the Gmail module/class like so (simplified):

module Gmail
class << self
def connect; end
end
end


What I would like to do is to extend the Gmail module/class into a class of my own. Essentially, this is a generic example of what I'm trying to do:

module Foo
class << self
def example
puts :this_is_foo
end
end
end

class Bar
extend Foo
end


Then I should be able to call:

Bar.example


But I get the following exception:

NoMethodError: undefined method `example' for Bar:Class


How do I make methods that are available in
Foo
available in
Bar
in the above example?

Answer

You can use included for your goal:

module Foo
  def self.included(base)
    base.extend ClassMethods
  end

  module ClassMethods
    def example
      puts :this_is_foo
    end 
  end
end

class Bar
  include Foo
end

Bar.example
this_is_foo
#=> nil

Or if you want to include only class methods, you can make your example method instance and extend Bar module:

module Foo
  def example
    puts :this_is_foo
  end 
end
class Bar
  extend Foo
end
Bar.example
this_is_foo
#=> nil