Guest User

Untitled

a guest
Aug 16th, 2018
69
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.45 KB | None | 0 0
  1. How can I extract blocks from this configuration file using Perl?
  2. pool {
  3. name "POOL_name1"
  4. ttl 30
  5. monitor all "tcp"
  6. preferred rr
  7. partition "Common"
  8.  
  9. member 12.24.5.100:80
  10. }
  11.  
  12. pool {
  13. name "Pool-name2"
  14. ttl 30
  15. monitor all "https_ignore_dwn"
  16. preferred rr
  17. fallback rr
  18. partition "Common"
  19.  
  20. member 69.241.25.121:8443
  21. member 69.241.25.122:8443
  22. }
  23.  
  24. my @POOLDATA = <FILE>;
  25. close FILE;
  26. foreach (@POOLDATA) {
  27. if (/^pools{s/ .. /^}s/) {
  28. push (@POOLCONFIG, "$_");
  29. }
  30. }
  31.  
  32. #!/usr/bin/env perl
  33.  
  34. use warnings; use strict;
  35.  
  36. my @pools;
  37.  
  38. my $keys = join('|', sort
  39. 'name',
  40. 'ttl',
  41. 'monitor all',
  42. 'preferred',
  43. 'partition',
  44. 'member'
  45. );
  46.  
  47. my $pat = qr/^($keys)s+([^n]+)nz/;
  48.  
  49. while ( my $line = <DATA> ) {
  50. if ($line =~ /^pools+{/ ) {
  51. push @pools, {},
  52. }
  53. elsif (my ($key, $value) = ($line =~ $pat)) {
  54. $value =~ s/^"([^"]+)"z/$1/;
  55. push @{ $pools[-1]->{$key} }, $value;
  56. }
  57. }
  58.  
  59. use Data::Dumper;
  60. print Dumper @pools;
  61.  
  62.  
  63. __DATA__
  64. pool {
  65. name "POOL_name1"
  66. ttl 30
  67. monitor all "tcp"
  68. preferred rr
  69. partition "Common"
  70.  
  71. member 12.24.5.100:80
  72. }
  73.  
  74. pool {
  75. name "Pool-name2"
  76. ttl 30
  77. monitor all "https_ignore_dwn"
  78. preferred rr
  79. fallback rr
  80. partition "Common"
  81.  
  82. member 69.241.25.121:8443
  83. member 69.241.25.122:8443
  84. }
  85.  
  86. while ( my $line = <DATA> ) {
  87. if ($line =~ /^pools+{/ ) {
  88. push @pools, {},
  89. }
  90. elsif (my ($key, $value) = ($line =~ $pat)) {
  91. $value =~ s/^"([^"]+)"z/$1/;
  92. push @{ $pools[-1]->{$key} }, $value;
  93. }
  94. elsif ($line =~ /^s*}/) {
  95. my $last = $pools[-1];
  96.  
  97. if ($last and not $last->{member}) {
  98. $last->{member} = [ qw(0.0.0.0) ];
  99. }
  100. }
  101.  
  102. }
  103.  
  104. while ( my $line = <DATA> ) {
  105. if ($line =~ /^pools+{/ ) {
  106. push @pools, {},
  107. }
  108. elsif (my ($key, $value) = ($line =~ $pat)) {
  109. $value =~ s/^"([^"]+)"z/$1/;
  110. push @{ $pools[-1]->{$key} }, $value;
  111. }
  112. elsif ($line =~ /^s*}/) {
  113. my $last = $pools[-1];
  114.  
  115. if ($last and not $last->{member}) {
  116. $last->{member} = [ qw(0.0.0.0) ];
  117. }
  118. }
  119.  
  120. }
  121.  
  122. use strict;
  123. use warnings;
  124. use Data::Dumper;
  125. use English qw<$RS>;
  126. use List::MoreUtils qw<natatime>;
  127. use Params::Util qw<_ARRAY _CODE>;
  128.  
  129. # Here, we rig the record separator to break on n}n
  130. local $RS = "n}n";
  131.  
  132. # Here, we standardize a behavior with hash duplicate keys
  133. my $TURN_DUPS_INTO_ARRAYS = sub {
  134. my ( $hr, $k, $ov, $nv ) = @_;
  135. if ( _ARRAY( $ov )) {
  136. push @{ $ov }, $nv;
  137. }
  138. else {
  139. $h->{ $k } = [ $ov, $nv ];
  140. }
  141. };
  142.  
  143. # Here is a generic hashing routine
  144. # Most of the work is figuring out how the user wants to store values
  145. # and deal with duplicates
  146. sub hash {
  147. my ( $code, $param_name, $store_op, $on_duplicate );
  148. while ( my ( $peek ) = @_ ) {
  149. if ( $code = _CODE( $peek )) {
  150. last unless $param_name;
  151.  
  152. if ( $param_name eq 'on_dup' ) {
  153. $on_duplicate = shift;
  154. }
  155. elsif ( $param_name eq 'store' ) {
  156. $store_op = shift;
  157. }
  158. else {
  159. last;
  160. }
  161. undef $code;
  162. }
  163. else {
  164. my @c = $peek =~ /^-?(on_dup|store$)/;
  165. last unless $param_name = $c[0];
  166. shift;
  167. }
  168. }
  169.  
  170. $store_op ||= sub { $_[0]->{ $_[1] } = $_[3]; };
  171. $on_duplicate ||= $code || $store_op;
  172.  
  173. my %h;
  174. while ( @_ ) {
  175. my $k = shift;
  176. next unless defined( my $v = shift );
  177. (( exists $h{ $k } and $on_duplicate ) ? $on_duplicate
  178. : $store_op
  179. )->( %h, $k, $h{ $k }, $v )
  180. ;
  181. }
  182. return wantarray ? %h : %h;
  183. }
  184.  
  185.  
  186. my %pools;
  187. # So the loop is rather small
  188. while ( <DATA> ) {
  189. # remove pool { ... } brackets
  190. s/As*pools+{s*n//smx;
  191. s/ns*}n*//smx;
  192. my $h
  193. = hash( -on_duplicate => $TURN_DUPS_INTO_ARRAYS
  194. , map { s/"$//; s/s+$//; $_ }
  195. map { split /s+"|s{2,}/msx, $_, 2 }
  196. split /n/m
  197. );
  198. $pools{ $h->{name} } = $h;
  199. }
  200. print Dumper( %pools );
  201. ### %pools
  202.  
  203. __DATA__
  204. pool {
  205. name "POOL_name1"
  206. ttl 30
  207. monitor all "tcp"
  208. preferred rr
  209. partition "Common"
  210.  
  211. member 12.24.5.100:80
  212. }
  213.  
  214. pool {
  215. name "Pool-name2"
  216. ttl 30
  217. monitor all "https_ignore_dwn"
  218. preferred rr
  219. fallback rr
  220. partition "Common"
  221.  
  222. member 69.241.25.121:8443
  223. member 69.241.25.122:8443
  224. }
Add Comment
Please, Sign In to add comment