# Defining a singleton method dynamically

**URL:** <https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325>\
**Category:** ruby-talk\
**Created:** [10 September 2009 12:35 UTC](https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325 "2009-09-10T12:35:09Z")\
**Posts on this page:** 6\
**Page:** 1

<div class="post-metadata">

**Author:** ![Nilesh\_Trivedi](https://avatars.discourse-cdn.com/v4/letter/n/b5a626/32.png) [@Nilesh\_Trivedi](https://rubytalk.org/u/Nilesh_Trivedi)\
**Post date:** [10 September 2009 12:35 UTC](https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325/1 "2009-09-10T12:35:09Z")

</div>

How do I define a singleton method dynamically?

I have code similar to this:

def foo(obj,label)  
&nbsp;&nbsp;def [obj.name](http://obj.name); label; end #we want to define a singleton method called  
"name" on obj which returns the value in label  
&nbsp;&nbsp;puts [obj.name](http://obj.name) #this is an example. Actually I have some code here which  
expects this singleton method in obj  
end

When I try to run this as foo(Object.new,"xyz"), it throws a "NameError:  
undefined local variable or method `label' for #\<Object:0xb7b02018\>" whereas  
I want it to print "xyz" to screen.

Of course, line 2 in method foo is not correct. But what is the correct way?

---

<div class="post-metadata">

**Author:** ![David\_A\_Black1](https://avatars.discourse-cdn.com/v4/letter/d/bcef8e/32.png) [@David\_A\_Black1](https://rubytalk.org/u/David_A_Black1)\
**Post date:** [10 September 2009 12:49 UTC](https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325/2 "2009-09-10T12:49:52Z")

</div>

Hi --

> How do I define a singleton method dynamically?
> 
> I have code similar to this:
> 
> def foo(obj,label)  
> def obj.name; label; end #we want to define a singleton method called  
> "name" on obj which returns the value in label  
> puts obj.name #this is an example. Actually I have some code here which  
> expects this singleton method in obj  
> end
> 
> When I try to run this as foo(Object.new,"xyz"), it throws a "NameError:  
> undefined local variable or method `label' for #\<Object:0xb7b02018\>" whereas  
> I want it to print "xyz" to screen.
> 
> Of course, line 2 in method foo is not correct. But what is the correct way?

def starts a new local scope, so it won't see label. You need to get  
into obj's singleton class, using code blocks rather than class and  
def blocks:

&nbsp;&nbsp;&nbsp;def foo(obj, label)  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(class \<\< obj; self; end).class\_eval do  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;define\_method("name") { label }  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;&nbsp;end

You could also do something with eval but I prefer to use the code  
block approach rather than the string-eval'ing approach.

(Still hoping for Object#singleton\_class to make the access to the  
singleton class a little less awkward 🙂

David

> **···**
>
> On Thu, 10 Sep 2009, Nilesh Trivedi wrote:
> 
> --  
> David A. Black / Ruby Power and Light, LLC / [http://www.rubypal.com](http://www.rubypal.com)  
> Ruby/Rails training, mentoring, consulting, code-review  
> Latest book: The Well-Grounded Rubyist ([http://www.manning.com/black2\](http://www.manning.com/black2%5C))
> 
> September Ruby training in NJ has been POSTPONED. Details to follow.

---

<div class="post-metadata">

**Author:** ![Nilesh\_Trivedi](https://avatars.discourse-cdn.com/v4/letter/n/b5a626/32.png) [@Nilesh\_Trivedi](https://rubytalk.org/u/Nilesh_Trivedi)\
**Post date:** [10 September 2009 12:52 UTC](https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325/3 "2009-09-10T12:52:05Z")

</div>

Replacing line 2 by:

obj.instance\_eval "def name; '#{label}'; end"

does get the behaviour that I want. Is this the best way to do this or is  
there a better, cleaner way?

cheers  
nilesh

> **···**
>
> On Thu, Sep 10, 2009 at 6:05 PM, Nilesh Trivedi \<nilesh.tr@gmail.com\> wrote:
> 
> > How do I define a singleton method dynamically?
> > 
> > I have code similar to this:
> > 
> > def foo(obj,label)  
> > &nbsp;&nbsp;def obj.name; label; end #we want to define a singleton method called  
> > "name" on obj which returns the value in label  
> > &nbsp;&nbsp;puts obj.name #this is an example. Actually I have some code here which  
> > expects this singleton method in obj  
> > end
> > 
> > When I try to run this as foo(Object.new,"xyz"), it throws a "NameError:  
> > undefined local variable or method `label' for #\<Object:0xb7b02018\>" whereas  
> > I want it to print "xyz" to screen.
> > 
> > Of course, line 2 in method foo is not correct. But what is the correct  
> > way?

---

<div class="post-metadata">

**Author:** ![David\_A\_Black1](https://avatars.discourse-cdn.com/v4/letter/d/bcef8e/32.png) [@David\_A\_Black1](https://rubytalk.org/u/David_A_Black1)\
**Post date:** [10 September 2009 12:56 UTC](https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325/4 "2009-09-10T12:56:44Z")

</div>

Hi --

> **···**
>
> On Thu, 10 Sep 2009, Nilesh Trivedi wrote:
> 
> > On Thu, Sep 10, 2009 at 6:05 PM, Nilesh Trivedi \<nilesh.tr@gmail.com\> wrote:
> > 
> > > How do I define a singleton method dynamically?
> > > 
> > > I have code similar to this:
> > > 
> > > def foo(obj,label)  
> > > &nbsp;&nbsp;def obj.name; label; end #we want to define a singleton method called  
> > > "name" on obj which returns the value in label  
> > > &nbsp;&nbsp;puts obj.name #this is an example. Actually I have some code here which  
> > > expects this singleton method in obj  
> > > end
> > > 
> > > When I try to run this as foo(Object.new,"xyz"), it throws a "NameError:  
> > > undefined local variable or method `label' for #\<Object:0xb7b02018\>" whereas  
> > > I want it to print "xyz" to screen.
> > > 
> > > Of course, line 2 in method foo is not correct. But what is the correct  
> > > way?
> > 
> > Replacing line 2 by:
> > 
> > obj.instance\_eval "def name; '#{label}'; end"
> > 
> > does get the behaviour that I want. Is this the best way to do this or is  
> > there a better, cleaner way?
> 
> It may be overkill, but I pretty much always choose the block form of  
> \*\_eval rather than the string form, as per my response of a couple of  
> minutes ago. If you're going to eval strings, you could also do:
> 
> &nbsp;&nbsp;&nbsp;eval "def obj.name; '#{label}'; end"
> 
> David
> 
> --  
> David A. Black / Ruby Power and Light, LLC / [http://www.rubypal.com](http://www.rubypal.com)  
> Ruby/Rails training, mentoring, consulting, code-review  
> Latest book: The Well-Grounded Rubyist ([http://www.manning.com/black2\](http://www.manning.com/black2%5C))
> 
> September Ruby training in NJ has been POSTPONED. Details to follow.

---

<div class="post-metadata">

**Author:** ![JEG2](https://avatars.discourse-cdn.com/v4/letter/j/a183cd/32.png) [@JEG2](https://rubytalk.org/u/JEG2)\
**Post date:** [10 September 2009 13:28 UTC](https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325/5 "2009-09-10T13:28:37Z")

</div>

I agree, but it's needed a little less in Ruby 1.9 which adds defined\_singleton\_method(). Thus, in 1.9 your code could be:

&nbsp;&nbsp;&nbsp;def foo(obj, label)  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;obj.define\_singleton\_method(:name) { label }  
&nbsp;&nbsp;&nbsp;end

As a side topic, the fact that this method was added seems to kill the argument about why we can't have singleton\_class(). As I understand it, the method we want is never added because we aren't sure if the name is right yet. Seems like we're committed to the name at this point and might as well just get on with defining the methods that help us.

James Edward Gray II

> **···**
>
> On Sep 10, 2009, at 7:49 AM, David A. Black wrote:
> 
> > Hi --
> > 
> > On Thu, 10 Sep 2009, Nilesh Trivedi wrote:
> > 
> > > How do I define a singleton method dynamically?
> > > 
> > > I have code similar to this:
> > > 
> > > def foo(obj,label)  
> > > def obj.name; label; end #we want to define a singleton method called  
> > > "name" on obj which returns the value in label  
> > > puts obj.name #this is an example. Actually I have some code here which  
> > > expects this singleton method in obj  
> > > end
> > > 
> > > When I try to run this as foo(Object.new,"xyz"), it throws a "NameError:  
> > > undefined local variable or method `label' for #\<Object:0xb7b02018\>" whereas  
> > > I want it to print "xyz" to screen.
> > > 
> > > Of course, line 2 in method foo is not correct. But what is the correct way?
> > 
> > def starts a new local scope, so it won't see label. You need to get  
> > into obj's singleton class, using code blocks rather than class and  
> > def blocks:
> > 
> > def foo(obj, label)  
> > &nbsp;&nbsp;&nbsp;(class \<\< obj; self; end).class\_eval do  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;define\_method("name") { label }  
> > &nbsp;&nbsp;&nbsp;end  
> > end
> > 
> > You could also do something with eval but I prefer to use the code  
> > block approach rather than the string-eval'ing approach.
> > 
> > (Still hoping for Object#singleton\_class to make the access to the  
> > singleton class a little less awkward 🙂

---

<div class="post-metadata">

**Author:** ![Nilesh\_Trivedi](https://avatars.discourse-cdn.com/v4/letter/n/b5a626/32.png) [@Nilesh\_Trivedi](https://rubytalk.org/u/Nilesh_Trivedi)\
**Post date:** [10 September 2009 13:23 UTC](https://rubytalk.org/t/defining-a-singleton-method-dynamically/55325/6 "2009-09-10T13:23:54Z")

</div>

Thanks Davind. That makes sense. 🙂

cheers  
nilesh  
[http://nileshtrivedi.in](http://nileshtrivedi.in)

> **···**
>
> On Thu, Sep 10, 2009 at 6:26 PM, David A. Black \<dblack@rubypal.com\> wrote:
> 
> > Hi --
> > 
> > On Thu, 10 Sep 2009, Nilesh Trivedi wrote:
> > 
> > On Thu, Sep 10, 2009 at 6:05 PM, Nilesh Trivedi \<nilesh.tr@gmail.com\> \>\> wrote:
> > 
> > > How do I define a singleton method dynamically?
> > > 
> > > > I have code similar to this:
> > > > 
> > > > def foo(obj,label)  
> > > > def obj.name; label; end #we want to define a singleton method called  
> > > > "name" on obj which returns the value in label  
> > > > puts obj.name #this is an example. Actually I have some code here which  
> > > > expects this singleton method in obj  
> > > > end
> > > > 
> > > > When I try to run this as foo(Object.new,"xyz"), it throws a "NameError:  
> > > > undefined local variable or method `label' for #\<Object:0xb7b02018\>"  
> > > > whereas  
> > > > I want it to print "xyz" to screen.
> > > > 
> > > > Of course, line 2 in method foo is not correct. But what is the correct  
> > > > way?
> > > 
> > > Replacing line 2 by:
> > > 
> > > obj.instance\_eval "def name; '#{label}'; end"
> > > 
> > > does get the behaviour that I want. Is this the best way to do this or is  
> > > there a better, cleaner way?
> > 
> > It may be overkill, but I pretty much always choose the block form of  
> > \*\_eval rather than the string form, as per my response of a couple of  
> > minutes ago. If you're going to eval strings, you could also do:
> > 
> > eval "def obj.name; '#{label}'; end"
> > 
> > David
> > 
> > --  
> > David A. Black / Ruby Power and Light, LLC / [http://www.rubypal.com](http://www.rubypal.com)  
> > Ruby/Rails training, mentoring, consulting, code-review  
> > Latest book: The Well-Grounded Rubyist ([http://www.manning.com/black2\](http://www.manning.com/black2%5C))
> > 
> > September Ruby training in NJ has been POSTPONED. Details to follow.
