From: Intransition Date: 2011-11-07T13:13:02+09:00 Subject: Re: Tricky DSL, how to do it? ------=_Part_2277_10667543.1320639179475 Content-Type: multipart/alternative; boundary="----=_Part_2278_8080077.1320639179475" ------=_Part_2278_8080077.1320639179475 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit Hi Luke, I think your idea about the "outside" is on the right track. I ended doing something akin to that, but in my case the "outside" is just toplevel (aka
). Your solution is defining methods on the class of the outside object. It gets the desired results, but at the expense of polluting the class's namespace. In my case, using toplevel, that actually might not be a problem, so yea, this might be a workable solution. But I found using methods had some other limitations (e.g. problem evaluate it in another scope). So I ended up doing something a bit different, but at it's core it's the same approach as yours, just without the method definitions. The "trick" I came up with was: def block.call(*args) ::Kernel.eval('self',::TOPLEVEL_BINDING).instance_exec(*args, &self) end This defines a singleton method on the block overriding the original #call method, forcing evaluation of the block at the toplevel. Once I had that working, I refactored so I could get the same result but without have to monkey patch the Proc object. So far so good. If you are interested in the actual project code, it is here: https://github.com/rubyworks/confection/blob/master/lib/confection.rb Thanks for the help. ------=_Part_2278_8080077.1320639179475 Content-Type: text/html; charset=UTF-8 Content-Transfer-Encoding: quoted-printable Hi Luke, 

I think your idea about the "outside" is = on the right track. I ended doing something akin to that, but in my case th= e "outside" is just toplevel (aka <main>).  Your solution is def= ining methods on the class of the outside object. It gets the desired resul= ts, but at the expense of polluting the class's namespace. In my case, usin= g toplevel, that actually might not be a problem, so yea, this might be a w= orkable solution. But I found using methods had some other limitations (e.g= . problem evaluate it in another scope). So I ended up doing something= a bit different, but at it's core it's the same approach as yours, just wi= thout the method definitions. The "trick" I came up with was:

      def block.call(*args)
  &nbs= p;      ::Kernel.eval('self',::TOPLEVEL_BINDING).instance_ex= ec(*args, &self)
      end
This defines a singleton method on the block overriding t= he original #call method, forcing evaluation of the block at the toplevel. = Once I had that working, I refactored so I could get the same result but wi= thout have to monkey patch the Proc object. So far so good.

<= /div>
If you are interested in the actual project code, it is here: &nb= sp;https://github.com/rubyworks/confection/blob/master/lib/confectio= n.rb

Thanks for the help.
------=_Part_2278_8080077.1320639179475-- ------=_Part_2277_10667543.1320639179475--