NAME

Config::Objective - Perl module for parsing object-oriented config files

SYNOPSIS

  use Config::Objective;
  use Config::Objective::String;
  use Config::Objective::List;

  my $conf = Config::Objective->new('filename',
                {
                        'var1' => Config::Objective::String->new(),
                        'var2' => Config::Objective::List->new(),
                        ...
                },
                'include_dir'   => '/usr/local/share/appname');

  print "var1 = \"" . $conf->var1 . "\"\n";

DESCRIPTION

The Config::Objective module provides a mechanism for parsing config files to manipulate configuration data. Unlike most other config file modules, which represent config data as simple variables, Config::Objective represents config data as perl objects. This allows for a much more flexible configuration language, since new classes can be easily written to add methods to the config syntax.

The Config::Objective class supports the following methods:

new()

The constructor. The first argument is the filename of the config file to parse. The second argument is a reference to a hash that maps names to configuration objects.

The remaining arguments are interpretted as a hash of attributes for the object. Currently, the only supported attribute is include_dir, which specifies the directory to search for include files (see "File Inclusion"). If not specified, include_dir defaults to ".".

object_name

Once the constructor parses the config file, you can call the get() method of any of the objects by using the object name as an autoloaded method (see "Recommended Methods").

get_obj()

Returns a reference to the object of the specified object name. The object name is the first argument.

obj_names()

Returns a list of known object names.

get_hash()

Returns a hash where the keys are the known object names and the values are the result of calling the get() method on the corresponding object.

CONFIG FILE SYNTAX

The config file format supported by Config::Objective is described here.

Data Types

Config::Objective supports three types of data: scalars, lists, and hashes. The syntax for these types is intentionally similar to their perl equivalents.

Scalars

A scalar is represented as a simple integer or string value. If it is composed only of letters, numbers, and the underscore character, it can be written literally:

  foo
  all_word_characters
  123
  alpha_123_numeric
  4sure

However, if the value contains whitespace or other non-word characters, it must be quoted:

  "telnet/tcp"
  "use quotes for whitespace"
  "quotes can be escaped like this \" inside quoted strings"
  "quoted
     strings
   can span
   multiple lines"
Lists

A list is represented as a sequence of comma-delimited values enclosed by square brackets:

  [ this, is, a, list ]

Note that each value in a list can itself be a scalar, list, or hash:

  [ this, is, a, [ nested, list ] ]
  [ this, list, contains, a, { hash => value } ]
Hashes

A hash is represented as a sequence of zero or more comma-delimited entries enclosed in curly braces:

  { this => 1, is => 2, a => 3, hash => 4 }

As in perl, each entry contains a key and a value. However, unlike perl, the value is optional:

  { this, is, a, hash, without, values }
  { this => hash, has => "some values", but, not, others }

When no value is specified for a given entry, its value is undefined.

Note that hash keys must always be scalars. However, values may be scalars, lists, or hashes:

  { "this is a" => [ list, within, a, hash ] }
  { "this is a" => { sub => hash } }

Configuration Statements

Each statement in the config file results in calling a method on a configuration object. The syntax is:

  object[->method] [args];

In this syntax, "object" is the name of the object. The object must be created and passed to the Config::Objective constructor, as described above.

The "->method" portion is optional. If specified, it indicates which method should be called on the object. If not specified, a method called default() will be used.

The "args" portion is also optional. It specifies one or more comma-delimited arguments to pass to the method. If multiple arguments are provided, the entire argument list must be enclosed in parentheses. Each argument can be a simple scalar, list, hash, or a complex, nested list or hash structure, as described above.

So, putting this all together, here are some example configuration statements:

  ### call default method with no arguments
  object;

  ### call a specific method, but still no args
  object->method;

  ### call default method, but specify a single scalar argument
  object scalar_arg;

  ### call default method, but specify a single list argument
  object [ this, is, a, single, list, argument ];

  ### call a specific method and specify a single hash argument
  object->method { this, is, a, single, hash, argument };

  ### call a specific method with multiple scalar args
  object->method(arg1, arg2, arg3);

  ### call a specific method with multiple args of different types
  object->method(scalar_arg, [ list, argument ], { hash => argument });

Conditional Evaluation

The config syntax also provides some rudementary support for conditional evaluation. A conditional directive is signalled by the use of a "%" character at the beginning of a line (i.e., no leading whitespace). There can be space between the "%" and the conditional directive, however, which can improve readability when using nested conditional blocks.

The conditional directives are %if, %else, %elif, and %endif. They can be used to enclose other config statements, which are evaluated or skipped based on whether the conditional expression evaluates to true. For example:

  %if ( expression )
    ... other config directives ...
  %endif

The most basic expression is simply a method call that returns a true or false value. The syntax for this is the same as a normal config statement, except without the trailing semicolon:

  %if ( object[->method] [args] )

If no method is specified, the equals() method will be called by default.

Multiple expressions can be combined using the "&&", "||", and "!" operators. Additional parentheses can also be used for grouping within the expression. For example:

  %if ( ( object1 foo && ! object2 bar ) || object3 baz )

File Inclusion

File inclusion is another type of conditional evaluation. It allows you to include another file in the config file that is currently being parsed, similar to the C preprocessor's "#include" directive. The syntax is:

  %include "filename"

If the specified filename is not an absolute path, Config::Objective will look for it in the directory specified by the include_dir attribute when the Config::Objective object was created.

Note that the %include directive will be ignored within an %if block whose condition is false. This means that you cannot start an %if block in one file, add a %include directive, and provide the %endif directive in the included file. All %if blocks must be fully contained within the same file.

Comments

Any text between a "#" character and the next newline is considered a comment. The "#" character loses this special meaning if it is enclosed in a quoted string or immediately preceded by a "\".

CONFIGURATION OBJECTS

This section explains the details of how configuration objects are used.

There are no strict requirements for how a class must be designed in order to be used for a configuration object. The following methods are recommended in that they will be used by Config::Objective in certain circumstances, but they do not need to be present if they are not actually going to be used.

get()

Return the value encapsulated by the object. This is used when you use call the variable name as a method of the Config::Objective object. For example:

  print "var1 = '" . $conf->var1 . "'\n";

This will implicitly call the get() method of the object named var1.

default()

This is the default method used when a configuration file references an object with no method.

equals()

This is the default method used when a configuration file references an object with no method as part of an expression. (See "Conditional Evaluation" above.)

Supplied Object Classes

Config::Objective supplies several classes that can be used for encapsulating common types of configuration data.

Config::Objective::Boolean
Config::Objective::Hash
Config::Objective::Integer
Config::Objective::List
Config::Objective::String
Config::Objective::Table

See the documentation for each of these classes for more information.

AUTHOR

Mark D. Roth <roth@uiuc.edu>

SEE ALSO

perl.