File Coverage

blib/lib/Net/DNS/Check/NSQuery.pm
Criterion Covered Total %
statement 18 157 11.4
branch 0 66 0.0
condition 0 17 0.0
subroutine 6 23 26.0
pod 0 15 0.0
total 24 278 8.6


line stmt bran cond sub pod time code
1             package Net::DNS::Check::NSQuery;
2            
3 1     1   5 use strict;
  1         2  
  1         34  
4              
5 1     1   5 use Net::DNS;
  1         1  
  1         207  
6 1     1   7 use Net::DNS::Check::Host;
  1         1  
  1         21  
7 1     1   5 use Net::DNS::Check::HostsList;
  1         2  
  1         29  
8 1     1   5 use Net::DNS::Check::Config;
  1         2  
  1         18  
9 1     1   5 use Carp;
  1         2  
  1         1913  
10             # use Data::Dumper;
11            
12             sub new {
13 0     0 0   my ($class, %param) = @_;
14            
15              
16 0 0 0       return 0 if (!$param{domain} || ! $param{nserver});
17            
18 0           my $self = {};
19              
20             # Nome del dominio
21 0           $self->{domain} = $param{domain};
22 0           $self->{qdomain} = $param{domain};
23 0           $self->{qdomain} =~ s/\./\\./g;
24              
25             # Nome del namserver da interrogare
26 0           $self->{nserver} = $param{nserver};
27              
28 0           my $fatal = 0;
29 0           my $msg_error =<
30              
31             FATAL ERROR
32             ===============
33             Wrong call of constructor: $class
34             ERROR
35              
36              
37 0 0         unless ( $self->{domain} ) {
38 0           $fatal = 1;
39 0           $msg_error .= "\ndomain param not found!\n";
40             }
41              
42 0 0         unless ( $self->{nserver} ) {
43 0           $fatal = 1;
44 0           $msg_error .= "\nnserver param not found!\n";
45             }
46              
47 0 0         if ( $fatal ) {
48 0           confess($msg_error . "\n");
49             }
50              
51              
52              
53             # IP del namserver da interrogare
54             # il parametro e' facoltativo. Se non viene passato
55             # viene utilizzata la ricorsione per determinare
56             # l'IP. Ovviamente per i nameserver appartenenti al dominio
57             # sul quale staimo operando DOVREBBE essere passato l'IP.
58             # Se non viene passato l'IP per quest'ultimi si utilizza
59             # la ricorsione che funzionera' solo se il dominio e' gia'
60             # esistente
61 0           $self->{ip} = $param{ip};
62              
63              
64 0   0       $self->{config} = $param{config} || new Net::DNS::Check::Config;
65              
66 0 0         if ( defined $param{debug} ) {
67 0           $self->{debug} = $param{debug};
68             } else {
69 0           $self->{debug} = $self->{config}->debug_default();
70             }
71              
72              
73            
74             # External/General Hostslist.
75 0   0       $self->{hostslist} = $param{hostslist} || new Net::DNS::Check::HostsList(
76             domain => $self->{domain},
77             debug => ($self->{debug} > 2),
78             config => $self->{config}
79             );
80              
81             # Internal HostsList
82 0           $self->{myhostslist} = new Net::DNS::Check::HostsList(
83             domain => $self->{domain},
84             debug => ($self->{debug} > 2),
85             config => $self->{config}
86             );
87            
88              
89              
90              
91             # Array of NS or MX hostnames
92 0           $self->{result}->{NS} = [];
93 0           $self->{result}->{MX} = [];
94              
95              
96 0           bless $self, $class;
97              
98 0 0         if ($self->{debug} > 0 ) {
99 0           print <
100              
101             Query for RR ANY for $self->{domain} to $self->{nserver}
102             =======================================================
103             DEBUG
104             }
105              
106              
107              
108             # Creiamo l'oggetto resolver usando il resolver di sistema
109 0           $self->{res} = Net::DNS::Resolver->new(
110             recurse => 0,
111             debug => ($self->{debug} > 2),
112             retrans => $self->{config}->query_retrans,
113             retry => $self->{config}->query_retry,
114             tcp_timeout => $self->{config}->query_tcp_timeout
115             );
116              
117              
118             # La add_host crea un oggetto host e lo aggiunge alla lista se non esiste
119             # o ritorna l'oggetto host gia' presente nella hostslist
120             # $self->{host} = $self->{hostslist}->add_host( $self->{nserver}, $self->{ip} );
121              
122              
123             # if an ip doesn't exist we try to find it using add_host function
124             # (that it uses hostslist object functions)
125 0 0         unless ( @{$self->{ip}} ) {
  0            
126              
127 0 0         if ($self->{debug} > 0 ) {
128 0           my $ips = join(' ', @{$self->{ip}});
  0            
129 0           print <
130             Search for $self->{nserver} IP
131              
132             DEBUG
133             }
134              
135 0           $self->{host} = $self->_add_host( $self->{nserver} );
136 0           $self->{ip} = $self->{host}->get_ip();
137              
138             }
139              
140             # We found an IP address to query so we make query
141             # .... otherwise we have an error
142 0 0         if ( @{$self->{ip}} ) {
  0            
143             # $self->{type} = $type;
144              
145 0 0         if ($self->{debug} > 0 ) {
146 0           my $ips = join(' ', @{$self->{ip}});
  0            
147 0           print <
148             $self->{nserver} IP : $ips
149             DEBUG
150             }
151              
152             # We set resolver to the ip found
153 0           $self->{res}->nameservers(@{ $self->{ip} });
  0            
154              
155 0 0         if ($self->{debug} > 2) {
156 0           print "\n\n";
157 0           $self->{res}->print;
158             }
159              
160             # Query of type ANY for $self->{domain} to $self->{ip}
161 0           $self->_queryANY();
162              
163             } else {
164              
165 0           $self->{error} = 'NOIP';
166              
167 0 0         if ($self->{debug} > 0 ) {
168 0           my $ips = join(' ', @{$self->{ip}});
  0            
169 0           print <
170             $self->{nserver} IP : Not Found
171             DEBUG
172             }
173             }
174              
175 0           return $self;
176             }
177              
178              
179             sub _queryANY() {
180 0     0     my $self = shift;
181              
182             # Creazione query per il dominio
183 0           my $packet = $self->{res}->send($self->{domain},'ANY');
184              
185 0 0         if ($packet) {
186 0           $self->{result}->{header} = $packet->header;
187              
188 0 0         if ($self->{debug} > 0 ) {
189 0           print <
190             Getting query answer
191              
192             DEBUG
193             }
194              
195 0 0         if ($self->{debug} > 1 ) {
196 0           my $result = $packet->string;
197 0           print <
198             $result
199             DEBUG
200             }
201              
202              
203 0 0 0       if ( $self->header_aa() && scalar $packet->answer() ) {
204 0           foreach my $rr ( $packet->answer ) {
205              
206 0 0         if ($rr->type eq 'SOA') {
207 0           $self->{result}->{SOA} = $rr;
208 0           next;
209             }
210            
211 0 0         if ($rr->type eq 'NS') {
212 0           push (@{$self->{result}->{NS}}, lc($rr->{nsdname}));
  0            
213 0           $self->_add_host( lc($rr->{nsdname}) );
214 0           next;
215             }
216            
217 0 0         if ($rr->type eq 'MX') {
218 0           push (@{$self->{result}->{MX}}, lc($rr->{exchange}));
  0            
219 0           $self->_add_host( lc($rr->{exchange}) );
220 0           next;
221             }
222             }
223             } else {
224 0           $self->{error} = 'NOAUTH';
225             }
226             } else {
227              
228             # Query Error... no answer (time out)
229 0           $self->{error} = 'NOANSWER';
230              
231 0 0         if ($self->{debug} > 0 ) {
232 0           my $qerror = $self->{res}->errorstring;
233 0           print <
234             Query Error: $qerror
235             DEBUG
236             }
237              
238             }
239             }
240              
241              
242              
243             sub _add_host() {
244 0     0     my $self = shift;
245 0           my ($hostname) = shift;
246              
247 0 0         unless ($hostname) {
248 0           confess("hostname parm not found!\n");
249             }
250              
251 0           my ($host, @temp);
252              
253 0           @temp = split('\.', $self->{domain});
254 0           my $domcount = scalar @temp;
255              
256 0           @temp = split('\.', $hostname);
257 0           my $hostcount = (scalar @temp)-1;
258              
259              
260             # Questo e' da rivedere.
261 0 0 0       if ( ($hostname eq $self->{domain}) || $hostname =~ /.*$self->{qdomain}$/ && $domcount == $hostcount ) {
      0        
262             # Se l'hostname fa parte del dominio lo aggiungiamo alla hostslist
263             # locale e usiamo per la risluzione l'ip del namserver
264             # con cui abbiamo creato l'oggetto NSQuery
265             #print "inside ";
266 0           $host = $self->{myhostslist}->add_host( hostname => $hostname, ip => $self->{ip} );
267             } else {
268             # Se l'hostname non fa parte del dominio lo aggiungiamo alla
269             # hostslist globale
270             #print "outside ";
271 0           $host = $self->{hostslist}->add_host( hostname => $hostname );
272             }
273 0           return $host;
274             }
275              
276              
277              
278             # Riporta 1 se le risposte del dns sono autoritativo
279             # Riporta 0 se la risposta non e' autoritativa
280             # Riporta -1 se non c'e' nessun header
281             sub header_aa() {
282 0     0 0   my $self = shift;
283              
284 0 0         return undef if (! defined $self->{result}->{header});
285              
286 0           return $self->{result}->{header}->aa();
287             }
288              
289              
290             # Riporta l'oggetto Net::DNS::Header oppure false se non c'e' l'oggetto
291             sub header() {
292 0     0 0   my $self = shift;
293              
294 0 0         return 0 if (! defined $self->{result}->{header});
295              
296 0           return $self->{result}->{header};
297             }
298              
299              
300             # Riporta un array vuoto se non ci sono record NS altrimenti riporta
301             # l'array contenente la lista dei DNS autoritativi
302             sub ns_list() {
303 0     0 0   my $self = shift;
304              
305 0 0         return () unless defined $self->{result}->{NS};
306              
307 0           return @{ $self->{result}->{NS} };
  0            
308             }
309              
310              
311             # Riporta un array vuoto se non ci sono record MX altrimenti
312             # Altrimenti riporta l'array dei contenente la lista degli
313             # exchange server
314             sub mx_list() {
315 0     0 0   my $self = shift;
316              
317 0 0         return () unless defined $self->{result}->{MX};
318              
319 0           return @{ $self->{result}->{MX} };
  0            
320             }
321              
322             # Riporta undef se non esiste un'oggetto SOA o non esiste un master altrimenti riporta il master nameserver che appare nel SOA
323             sub soa_mname() {
324 0     0 0   my $self = shift;
325              
326 0 0         return if (! defined $self->{result}->{SOA} );
327              
328 0           return lc($self->{result}->{SOA}->mname());
329             }
330              
331             # Riporta undef se non esiste un'oggetto SOA altrimenti
332             # Riporta il serial che appare nel SOA
333             sub soa_serial() {
334 0     0 0   my $self = shift;
335              
336 0 0         return if (! defined $self->{result}->{SOA} );
337              
338 0           return $self->{result}->{SOA}->serial();
339             }
340              
341              
342              
343             # Riporta 0 se non esiste un'oggetto SOA o non esiste un refresh
344             # Riporta il refresh che che appare nel SOA
345             sub soa_refresh() {
346 0     0 0   my $self = shift;
347              
348 0 0         return 0 if (! defined $self->{result}->{SOA} );
349              
350 0           return $self->{result}->{SOA}->refresh();
351             }
352              
353             # Riporta 0 se non esiste un'oggetto SOA o non esiste un retry
354             # Riporta il retry che che appare nel SOA
355             sub soa_retry() {
356 0     0 0   my $self = shift;
357              
358 0 0         return 0 if (! defined $self->{result}->{SOA} );
359              
360 0           return $self->{result}->{SOA}->retry();
361             }
362              
363             # Riporta 0 se non esiste un'oggetto SOA o non esiste un expire
364             # Riporta il expire che che appare nel SOA
365             sub soa_expire() {
366 0     0 0   my $self = shift;
367              
368 0 0         return 0 if (! defined $self->{result}->{SOA} );
369              
370 0           return $self->{result}->{SOA}->expire();
371             }
372              
373             # Riporta 0 se non esiste un'oggetto SOA o non esiste un minimum
374             # Riporta il minimum che che appare nel SOA
375             sub soa_minimum() {
376 0     0 0   my $self = shift;
377              
378 0 0         return 0 if (! defined $self->{result}->{SOA} );
379              
380 0           return $self->{result}->{SOA}->minimum();
381             }
382              
383             # Riporta 0 se non esiste un'oggetto SOA o non esiste un minimum
384             # Riporta il minimum che che appare nel SOA
385             sub soa_mail() {
386 0     0 0   my $self = shift;
387              
388 0 0         return 0 if (! defined $self->{result}->{SOA} );
389              
390 0           return $self->{result}->{SOA}->rname();
391             }
392              
393             # Riporta il nome del nameserver che stiamo interrogando
394             sub ns_name() {
395 0     0 0   my $self = shift;
396              
397 0           return $self->{nserver};
398             }
399              
400              
401             sub error() {
402 0     0 0   my $self = shift;
403              
404 0           return $self->{error};
405             }
406              
407             sub hostslist() {
408 0     0 0   my $self = shift;
409              
410 0           return $self->{myhostslist};
411             }
412              
413             1;
414              
415             __END__