problem with accessors and dsl's

T

Tsunami Scripter

I've created a class using the following code :

class CommandHandler

attr_accessor :command,:arguments

def initialize(command=nil,arguments=nil,what=nil)
@command = command
@arguments = arguments
@what = what
@code = nil
end

def perform(arguments,what)
@code.call(arguments,what) if [email protected]?
end

end

and a class named CommandProcessor , which , among other methods has the
following :

def add_handler(&block)
handler = CommandHandler.new
handler.instance_eval &block
@map[handler.command] = handler
end

so I can add handlers in a DSL-like way . Here is a sample of code in
action :

add_handler do
command=("get")
code=(lambda do |arguments,what|
begin
@mech.get(arguments.join(""))
return @mech.page.body
rescue
return "#{arguments} could not be loaded"
end
end)
end
end

However , by the time the code reaches @map[handler.command] = handler ,
if I print the handler object , all of it's attributes appear as nil . I
specifically added

command=("...")
and code=("...")

so that the interpreter wouldn't have to use "heuristics" to deduce what
I was trying to say . Why isn't the code working as it should ?

Thanks !
 
J

Joel VanderWerf

Tsunami said:
so I can add handlers in a DSL-like way . Here is a sample of code in
action :

add_handler do
command=("get")

This is interpreted as local variable assignment. You can use the
following syntaxes instead:

self.command = "get"

or (defining #command differently)

command "get"
 
D

David A. Black

Hi --

I've created a class using the following code :

class CommandHandler

attr_accessor :command,:arguments

def initialize(command=nil,arguments=nil,what=nil)
@command = command
@arguments = arguments
@what = what
@code = nil
end

def perform(arguments,what)
@code.call(arguments,what) if [email protected]?
end

end

and a class named CommandProcessor , which , among other methods has the
following :

def add_handler(&block)
handler = CommandHandler.new
handler.instance_eval &block
@map[handler.command] = handler
end

so I can add handlers in a DSL-like way . Here is a sample of code in
action :

add_handler do
command=("get")
code=(lambda do |arguments,what|
begin
@mech.get(arguments.join(""))
return @mech.page.body
rescue
return "#{arguments} could not be loaded"
end
end)
end
end

However , by the time the code reaches @map[handler.command] = handler ,
if I print the handler object , all of it's attributes appear as nil . I
specifically added

command=("...")
and code=("...")

so that the interpreter wouldn't have to use "heuristics" to deduce what
I was trying to say . Why isn't the code working as it should ?

See Joel's answer; I just wanted to add the gloss that the interpreter
doesn't really use heuristics to figure out what x = y means. It
*always* interprets it as an local variable assignment. If it used
more elaborate heuristics, it might pick up on your non-use of the
syntactic sugar and decide it was a method call. But it's very
literal-minded about that form of expression.

I wouldn't sweat the "DSL" aspects of it, if by that you mean the
business of not having to specify a receiver. There's no real
advantage to that unless you're trying to create a full-blown
self-describing toolset (and even then, I think the "stealth"
instance_eval is not as great an idea as it might sometimes seem).


David

--
David A. Black / Ruby Power and Light, LLC
Ruby/Rails consulting & training: http://www.rubypal.com
Coming in 2009: The Well-Grounded Rubyist (http://manning.com/black2)

http://www.wishsight.com => Independent, social wishlist management!
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,582
Members
45,067
Latest member
HunterTere

Latest Threads

Top