summaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorluke <luke@980ebf18-57e1-0310-9a29-db15c13687c0>2006-02-07 02:31:00 +0000
committerluke <luke@980ebf18-57e1-0310-9a29-db15c13687c0>2006-02-07 02:31:00 +0000
commit4ecfa7bf4a0f88334afdec359f317b3bf7b44c21 (patch)
tree02dd9e06b7d7dc4ca29aa4523a3ada56c9f1be6c /lib
parent9114cbe18b11d2a4f3f58c4799f615721f4c2d71 (diff)
downloadpuppet-4ecfa7bf4a0f88334afdec359f317b3bf7b44c21.tar.gz
puppet-4ecfa7bf4a0f88334afdec359f317b3bf7b44c21.tar.xz
puppet-4ecfa7bf4a0f88334afdec359f317b3bf7b44c21.zip
Config files now seem to work, so I am ready to start incorporating them.
git-svn-id: https://reductivelabs.com/svn/puppet/trunk@868 980ebf18-57e1-0310-9a29-db15c13687c0
Diffstat (limited to 'lib')
-rw-r--r--lib/puppet/config.rb209
1 files changed, 164 insertions, 45 deletions
diff --git a/lib/puppet/config.rb b/lib/puppet/config.rb
index 833a2c6e3..3f9f65c47 100644
--- a/lib/puppet/config.rb
+++ b/lib/puppet/config.rb
@@ -1,16 +1,42 @@
module Puppet
# The class for handling configuration files.
class Config
- # Slight override, since we can't seem to have a subclass where all instances
- # have the same default block.
- def [](section)
- unless self.has_key?(section)
- self[section] = {}
+ # Retrieve a config value
+ def [](param)
+ param = param.intern unless param.is_a? Symbol
+ if @config.include?(param)
+ if @config[param]
+ val = @config[param].value
+ return val
+ end
+ else
+ nil
+ end
+ end
+
+ # Set a config value. This doesn't set the defaults, it sets the value itself.
+ def []=(param, value)
+ param = param.intern unless param.is_a? Symbol
+ unless @config.include?(param)
+ @config[param] = newelement(param, value)
end
- super
+ @config[param].value = value
+ end
+
+ # Remove all set values.
+ def clear
+ @config.each { |name, obj|
+ obj.clear
+ }
end
- def initialize(file)
+ # Create a new config object
+ def initialize
+ @config = {}
+ end
+
+ # Parse a configuration file.
+ def parse(file)
text = nil
begin
@@ -34,64 +60,157 @@ class Config
when /^\[(\w+)\]$/: section = $1 # Section names
when /^\s*#/: next # Skip comments
when /^\s*$/: next # Skip blanks
- when /^\s*(\w+)\s+(.+)$/: # settings
- var = $1
+ when /^\s*(\w+)\s*=\s*(.+)$/: # settings
+ var = $1.intern
value = $2
- self[section][var] = value
+ Puppet.info "%s: Setting %s to '%s'" % [section, var, value]
+
+ self[var] = value
+ @config[var].section = section
else
raise Puppet::Error, "Could not match line %s" % line
end
}
end
- def setdefaults(hash)
+ # Create a new element. The value is passed in because it's used to determine
+ # what kind of element we're creating, but the value itself might be either
+ # a default or a value, so we can't actually assign it.
+ def newelement(param, value)
+ mod = nil
+ case value
+ when true, false, "true", "false":
+ mod = CBoolean
+ when /^\$/, /^\//:
+ mod = CFile
+ when String: # nothing
+ else
+ raise Puppet::Error, "Invalid value '%s'" % value
+ end
+ element = CElement.new(param)
+ element.parent = self
+ if mod
+ element.extend(mod)
+ end
+
+ return element
+ end
+
+ # Set a bunch of defaults in a given section. The sections are actually pretty
+ # pointless, but they help break things up a bit, anyway.
+ def setdefaults(section, hash)
+ section = section.intern unless section.is_a? Symbol
hash.each { |param, value|
- if @defaults.include?(param)
+ if @config.include?(param) and @config[param].default
raise Puppet::Error, "Default %s is already defined" % param
end
+ unless @config.include?(param)
+ @config[param] = newelement(param, value)
+ end
+ @config[param].default = value
+ @config[param].section = section
+ }
+ end
- case value
- when true, false:
- @defaults[param] = Boolean.new(param, value)
- when String:
- @defaults[param] = Element.new(param, value)
- when Hash:
- type = nil
- unless value.include?(:type)
- raise Puppet::Error, "You must include the object type"
- end
- unless type = Puppet.type(value[:type])
- raise Puppet::Error, "Invalid type %s" % value[:type]
- end
+ # The base element type.
+ class CElement
+ attr_accessor :name, :section, :default, :parent
- value.delete(:type)
+ # Unset any set value.
+ def clear
+ @value = nil
+ end
- # FIXME this won't work, because we don't want to interpolate the
- # file name until they actually ask for it
- begin
- @defaults[param] = type.create(value)
- rescue => detail
- raise Puppet::Error, "Could not create default %s: %s" %
- [param, detail]
- end
+ # Create the new element. Pretty much just sets the name.
+ def initialize(name, value = nil)
+ @name = name
+ if value
+ @value = value
end
- }
- end
+ end
- class Element
- attr_accessor :name, :value
- end
+ # Retrieves the value, or if it's not set, retrieves the default.
+ def value
+ retval = nil
+ if defined? @value and ! @value.nil?
+ retval = @value
+ elsif defined? @default
+ retval = @default
+ else
+ return nil
+ end
- class File < Element
- end
+ if respond_to?(:convert)
+ return convert(retval)
+ else
+ return retval
+ end
+ end
- class Boolean < Element
+ # Set the value.
def value=(value)
- unless value == true or value == false
- raise Puppet::DevError, "Invalid value %s for %s" % [value, @name]
+ if respond_to?(:validate)
+ validate(value)
+ end
+ if respond_to?(:munge)
+ @value = munge(value)
+ else
+ @value = value
end
+ end
+ end
- @value = value
+ # A file.
+ module CFile
+ attr_accessor :user, :group, :mode, :type
+
+ def convert(value)
+ unless value
+ return nil
+ end
+ if value =~ /\$(\w+)/
+ parent = $1
+ if pval = @parent[parent]
+ newval = value.sub(/\$#{parent}/, pval)
+ return File.join(newval.split("/"))
+ else
+ raise Puppet::DevError, "Could not find value for %s" % parent
+ end
+ else
+ return value
+ end
+ end
+
+ # Set the type appropriately. Yep, a hack.
+ def munge(value)
+ if @name.to_s =~ /dir/
+ @type = :directory
+ else
+ @type = :file
+ end
+ return value
+ end
+
+ # Make sure any provided variables look up to something.
+ def validate(value)
+ value.scan(/\$(\w+)/) { |name|
+ name = name[0]
+ unless @parent[name]
+ raise Puppet::Error, "'%s' is unset" % name
+ end
+ }
+ end
+ end
+
+ # A simple boolean.
+ module CBoolean
+ def munge(value)
+ case value
+ when true, "true": return true
+ when false, "false": return false
+ else
+ raise Puppet::Error, "Invalid value %s for %s" % [value, @name]
+ end
end
end
end