NAME
Advanced::Config::Reader - Reader manager for Advanced::Config.
SYNOPSIS
use Advanced::Config::Reader;
or
require Advanced::Config::Reader;
DESCRIPTION
Advanced::Config::Reader is a helper module to Advanced::Config. So it should be very rare to directly call any methods defined by this module.
This module manages reading the requested config file into memory and parsing it for use by Advanced::Config.
Each config file is highly customizable. Where you are allowed to alter the comment char from # to anything you like, such as ;;. The same is true for things like the assignment operator (=), and many other character sequences with special meaning to this module.
So to avoid confusion, when I talk about a feature, I'll talk about it's default appearance and let it be safely assumed that the same will hold true if you've overriden it's default character sequence with something else. Such as when discussing comments as '#', even though you could have overriden it as ';*;'. See Advanced::Config::Options for a list of symbols you can overrides.
You are also allowed to surround your values with balanced quotes or leave them off entirely. The only time you must surround your value with quotes is when you want to preserve leading or trailing spaces in your value. Without balanced quotes these spaces are trimmed off. Also if you need a comment symbol in your tag's value, the entire value must be surrounded by quotes! Finally, unbalanced quotes can behave very strangly and are not stripped off.
So in general white space in your config file is basically ignored unless it's surrounded by printible chars or quotes.
Sorry you can't use a comment symbol as part of your tag's name.
See Advanced::Config::Examples for some sample config files. You may also find a lot of example config files in the package you downloaded from CPAN to install this module from under t/config.
FUNCTIONS
- $sts = read_config ( $file, $config )
-
This method performs the reading and parsing of the given config file and puts the results into the Advanced::Config object $config. This object provides the necessary parsing rules to use.
If a line was too badly mangled to be parsed, it will be ignored and a warning will be written to your screen.
It returns 1 on success and 0 on failure.
Please note that comments are just thrown away by this process and only tag/value pairs remain afterwards. Everything else is just instructions to the parser or how to group together these tag/value pairs.
If it sees something like: export tag = value, it will export tag's value to the %ENV hash for you just like it does in a Unix shell script!
Additional modifiers can be found in the comments after a tag/value pair as well.
- $boolean = source_file ($config, $def_sct, $new_file, $curr_file)
-
This is a private method called by read_config to source in the requested config file and merge the results into the current config file.
If $def_sct is given, it will be the name of the current section that the sourced in file is to use for it's default unlabeled section. If the default section name has been hard coded in the config file, this value overrides it.
The $new_file may contain variables and after they are expanded the source callback function is called before load_config() is called. See Advanced::Config::lookup_one_variable for rules on variable expansion.
If $new_file is a relative path, it's a relative path from the location of $curr_file, not the program's current directory!
If a source callback was set up, it will call it here.
This method will also handle the removal of decryption related options if new ones weren't provided by the callback function. See Advanced::Config::Options for more details.
Returns 1 if the new file successfully loaded. Else 0 if something went wrong during the load!
- $name = make_new_section ($config, $section)
-
This is a private method called by read_config to create a new section in the Advanced::Config object if a section of that name doesn't already exist.
The $section name is allowed to contain variables to expand before the string is used. But those variables must be defined in the main section.
Returns the name of the section found/created in lower case.
- @ret[0..4] = parse_line ( $input, \%opts )
-
This is a private method called by read_config to parse each line of the config file as it's read in. It's main purpose is to strip off leading and trailing spaces and any comments it might find on the input line. It also tells if the $input contains a tag/value pair.
It returns 5 values: ($tv_flg, $line, $comment, $lQuote, $rQuote)
$tv_flg - True if $line contains a tag/value pair in it, else false.
$line - The trimmed $input line minus any comments.
$comment - The comment stripped out of the original input line minus the leading comment symbol(s).
$lQuote & rQuote - Only set if $tv_flg is true and $lQuote was the 1st char of the value and $rQuote was the last char of the tag's value. If the value wasn't surrounded by balanced quotes, both return values will be the empty string "".
If these quotes are returned, it expects the caller to remove them from the tag's value. The returned values for these quote chars are suitable for use as is in a RegExpr. The caller must do this in order to preserve potential leading/trailing spaces.
- ($v[, $h]) = expand_variables ( $config, $string[, $file[, $sensitive[, trim]]] )
-
This function takes the provided $string and expands any embedded variables in this string similar to how it's handled by a Unix shell script.
The optional $file tells which file the string was read in from.
The optional $sensitive when set to a non-zero value is used to disable fish logging when it's turned on because the $string being passed contains sensitive information.
The optional $trim tells if you may trim the results before it's returned.
It returns the new value $v, once all the variable substitition(s) have occured. And optionally a second return value $h that tells if fish was paused during the expansion of that value due to something being sensitive. This 2nd return value $h is meaningless in most situations, so don't ask for it.
All variables are defined as ${...}, where ... is the variable you wish to substitute. If something isn't surrounded by a ${ + } pair, it's not a variable.
A config file exampe: tmp1 = /tmp/work-1 tmp2 = /tmp/work-2 opt = 1 date = 2011-02-03 logs = ${tmp${opt}}/log-${date}.txt date = 2012-12-13 So when passed "${tmp${opt}}/log-${date}.txt", it would return: /tmp/work-1/log-2011-02-03.txt And assigned it to B<logs>.
As you can see multiple variable substitutions may be expanded in a single string as well as nested substitutions. And when the variable substitution is done while reading in the config file, all the values used were defined before the tag was referenced.
Should you call this method after the config file was loaded you get slightly different results. In that case the final tag value is used instead and the 2nd date in the above example would have been used in it's place.
See Advanced::Config::lookup_one_variable for more details on how it evaluates individual variables.
As a final note, if one or more of the referenced variables holds encrypted values that haven't yet been decrypted, those variables are not resolved. But all variables that don't contain encrypted data are resolved.
- ($v[, $s]) = apply_modifier ( $config, $value, $tag, $rule, $sub_rule, $file )
-
This is a helper method to expand_variables. Not for public use.
This function takes the rule specified by $rule and applies it against the $value with assistance from the $sub_rule.
It returns the edited value and whether applying the modifier made it sensitive. (-1 means it's an encrypted value. -2 means it's the variable name that resolves to an encrypted value. 0 - Non-senitive, 1 - Sensitive.)
See https://web.archive.org/web/20200309072646/https://wiki.bash-hackers.org/syntax/pe for information on how this can work. This module supports most of the parameter expansions listed there except for those dealing with arrays. Other modifier rules may be added upon request.
- @ret[0..7] = parse_for_variables ( $value, $ignore_disable_flag, $rOpts )
-
This is a helper method to expand_variables and parse_line.
This method parses the $value to see if any variables are defined in it and returns the information about it. If there is more than one variable present in the $value, only the 1st variable/tag to evaluate is returned.
By default, a variable is the tag in the $value between ${ and }, which can be overriden with other anchor patterns. See Advanced::Config::Options for more details on this.
If you've configured the module to ignore variables, it will never find any. Unless you also set $ignore_disable_flag to a non-zero value.
Returns 8 values. ( $left, $tag, $right, $cmt, $sub_tag, $sub_opr, $sub_val, $otag )
All 8 values will be undef if no variables were found in $value.
Otherwise it returns at least the 1st four values. Where $tag is the variable that needs to be looked up. And the caller can join things back together as "$left . $look_up_value . $right" after the variable substitution is done and before this method is called again to locate additional variables in the resulting new $value.
The 4th value $cmt, will be true/false based on if $left has a comment symbol in it! This flag only has meaning to parse_line. And is terribly misleading to other users.
Should the $tag definition have one of the supported shell script variable modifiers embedded inside it, then the $tag will be parsed and the 3 sub_* return values will be calculated as well. See http://wiki.bash-hackers.org/syntax/pe for more details. Most of the modifiers listed there are supported except for those dealing with arrays. See apply_modifier for applying these rules against the returned $tag. Other modifier rules may be added upon request.
These 3 sub_* return values will always be undef should the variable left/right anchors be overriden with the same value. Or if no modifiers are detected in the tag's name.
If you've configured the module to be case insensitive (option tag_case), then both $tag and $sub_tag will be shifted to lower case for case insensitive variable lookups.
Finally there is an 8th return value, $otag, that contains the original $tag value before it was edited. Needed by parse_line logic.
- $string = format_section_line ( $name, \%rOpts )
-
Uses the given Read Options Hash to generate a section string from $name.
- $string = format_tag_value_line ( $cfg, $tag, \%rOpts )
-
It looks up the tag in the $cfg object, then it uses the given Read Options Hash options to format a tag/value pair string.
- $string = format_encrypt_cmt ( \%rOpts )
-
Uses the given Read Options Hash to generate a comment suitable for use in marking a tag/value pair as ready to be encrypted.
- $status = encrypt_config_file_details ( $file, $writeFile, \%rOpts )
-
This function encrypts all tag values inside the specified confg file that are marked as ready for encryption and generates a new config file with everything encrypted. If a tag/value pair isn't marked as ready for encryption it is left alone. By default this label is ENCRYPT.
After a tag's value has been encrypted, the label in the comment is updated from ENCRYPT to DECRYPT in the new file.
If you are adding new ENCRYPT tags to an existing config file that already has DECRYPT tags in it, you must use the same encryption related options in %rOpts as the last time. Otherwise you won't be able to decrypt all encrypted values.
This method ignores any request to source in other config files. You must encryt each file individually.
It writes the results of the encryption process to $writeFile.
See Advanced::Config::Options for some caveats about this process.
Returns: 1 if something was encrypted. -1 if nothing was encrypted. Otherwise 0 on error.
- $status = decrypt_config_file_details ( $file, $writeFile, \%rOpts )
-
This function decrypts all tag values inside the specified confg file that are marked as encrypted and generates a new file with everyting decrypted. If a tag/value pair isn't marked as being encrypted it is left alone. By default this label is DECRYPT.
After a tag's value has been decrypted, the label in the comment is updated from DECRYPT to ENCRYPT in the config file.
For this to work, the encryption related options in \%rOpts must match what was used in the call to encrypt_config_file_details or the decryption will fail.
This method ignores any request to source in other config files. You must decrypt each file individually.
It writes the results of the decryption process to $writeFile.
See Advanced::Config::Options for some caveats about this process.
Returns: 1 if something was decrypted. -1 if nothing was decrypted. Otherwise 0 on error.
- $value = encrypt_value ($value, $tag, $rOpts, $file)
-
Takes the $value and encrypts it using the other 3 args as part of the encryption key. To successfully decrypt it again you must pass the same 3 values for these args to the decrypt_value() call.
See Advanced::Config::Options for some caveats about this process.
- $value = decrypt_value ($value, $tag, $rOpts, $file)
-
Takes the $value and decrypts it using the other 3 args as part of the decryption key. To successfully decrypt it the values for these 3 args must match what was passed to encryption_value() when the value was originially encrypted.
See Advanced::Config::Options for some caveats about this process.
COPYRIGHT
Copyright (c) 2007 - 2025 Curtis Leach. All rights reserved.
This program is free software. You can redistribute it and/or modify it under the same terms as Perl itself.
SEE ALSO
Advanced::Config - The main user of this module. It defines the Config object.
Advanced::Config::Options - Handles the configuration of the Config module.
Advanced::Config::Date - Handles date parsing for get_date().
Advanced::Config::Examples - Provides some sample config files and commentary.