Suavocado
Suavocado

Reputation: 969

Removing the need for capital letter in Ruby create for a DSL

I wrote a simple DSL that works with a call like:

create Pizza do 
    spread cheese
    spread sauce
    toppings shoes, jalapeno, apples
    bake
end

I would like to remove the uppercase P to make this call a little cleaner but I'm having trouble finding a way to make that possible.

Here is my code for PizzaBuilder.rb

class PizzaIngredients #factory


    def initialize
        @@order = {}
    end

    def method_missing(name, *args, &block)
        name.to_s
    end


    def spread (spread)
        @@order[:spreads] ||= []
        @@order[:spreads]  << spread
    end

    def bake
        @@order
    end

    def create (pizza)
        "making the #{pizza}"
    end

    def toppings (*toppingList)
        @@order[:toppings] ||= []
        @@order[:toppings]  += toppingList
    end
end

module Pizza #smokestack
    @order = []
    def self.order
        @order
    end

    def self.create(&block)
        pizza = PizzaIngredients.new
        pizza.instance_eval(&block)
    end
end

def create (param, &block)
    Pizza.create(&block)
end

Upvotes: 0

Views: 48

Answers (2)

Myst
Myst

Reputation: 19221

@suavocado - The capital letter is part of the conventions used by Ruby programmers all over the world...

Constants start with capital letters. variables use small letters... It's part of how we code and how we design....

These conventions are hard coded into the Ruby interperter.

Try the following code and see for your self:

class Pizza
   def self.test
     "hello!"
   end
end

Object.const_set 'Pita', Pizza # => okay

Object.const_set 'pizza', Pizza # => error

As some of the comments mentioned, you could use a symbol instead of a constant for your DSL, i.e.

create :pizza do
    # ...
end

Upvotes: 1

Suavocado
Suavocado

Reputation: 969

I fixed it by using this in the global scope

def method_missing(name, *args, &block)
    name.to_s == "pizza"? name.to_s : super
end

Upvotes: 0

Related Questions