Make instance methods private in runtime

access-specifier, ruby

Solution

What's public and what's private is per class. But each object can have its own class:

class Foo

  private

  def private_except_to_bar
    puts "foo"
  end

end

class Bar

  def initialize(foo)
    @foo = foo.dup
    class << @foo
      public :private_except_to_bar
    end
    @foo.private_except_to_bar
  end

end

foo = Foo.new
Bar.new(foo)    # => "foo"

foo.private_except_to_bar
# => private method `private_except_to_bar' called for #<Foo:0xb7b7e550> (NoMethodError)

But yuck. Consider these alternatives:

- Just make the method public.

- Explore alternative designs.

Problem

I need to make some instance methods private after registering that object in another object. I don't want to freeze the object because it must remain editable, only with less functionality. And I don't want to undef the methods since they are used internally. What I need is something like: ``` class MyClass def my_method puts "Hello" end end a = MyClass.new b = MyClass.new a.my_method #=> "Hello" a.private_instance_method(:my_method) a.my_method #=> NoMethodError b.my_method #=> "Hello" ``` Any ideas?

Original source