Vyacheslav Loginov
Vyacheslav Loginov

Reputation: 3216

ruby dsl making

I try to write DSL

class Warcraft 
  class << self
    def config
      unless @instance
        yield(self)
      end
      @instance ||= self
    end

    attr_accessor :name, :battle_net

    def game(&block)
      @instance ||= Game.new(&block)
    end
  end

  class Game
    class << self
      def new
        unless @instance
          yield
        end
        @instance ||= self
      end

      attr_accessor :side, :hero

      def rune_appear_every(period)
        @rune_appear_every = period
      end

    end
  end
end

Warcraft.config do |war|
  war.name = "Warcraft III"
  war.battle_net = :iccup

  war.game do |game|
    game.side = :sentinels
    game.hero = "Furion"
    game.rune_appear_every 2.minutes
  end
end

And i get such error:

dsl.rb:41:in `block (2 levels) in <main>': undefined method `side=' for nil:NilClass (NoMethodError)

Upvotes: 0

Views: 142

Answers (1)

robbrit
robbrit

Reputation: 17960

The issue is here:

  def new
    unless @instance
      yield
    end
    @instance ||= self
  end

You're not passing in any argument when you yield, later on when you call:

 war.game do |game|

The game variable is nil. So instead of just doing yield, do yield self.

Upvotes: 3

Related Questions