in reply to Net::DNS::Resolver doesn't return the desired domain name
First of all, after re-formatting, adding the usual use strict; use warnings; and adding the missing use Net::DNS::Resolver and adding the missing variables, i get Net::DNS::Resolver->new(): nameservers must be an arrayref.
Let's fix that and add some actual nameservers and an IP to query:
#!/usr/bin/env perl use strict; use warnings; use Net::DNS::Resolver; my $l_ip = '216.92.34.251'; # one of the perlmonks.org servers my @nameservers = qw[8.8.8.8 8.8.4.4]; # Googles DNS Servers my $l_dns_name = $l_ip; my $l_dns = Net::DNS::Resolver->new( nameservers => \@nameservers ); my $l_response = $l_dns->query($l_ip); if($l_dns->errorstring eq 'NOERROR') { my $l_record; foreach $l_record ($l_response->answer()) { print 'Got: ', $l_record->type(), ' -> ', $l_record->name(), + "\n"; if($l_record->type() eq 'PTR') { $l_dns_name = $l_record->name(); last; } } } else { print $l_dns->errorstring, "\n"; }
This gives us the result Got: PTR -> 251.34.92.216.in-addr.arpa
Took me a while playing with the code and reading the docs to find out the problem. Turns out that you have to use type-specific methods to parse the part of the answer you actually want. The complete answer from the nameserver is something like this record:
251.34.92.216.in-addr.arpa. 6883 IN PTR perlmonks.org.
name() returns the first part, the name ("key") of that record. But what you want is the second part (the "value"), for which you need type-specific query functions, in this case ptrdname() from the Net::DNS::RR::PTR module.
So, here's what i finally ended up with:
#!/usr/bin/env perl use strict; use warnings; use Net::DNS::Resolver; my $destip = '216.92.34.251'; # one of the perlmonks.org servers my @nameservers = qw[8.8.8.8 8.8.4.4]; # Googles DNS Servers my $ptr = getHostname($destip, \@nameservers, 'PTR'); print "Got name $ptr\n"; sub getHostname { my ($l_ip, $nameservers, $recordtype) = @_; my $l_dns_name = $l_ip; my $l_dns = Net::DNS::Resolver->new( nameservers => \@nameservers, + $recordtype ); my $l_response = $l_dns->query($l_ip); if(!defined($l_response)) { print "Error: Got no response\n"; return $l_ip; } if($l_dns->errorstring eq 'NOERROR') { my $l_record; foreach $l_record ($l_response->answer()) { print 'Got: ', $l_record->type(), ' -> ', $l_record->nam +e(), "\n"; if($l_record->type() eq 'PTR') { $l_dns_name = $l_record->ptrdname(); #$l_dns_name = $l_record->address(); last; } } } else { print $l_dns->errorstring, "\n"; } return $l_dns_name; }
Got: PTR -> 251.34.92.216.in-addr.arpa Got name perlmonks.org
Be aware: Not every IP will resolve to a hostname. You will need to add appropriate error handling as well as handling Nameserver connection and lookup errors of all kinds.
|
|---|
| Replies are listed 'Best First'. | |
|---|---|
|
Re^2: Net::DNS::Resolver doesn't return the desired domain name
by Robidu (Acolyte) on Jun 11, 2015 at 18:45 UTC | |
by cavac (Prior) on Jun 12, 2015 at 11:50 UTC |