module RubyYacht::DSL::Base

This module provides the core functionality for providing configuration DSLs.

Classes that provide DSLs should include this module and extend the ClassMethods module.

Public Class Methods

new() click to toggle source

This initializer creates a new DSL instance.

# File lib/ruby_yacht/dsl/dsl.rb, line 200
def initialize
  load_custom_attributes
end

Public Instance Methods

check_required_attributes() click to toggle source

This method checks that all of the required attributes have been set on the object.

If they haven’t, this will raise an exception.

# File lib/ruby_yacht/dsl/dsl.rb, line 330
def check_required_attributes
  attributes = self.singleton_class.required_attributes || []
  attributes.each do |name|
    value = instance_variable_get("@#{name}")
    if value == nil || value == ''
      raise "Missing required attribute #{name} for #{self.class}"
    end
  end
end
check_server_type(server_type, container_type) click to toggle source

This method checks that a server type has been registered.

If it has not, this will raise an exception.

### Parameters

  • **server_type: Symbol** The server type that has been set on this

    DSL instance.
  • **container_type: Symbol** The container type that the server type

    must be registered for.
# File lib/ruby_yacht/dsl/dsl.rb, line 350
def check_server_type(server_type, container_type)
  result = RubyYacht.configuration.find_server_type(server_type)
  unless result && result.container_type == container_type
    raise "#{self.class.name} has invalid #{container_type} server type `#{server_type}`"
  end
end
copy_local_config(*fields, from:nil) click to toggle source

This method copies fields from the local config to this DSL.

The local config must have been loaded in a previous configuration block using the ‘add_local_config` method.

The keys in the local config file should all be symbols, as should the ‘fields`. If they are not, this method may not be able to find the config entries.

Any fields that are not present in the local config will be set to nil.

### Parameters

  • **fields: [Symbol]** The fields to load.

  • **from: String** A dot-separated key path to the location in

    the config file that contains the dictionary
    that we are pulling the fields from.
# File lib/ruby_yacht/dsl/dsl.rb, line 311
def copy_local_config(*fields, from:nil)
  dictionary = RubyYacht.configuration.local_config
  if from
    from.split('.').each do |key|
      dictionary = dictionary[key.to_sym]
    end
  end
  fields.each do |field|
    unless self.singleton_class.all_attributes.include?(field)
      raise "Undefined field in #{self.class.name}: #{field}"
    end
    instance_variable_set("@#{field}", dictionary[field])
  end
end
create_object() click to toggle source

This method creates an object with the attributes from this instance.

We will check that all the required attributes have been set first, and will raise an exception if they haven’t.

The created type, and the attributes we set on it, will be defined by the call to the class method ‘creates_object`.

### Returns This will return the newly created object.

# File lib/ruby_yacht/dsl/dsl.rb, line 367
def create_object
  check_required_attributes
  object = self.class.created_type.new
  self.singleton_class.copied_attributes.each do |name|
    object.send("#{name}=", instance_variable_get("@#{name}"))
  end
  object
end
load_custom_attributes() click to toggle source

This method adds attributes to this DSL instance’s singleton DSL, based on the attributes defined by the app types that have been loaded.

# File lib/ruby_yacht/dsl/dsl.rb, line 206
def load_custom_attributes
  full_class = self.class
  self.singleton_class.instance_eval do
    @copied_attributes = (full_class.copied_attributes || []).dup
    @all_attributes = full_class.all_attributes.dup
    @required_attributes = full_class.required_attributes.dup
    @default_values = full_class.default_values.dup
  end

  if self.class.created_type
    RubyYacht.configuration.server_types.each do |server_type|
      next if @server_type && server_type.name != @server_type
      if server_type.respond_to?(self.class.custom_attribute_method)
        attributes = server_type.send(self.class.custom_attribute_method)
        attributes.each do |attribute|
          attribute = attribute.merge(name: "#{server_type.name}_#{attribute[:name]}".to_sym)
          load_custom_attribute(attribute)
        end
      end
    end
  end
end
run(block) click to toggle source

This method runs a block with DSL methods.

The block will reun in the instance context of the DSL object, so you can call the DSL methods directly.

It will also copy the default values into the attributes on the DSL object.

### Parameters

  • **block: Proc** The block to run.

# File lib/ruby_yacht/dsl/dsl.rb, line 265
def run(block)
  defaults = self.singleton_class.default_values || {}
  defaults.each do |name, value|
    copy =
      case value
      when TrueClass, FalseClass, Fixnum, Symbol
        value
      else
        value.dup
      end
    instance_variable_set("@#{name}", copy)
  end
  if block
    instance_eval(&block)
  end
  
  type = RubyYacht.configuration.find_server_type(@server_type)
  if type
    type.server_defaults.each do |server_defaults|
      server_defaults.each do |key, value|
        if instance_variable_get("@#{key}") == nil
          instance_variable_set("@#{key}", value)
        end
      end
    end
  end
  self
end

Private Instance Methods

load_custom_attribute(attribute) click to toggle source

This method defines the fields for a custom attribute on the DSL.

### Parameters

  • **attribute: Hash** The settings on the attribute. The ‘name`

    setting must already include the app type's
    prefix.
# File lib/ruby_yacht/dsl/dsl.rb, line 238
def load_custom_attribute(attribute)
  if attribute.has_key?(:required)
    required = attribute[:required]
  else
    required = true
  end
  name = attribute[:name]
  self.singleton_class.add_attribute name, attribute[:default], required
  self.singleton_class.copied_attributes << name
  self.class.created_type.instance_eval do
    attr_accessor name
  end
end