055782a20b8391df7ef662e7590b606c4a9eb926
[freeside.git] / bin / bind.export
1 #!/usr/bin/perl -w
2
3 use strict;
4 use File::Path;
5 use File::Rsync;
6 use Net::SSH qw(ssh);
7 use FS::UID qw(adminsuidsetup datasrc);
8 use FS::Record qw(qsearch qsearchs);
9 use FS::part_export;
10 use FS::cust_pkg;
11 use FS::cust_svc;
12 use FS::svc_domain;
13
14 my $user = shift or die &usage;
15 adminsuidsetup $user;
16
17 my $spooldir = "/usr/local/etc/freeside/export.". datasrc. "/bind";
18 mkdir $spooldir, 0700 unless -d $spooldir;
19
20 my @exports = qsearch('part_export', { 'exporttype' => 'bind' } );
21 my @sexports = qsearch('part_export', { 'exporttype' => 'bind_slave' } );
22
23 my $rsync = File::Rsync->new({
24   rsh     => 'ssh',
25 #  dry_run => 1,
26 });
27
28 foreach my $export ( @exports ) {
29
30   my $machine = $export->machine;
31   my $prefix = "$spooldir/$machine";
32
33   #prevent old domain files from piling up
34   #rmtree "$prefix" or die "can't rmtree $prefix.db: $!";
35
36   mkdir $prefix, 0700 unless -d $prefix;
37
38   open(NAMED_CONF,">$prefix/named.conf")
39     or die "can't open $prefix/named.conf: $!";
40
41   open(CONF_HEADER,"<$prefix/named.conf.HEADER")
42     or die "can't open $prefix/named.conf.HEADER: $!";
43   while (<CONF_HEADER>) { print NAMED_CONF $_; }
44   close CONF_HEADER;
45
46   my $zonepath = $export->option('zonepath');
47   $zonepath =~ s/\/$//;
48
49   my @svc_domain = $export->svc_x;
50
51   foreach my $svc_domain ( @svc_domain ) {
52     my $domain = $svc_domain->domain;
53     my @masters = qsearch('domain_record', {
54       'svcnum' => $svc_domain->svcnum,
55       'rectype' => '_mstr',
56     } );
57     if ( @masters ) {
58       my $masters = join('; ', map { $_->recdata } @masters );
59
60       print NAMED_CONF <<END;
61 zone "$domain" {
62         type slave;
63         file "db.$domain";
64         masters { $masters; };
65 };
66
67 END
68
69     } else {
70
71       print NAMED_CONF <<END;
72 zone "$domain" {
73         type master;
74         file "$zonepath/db.$domain";
75 };
76
77 END
78
79       open (DB_MASTER,">$prefix/db.$domain")
80         or die "can't open $prefix/db.$domain: $!";
81
82       my @domain_records =
83         qsearch('domain_record', { 'svcnum' => $svc_domain->svcnum } );
84       foreach my $domain_record (
85         sort { $b->rectype cmp $a->rectype } @domain_records
86       ) {
87         #if ( $domain_record->rectype eq 'SOA' ) {
88         #  print DB_MASTER join("\t", $domain_record-> reczone
89         #} else {
90           print DB_MASTER join("\t",
91             map { $domain_record->getfield($_) }
92               qw( reczone recaf rectype recdata )
93           ), "\n";
94         #}
95       }
96
97       close DB_MASTER;
98
99     }
100
101   }
102
103   $rsync->exec( {
104     src       => "$prefix/",
105     recursive => 1,
106     dest      => "root\@$machine:$zonepath/",
107     exclude   => [qw( *.import named.conf.HEADER named.conf )],
108   } ) or die "rsync to $machine failed: ". join(" / ", $rsync->err);
109  # warn $rsync->out;
110
111   $rsync->exec( {
112     src     => "$prefix/named.conf",
113     dest    => "root\@$machine:". $export->option('named_conf'),
114   } ) or die "rsync to $machine failed: ". join(" / ", $rsync->err);
115 #  warn $rsync->out;
116
117   ssh("root\@$machine", 'ndc reload');
118
119 }
120
121 close NAMED_CONF;
122
123 foreach my $sexport ( @sexports ) { #false laziness with above
124
125   my $machine = $sexport->machine;
126   my $prefix = "$spooldir/$machine";
127
128   #prevent old domain files from piling up
129   #rmtree "$prefix" or die "can't rmtree $prefix.db: $!";
130
131   mkdir $prefix, 0700 unless -d $prefix;
132
133   open(NAMED_CONF,">$prefix/named.conf")
134     or die "can't open $prefix/named.conf: $!";
135
136   open(CONF_HEADER,"<$prefix/named.conf.HEADER")
137     or die "can't open $prefix/named.conf.HEADER: $!";
138   while (<CONF_HEADER>) { print NAMED_CONF $_; }
139   close CONF_HEADER;
140
141   my $masters = $sexport->option('master');
142
143   #false laziness with  freeside-sqlradius-reset 
144   my @svc_domain =
145     map { qsearchs('svc_domain', { 'svcnum' => $_->svcnum } ) }
146       map { qsearch('cust_svc', { 'svcpart' => $_->svcpart } ) }
147         grep { qsearch('cust_svc', { 'svcpart' => $_->svcpart } ) }
148           $sexport->export_svc;
149
150   foreach my $svc_domain ( @svc_domain ) {
151     my $domain = $svc_domain->domain;
152     print NAMED_CONF <<END;
153 zone "$domain" {
154         type slave;
155         file "db.$domain";
156         masters { $masters; };
157 };
158
159 END
160
161   }
162
163   $rsync->exec( {
164     src     => "$prefix/named.conf",
165     dest    => "root\@$machine:". $sexport->option('named_conf'),
166   } ) or die "rsync to $machine failed: ". join(" / ", $rsync->err);
167 #  warn $rsync->out;
168
169   ssh("root\@$machine", 'ndc reload');
170
171 }
172 close NAMED_CONF;
173
174 # -----
175
176 sub usage {
177   die "Usage:\n  bind.export user\n"; 
178 }
179