help-cfengine
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

editfiles complexity


From: Systems Administrator
Subject: editfiles complexity
Date: Mon, 19 Jan 2004 17:21:16 +1100 (EST)

        Hi all.  We have about 80 different kinds of functions in the
editfiles section, and often there are groups that do similar things.  I
was windering if we could have a bit of a think, and see if we couldn't
come up with a better way of doing things, ie. performing the same
functions without having to remember 80 or so different commands.

        The first thing I noticed was how many of these commands were
based around IF x DO y.  My suggestion would be to have an IF ... DO
structure (only in editfiles, of course).  However, the <condition> will
sometimes need to access the parameters of the <action>, and vice versa, I
think.  Also, where I specify a field # in the action, it means the action
is done to that field # instead of the whole line.

IF [No(t)] <condition> [Parameters] DO <action> [Parameters]

condition:
        AnyLineMatches [ regex <regex> ]
        ThisLineMatches [ regex <regex> ]
        Defined <class>
        FileExists <filename>
        FileIsNewer <filename>
        FieldMatches [ regex ] <regex> <field#>
        LineNumber <line #>
        LastLine

action:
        Abort
        Append <string> [ <field#> ]
        BeginGroup ... EndGroup
        Break
        Comment [ <commentchar> ]
        Define [ InGroup ] <classes>
        DeleteLines
        Elapsed
        For <iterator> <action>
                Can be used to replace eg. CommentNLines.  Can contain a
                BeginGroup
        Locate <condition>
                (unfortunately this requires that conditions be settable,
                and it's up to cfengine to figure out how to make them
                true, but it's easy enough for things like LastLine)
        Prepend <string> [ <field#> ]
        ReplaceWith <string> [ <field#> ]
        RunScript
        Set [ InGroup ] <editvar> <value>
        UnComment [ <commentchar> ]
        Warn

        AutoCreate
        AutomountDirectResources quoted-string
        Backup quoted-string
        CatchAbort
        EditMode "Binary"
        EmptyEntireFilePlease
        ElseDefineClasses
        ExpireAfter mins
        Filter filteralias
        FixEndOfLine
        IncrementPointer quoted-number
        Inform quoted-string
        InsertFile quoted-string
        InsertLine quoted-string
        Recurse digit/inf
        ReplaceAll quoted-regex With quoted-string
        UnsetAbort quoted-string

editvars:
        CommentStart
        CommentEnd
        Line
        Script
        SplitOn
        Repository
        Syslog
        Umask
        UseShell

iterator:
        EachLineIn quoted-filename
        NLines <#lines>
        LinesTo <condition>


        Ok, so assuming we were to follow my advice, we'd now have 8
conditions, 33 commands, 9 variables which can be set with the Set
command, and 3 iterators (for use with "For").  Which is still 53 things
to remember.  Not a big improvement over 80, you might think.  But the
difference is, these 53 things can be combined to produce the equivalent
of 264 possible commands (and that's not counting editvars or iterators).
So 53 is a big reduction from 264+, at least to my mind.

        Additionally, say someone says "hey, we need a
RemovePorridgeIfAlmostMatches function".  Rather than writing a
function with that name, they'd write two functions, RemovePorridge, and
AlmostMatches.  That way, we'd be able to use:
-----
IF Not AlmostMatches DO Append "/etc/fstab"
-----
        And no-one would have to write the AppendIfAlmostMatches function.

        It would also mean that I'd have my:
-----
IF FieldMatches "/home" 2 DO Append ",nosuid,nodev" 4
-----
(IF Field 2 matches "/home" DO Append ",nosuid,nodev" to field 4).  Yeah,
sure, this looks a bit more complex, but the alternative would be
-----
AppendToFieldIfOtherFieldMatches "/home" 2 ",nosuid,nodev" 4
-----
-- which is even worse

        Or, to give you a more familar example (using /etc/sysctl.conf),
-----
AppendIfNoSuchLine "net.ipv4.ip_forward = 0"
-----
now becomes
-----
IF Not AnyLineMatches DO Append "net.ipv4.ip_forward = 0"
-----
        Of course, this is an example where the condition has to access
the parameters of the action.

        The editfiles section could also be turned into a separate
language as someone on the mailing list suggested some time ago.

        Possible objections answered:
-       It's less powerful
        I believe I've duplicated all existing functionality here, and
        with very little loss of readability for the power gained.  If
        you think otherwise, feel free to give me an example.
-       It's not the cfengine way (contains IF statements)
        Actually, it's pretty much identical to the current situation.
        Look at how many of the current editfiles commands already contain
        the word "if".  They're basically if statements in disguise.
        *However,* they're not your standard IF statements (either way) --
        they often contain iterators (cf. AnyLineMatches) or other
        powerful functionality under the hood (all of which I want to
        keep).

        Anyway, hope this is useful to how cfengine works, and means that
we don't have to add all of those 264 functions that I mentioned.

        Also, I by no means think that my idea is the be-all and end-all
of solutions.  I guess I was hoping to promote discussion of an area where
I think cfengine needs some work.

        Thanks,

        :)

--
Tim Nelson
Systems Administrator
Sunet Internet
Tel: +61 3 5241 1155
Fax: +61 3 5241 6187
Web: http://www.sunet.com.au/
Email: sysadmin@sunet.com.au











reply via email to

[Prev in Thread] Current Thread [Next in Thread]