Beefy Boxes and Bandwidth Generously Provided by pair Networks
The stupid question is the question not asked
 
PerlMonks  

Specifying multiple conditions in a config file

by korpenkraxar (Sexton)
on Jan 24, 2012 at 21:50 UTC ( [id://949775]=perlquestion: print w/replies, xml ) Need Help??

korpenkraxar has asked for the wisdom of the Perl Monks concerning the following question:

Dear bringers of Perl wisdom,

I am designing a Perl program that uses external configuration files and I thought I better ask here before I fall down the rabbit hole. In the application, the user will be able to specify certain external actions or settings (values in the config file) that are tied to labeled conditions in my program (keys in the config file). The program parses the settings and notes what actions are tied to what condition. This is pretty straightforward if the conditions are all expected to be "true" and "singular", but what if I would like to provide the option to trigger actions when a condition is not true or be able to combine conditions into arbitrary nested sets?

I guess my question boils down to this, should I spend time trying to develop a condition engine that can take any specified nested set of true or false conditions and walk through the corresponding Perl "if", "else", "OR", "AND" , "NOT" , "()" chain or simply require the user to write his/her own modified object that has requirements different from the basic vanilla object?

The first option may be nice for the user if the grammar is close to what we are used to from search engines for instance. However, unless there already exists a module that generates such conditional Perl code on the fly, I suspect I will be spending most of my development time on that feature alone. The second option is far more simple to implement, but basically asks users to write their own plugins.

What are your thoughts on this?

  • Comment on Specifying multiple conditions in a config file

Replies are listed 'Best First'.
Re: Specifying multiple conditions in a config file
by stevieb (Canon) on Jan 24, 2012 at 22:15 UTC

    If I understand correctly, you want to research 'dispatch tables'.

    They may not provide you with all of the complexity you are looking to achieve, but they will get you well on your way.

    Perhaps you could show some code and a snip with examples from your config file

    Steve

      Hi!

      Yes something like a dispatch table is probably what I need. I plan to use objects that register signals that they listen for and a state engine that keeps track of the signals. When an object catches a signal/condition it may send new ones and the fall-through restarts. The actual sensory input comes from a pipe or socket.

Re: Specifying multiple conditions in a config file
by Anonymous Monk on Jan 24, 2012 at 22:37 UTC
Re: Specifying multiple conditions in a config file
by TJPride (Pilgrim) on Jan 25, 2012 at 03:46 UTC
    Might help to see what format you want your config file to be in. But here's a quick hack. There might be ways to make it tighter in terms of variable scope and regex and so on, but it should work and be safe:

    use strict; use warnings; no warnings 'uninitialized'; my (%cond, %func, @config, %config, $cond, $func); ### Sample function sub FUNC { print "Successful condition.\n"; } ### Config values to allow in conditions $cond{$_}++ for qw/COND1 COND2 COND3/; ### Functions that can be called upon successful condition $func{$_}++ for qw/FUNC/; ### Eliminate potential exploits, convert operators sub c_parse { return $_[0] if $cond{$_[0]}; return '&&' if $_[0] eq 'AND'; return '||' if $_[0] eq 'OR'; } ### Safe the config file, store pre-processed results for later sub c_initialize { while (<DATA>) { chomp; ($cond, $func) = split / /; $cond =~ s/[^\w\(\) ]+/ /g; $cond =~ s/(\w+)/c_parse($1)/eg; $func =~ s/\W+//g; return if !$func{$func}; push @config, [$cond, $func]; } } ### Run through config looking for successful conditions sub c_process { print "Testing conditions.\n"; for (@config) { ($cond, $func) = @$_; $cond =~ s/(\w+)/$config{$1} || 0/eg; eval "$func\(\) if $cond"; } } c_initialize(); $config{COND1} = 1; $config{COND3} = 1; c_process(); $config{COND3} = 0; c_process(); $config{COND2} = 1; c_process(); __DATA__ COND1 AND (COND2 OR COND3) FUNC
      This is a very good reply for describing the internal logic! Thanx! eval will probably provide the most flexible solution together with some simple pseudoperl in the config file.

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://949775]
Approved by ww
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others about the Monastery: (7)
As of 2024-04-19 07:38 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found