[augeas-devel] Hash-like entries across multiple lines
Free Ekanayaka
free at 64studio.com
Mon Aug 25 08:22:49 UTC 2008
Hi,
I am working on a lens to parse /etc/dhclient.conf (you find the
current code below), and I would like to parse a sequence of
statements like:
send fqdn.fqdn \"grosse.fugue.com.\";
send fqdn.encoded on;
into a tree like:
{ "send"
{ "fqdn.fqdn" = "\"grosse.fugue.com.\"" }
{ "fqdn.encoded" = "on" } }
Note that the two statements could also be in different positions in
the file, not only one right after the other, for example:
send fqdn.fqdn \"grosse.fugue.com.\";
some statement;
more statements at will;
send fqdn.encoded on;
So the problem I am facing is how to add subnodes to a tree node which
was created before. I'm not sure if this is possible/acceptable..
Currently I'm creating different tree nodes for the two statements (see
test_dhclient.aug), like:
{ "send"
{ "fqdn.fqdn" = "\"grosse.fugue.com.\"" } }
{ "send"
{ "fqdn.encoded" = "on" } }
However I'd like to be able to have a single /send node with all its
hashed key/values pairs.
Ciao,
Free
================================ dhclient.aug =================================
(* Intefraces module for Augeas
Author: Free Ekanayaka <free at 64studio.com>
Reference: man dhclient.conf
The only difference with the reference syntax is that this lens assumes
that statements end with a new line, while the reference syntax allows
new statements to be started right after the trailing ";" of the previous
statement. This should not be a problem in real-life configuration files
as statements get usually splitted across several lines, rather than merged
in a single one.
*)
module Dhclient =
autoload xfm
(************************************************************************
* USEFUL PRIMITIVES
*************************************************************************)
let eol = Util.eol
let spc = Util.del_ws_spc
let comment = Util.comment
let empty = Util.empty
(* Define basic types *)
let comma = del /[ \t\n]*,[ \t\n]*/ ","
let scolon = del /[ \t]*;/ ";"
let word = /[A-Za-z0-9_.-]+(\[[0-9]+\])?/
let value = store /[^\\#,; \t\n]+/
let sep = del /[ \t\n]*/ " "
let indent = del /\n?[ \t]/ " "
(************************************************************************
* ARRAY STATEMENTS
*************************************************************************)
let array (t:string) = del t t . label t . indent .
[ sep . seq t . value ] .
[ comma . seq t . value ]* .
scolon . (eol|comment)
let a_statement_key = /request|require/
let a_statement = (
[ array "request" ] |
[ array "require" ] )
(************************************************************************
* HASH STATEMENTS
*************************************************************************)
let hash (t:string) =
del t t . label t .
indent .
[ sep . key word . indent . sep . value ]
let h_statement_key = /send/
let h_statement = (
[ hash "send" . scolon . (eol|comment) ] )
(************************************************************************
* SIMPLE STATEMENTS
*************************************************************************)
let s_statement_key = word - (a_statement_key | h_statement_key)
let s_statement = [
key s_statement_key .
indent . sep .
value .
scolon . (eol|comment) ]
let statement = (a_statement|s_statement |h_statement )
let lns = (empty | comment | statement)*
let filter = incl "/etc/dhcp3/dhclient.conf"
. Util.stdexcl
let xfm = transform lns filter
========================= test_dhclient.aug ===============================
module Test_dhclient =
let conf ="# Sample dhclient.conf
#
# Protocol timing
timeout 3; # Expect a fast server
retry
10;
# Lease requirements and requests
request
subnet-mask,
broadcast-address,
ntp-servers;
require subnet-mask, domain-name-servers; # We want these
# Dynamic DNS
send
fqdn.fqdn
\"grosse.fugue.com.\";
send fqdn.encoded on;
"
test Dhclient.lns get conf =
{ "#comment" = "Sample dhclient.conf" }
{}
{}
{ "#comment" = "Protocol timing" }
{ "timeout" = "3"
{ "#comment" = "Expect a fast server" } }
{ "retry" = "10" }
{}
{ "#comment" = "Lease requirements and requests" }
{ "request"
{ "1" = "subnet-mask" }
{ "2" = "broadcast-address" }
{ "3" = "ntp-servers" } }
{ "require"
{ "1" = "subnet-mask" }
{ "2" = "domain-name-servers" }
{ "#comment" = "We want these" } }
{}
{ "#comment" = "Dynamic DNS" }
{ "send"
{ "fqdn.fqdn" = "\"grosse.fugue.com.\"" } }
{ "send"
{ "fqdn.encoded" = "on" } }
More information about the augeas-devel
mailing list