From: ivan Date: Sun, 16 Oct 2005 14:04:00 +0000 (+0000) Subject: add zone-underscore config file, update bind.import to use command-line options inste... X-Git-Tag: BEFORE_FINAL_MASONIZE~350 X-Git-Url: http://git.freeside.biz/gitweb/?p=freeside.git;a=commitdiff_plain;h=4750962f384c8061f4b5c78201a449b1f41c56c7 add zone-underscore config file, update bind.import to use command-line options instead of ask for input --- diff --git a/FS/FS/Conf.pm b/FS/FS/Conf.pm index fc10b137e..7ba0f35be 100644 --- a/FS/FS/Conf.pm +++ b/FS/FS/Conf.pm @@ -1617,6 +1617,12 @@ httemplate/docs/config.html 'type' => 'checkbox', }, + { + 'key' => 'zone-underscore', + 'section' => 'BIND', + 'description' => 'Allow underscores in zone names. As underscores are illegal characters in zone names, this option is not recommended.', + 'type' => 'checkbox', + }, ); diff --git a/FS/FS/domain_record.pm b/FS/FS/domain_record.pm index e975cac51..3c65a1a05 100644 --- a/FS/FS/domain_record.pm +++ b/FS/FS/domain_record.pm @@ -250,9 +250,17 @@ sub check { return "Unknown svcnum (in svc_domain)" unless qsearchs('svc_domain', { 'svcnum' => $self->svcnum } ); - $self->reczone =~ /^(@|[a-z0-9\.\-\*]+)$/i - or return "Illegal reczone: ". $self->reczone; - $self->reczone($1); + my $conf = new FS::Conf; + + if ( $conf->exists('zone-underscore') ) { + $self->reczone =~ /^(@|[a-z0-9_\.\-\*]+)$/i + or return "Illegal reczone: ". $self->reczone; + $self->reczone($1); + } else { + $self->reczone =~ /^(@|[a-z0-9\.\-\*]+)$/i + or return "Illegal reczone: ". $self->reczone; + $self->reczone($1); + } $self->recaf =~ /^(IN)$/ or return "Illegal recaf: ". $self->recaf; $self->recaf($1); @@ -284,17 +292,26 @@ sub check { or return "Illegal data for A record: ". $self->recdata; $self->recdata($1); } elsif ( $self->rectype eq 'PTR' ) { - $self->recdata =~ /^([a-z0-9\.\-]+)$/i - or return "Illegal data for PTR record: ". $self->recdata; - $self->recdata($1); + if ( $conf->exists('zone-underscore') ) { + $self->recdata =~ /^([a-z0-9_\.\-]+)$/i + or return "Illegal data for PTR record: ". $self->recdata; + $self->recdata($1); + } else { + $self->recdata =~ /^([a-z0-9\.\-]+)$/i + or return "Illegal data for PTR record: ". $self->recdata; + $self->recdata($1); + } } elsif ( $self->rectype eq 'CNAME' ) { $self->recdata =~ /^([a-z0-9\.\-]+|\@)$/i or return "Illegal data for CNAME record: ". $self->recdata; $self->recdata($1); } elsif ( $self->rectype eq 'TXT' ) { - $self->recdata =~ /^((?:\S+)|(?:".+"))$/ - or return "Illegal data for TXT record: ". $self->recdata; - $self->recdata($1); + if ( $self->recdata =~ /^((?:\S+)|(?:".+"))$/ ) { + $self->recdata($1); + } else { + $self->recdata('"'. $self->recdata. '"'); #? + } + # or return "Illegal data for TXT record: ". $self->recdata; } elsif ( $self->rectype eq '_mstr' ) { $self->recdata =~ /^((\d{1,3}\.){3}\d{1,3})$/ or return "Illegal data for _master pseudo-record: ". $self->recdata; diff --git a/bin/bind.import b/bin/bind.import index 41313fba6..1cdf5672c 100755 --- a/bin/bind.import +++ b/bin/bind.import @@ -1,22 +1,33 @@ #!/usr/bin/perl -w # +# REQUIRED: +# -p: part number for domains +# +# -n: named.conf file (or an include file with zones you want to import), +# for example root@ns.isp.com:/var/named/named.conf +# +# OPTIONAL: +# -d: dry-run, debug: don't insert any records, just dump debugging output # -s: import slave zones as master. useful if you need to recreate your # primary nameserver from a secondary -# -c chroot_dir: import data from chrooted bind (corrects the path for -# downloading zone files +# -c dir: override patch for downloading zone files (for example, when +# downloading zone files from chrooted bind) # # need to manually put header in # /usr/local/etc/freeside/export./named.conf.HEADER +# (or, nowadays, better just to include the file freeside exports) use strict; -use vars qw( %d_part_svc ); + +use vars qw($domain_svcpart); + use Getopt::Std; -use Term::Query qw(query); +use Data::Dumper; #use BIND::Conf_Parser; #use DNS::ZoneParse 0.81; -#use Net::SCP qw(iscp); -use Net::SCP qw(scp); +use Net::SCP qw(scp iscp); + use FS::UID qw(adminsuidsetup datasrc); use FS::Record qw(qsearch); #qsearchs); #use FS::svc_acct_sm; @@ -25,8 +36,8 @@ use FS::domain_record; #use FS::svc_acct; #use FS::part_svc; -use vars qw($opt_s $opt_c); -getopts("sc:"); +use vars qw($opt_p $opt_n $opt_s $opt_c $opt_d); +getopts("p:n:sc:d"); my $user = shift or die &usage; adminsuidsetup $user; @@ -38,42 +49,19 @@ use vars qw($spooldir); $spooldir = "/usr/local/etc/freeside/export.". datasrc. "/bind"; mkdir $spooldir unless -d $spooldir; -%d_part_svc = - map { $_->svcpart, $_ } qsearch('part_svc',{'svcdb'=>'svc_domain'}); +$domain_svcpart = $opt_p; + +my $named_conf = $opt_n; -print "\n\n", - ( join "\n", map "$_: ".$d_part_svc{$_}->svc, sort keys %d_part_svc ), - "\n\n"; -use vars qw($domain_svcpart); -$^W=0; #Term::Query isn't -w-safe -$domain_svcpart = - query "Enter part number for domains: ", 'irk', [ keys %d_part_svc ]; -$^W=1; - -print "\n\n", <{masters} } ) { - my $domain_record = new FS::domain_record( { - 'svcnum' => $domain->svcnum, - 'reczone' => '@', - 'recaf' => 'IN', - 'rectype' => '_mstr', - 'recdata' => $master, - } ); - my $error = $domain_record->insert; - die $error if $error; + if ( $main::opt_d ) { + + use Data::Dumper; + print "$name: ". Dumper($options); + + } else { + + foreach my $master ( @{ $options->{masters} } ) { + my $domain_record = new FS::domain_record( { + 'svcnum' => $domain->svcnum, + 'reczone' => '@', + 'recaf' => 'IN', + 'rectype' => '_mstr', + 'recdata' => $master, + } ); + my $error = $domain_record->insert; + die $error if $error; + } + } } elsif ( $type eq 'master' || ( $type eq 'slave' && $main::opt_s ) ) { @@ -153,54 +148,79 @@ BEGIN { use File::Basename; my $basefile = basename($file); my $sourcefile = $file; - $sourcefile = "$named_dir/$sourcefile" unless $file =~ /^\//; - $sourcefile = "$main::opt_c/$sourcefile" if $main::opt_c; + if ( $main::opt_c ) { + $sourcefile = "$main::opt_c/$sourcefile" if $main::opt_c; + } else { + $sourcefile = "$named_dir/$sourcefile" unless $file =~ /^\//; + } use Net::SCP qw(iscp scp); - scp("root\@$main::named_machine:$sourcefile", - "$main::prefix/$basefile.import"); + #iscp("$main::named_machine:$sourcefile", + # "$main::prefix/$basefile.import"); + scp("$main::named_machine:$sourcefile", + "$main::prefix/$basefile.import"); use DNS::ZoneParse 0.84; my $zone = DNS::ZoneParse->new("$main::prefix/$basefile.import"); my $dump = $zone->dump; - - #use Data::Dumper; - #print "$name: ". Dumper($dump); - #exit; + + if ( $main::opt_d ) { + + use Data::Dumper; + print "$name: ". Dumper($dump); + + } else { - foreach my $rectype ( keys %$dump ) { - if ( $rectype =~ /^SOA$/i ) { - my $rec = $dump->{$rectype}; - my $domain_record = new FS::domain_record( { - 'svcnum' => $domain->svcnum, - 'reczone' => $rec->{origin}, - 'recaf' => 'IN', - 'rectype' => $rectype, - 'recdata' => - $rec->{primary}. ' '. $rec->{email}. ' ( '. - join(' ', map $rec->{$_}, - qw( serial refresh retry expire minimumTTL ) ). - ' )', - } ); - my $error = $domain_record->insert; - die $error if $error; - } else { - #die $dump->{$rectype}; - foreach my $rec ( @{ $dump->{$rectype} } ) { + foreach my $rectype ( keys %$dump ) { + if ( $rectype =~ /^SOA$/i ) { + my $rec = $dump->{$rectype}; + $rec->{email} =~ s/\@/\./; my $domain_record = new FS::domain_record( { 'svcnum' => $domain->svcnum, - 'reczone' => $rec->{name}, - 'recaf' => $rec->{class}, + 'reczone' => $rec->{origin}, + 'recaf' => 'IN', 'rectype' => $rectype, - 'recdata' => ( $rectype =~ /^MX$/i - ? $rec->{priority}. ' '. $rec->{host} - : $rec->{host} ), + 'recdata' => + $rec->{primary}. ' '. $rec->{email}. ' ( '. + join(' ', map $rec->{$_}, + qw( serial refresh retry expire minimumTTL ) ). + ' )', } ); my $error = $domain_record->insert; die $error if $error; + } else { + #die $dump->{$rectype}; + + my $datasub; + if ( $rectype =~ /^MX$/i ) { + $datasub = sub { $_[0]->{priority}. ' '. $_[0]->{host}; }; + } elsif ( $rectype =~ /^TXT$/i ) { + $datasub = sub { $_[0]->{text}; }; + } else { + $datasub = sub { $_[0]->{host}; }; + } + + foreach my $rec ( @{ $dump->{$rectype} } ) { + my $domain_record = new FS::domain_record( { + 'svcnum' => $domain->svcnum, + 'reczone' => $rec->{name}, + 'recaf' => $rec->{class} || 'IN', + 'rectype' => $rectype, + 'recdata' => &{$datasub}($rec), + } ); + my $error = $domain_record->insert; + if ( $error ) { + warn "$error inserting ". + $rec->{name}. ' . '. $domain->domain. "\n"; + warn Dumper($rec); + #system('cat',"$main::prefix/$basefile.import"); + die; + } + } } } + } #} else {