LinuxQuestions.org

LinuxQuestions.org (/questions/)
-   Linux - Newbie (https://www.linuxquestions.org/questions/linux-newbie-8/)
-   -   DNS query script (https://www.linuxquestions.org/questions/linux-newbie-8/dns-query-script-460815/)

Braynid 07-04-2006 03:34 AM

DNS query script
 
Hello,
I am working with a couple of friends on a linux toolbox to use at work and we have some scripts that are a must have. We have managed some of them but i have some trouble with one, so here goes:

I need a script that makes a DNS query, shows the pointed IP, verifies if the given DNS is registered on a specific DNS server and shows the mx entry if it exists.

I have a Ubuntu RC 6.06 server on my machine.
I would really appreciate the help.

Thanks!

Tinkster 07-04-2006 03:58 AM

http://search.cpan.org/~darren/Net-N...et/Nslookup.pm


If that's overkill look at dig, things like
dig google.com
or
dig google.com MX +noall +answer
may be what you need.


Cheers,
Tink

Braynid 07-04-2006 04:58 AM

Ok, so i have installed nslookup, that only helps me partially, and it's kind of hard to use. I didn't manage to get a MX query.
On the other hand 'dig' looks helpful but i just could not find a .tar.gz archive dor dowload on google (shame on me).
Could you give me some scripting tips to?

Thanks

UPDATE:
Ok so i found 'dig' but it looks very hard to me to use dig+nslookup in a script to obtain only the information i need... any ideas?

timmeke 07-04-2006 05:18 AM

nslookup is slightly deprecated. "dig" or "host" should be better.
nslookup is designed to be used interactively, which indeed makes it hard to include in scripts.
To lookup up MX records using nslookup:
Code:

nslookup
nslookup_prompt> set type=mx
nslookup_prompt> <enter_domain_to_search>
=> nslookup will report back the MX records found (if any)

To get dig, you need the bind-utils package. Download and install that.

Maybe you can use your package manager (apt-get) to install "bind-utils" for you?

Braynid 07-04-2006 05:34 AM

root@MainThinkTank:~# dig -t mx google.com
Code:

; <<>> DiG 9.3.2 <<>> -t mx google.com
;; global options:  printcmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 18951
;; flags: qr rd ra; QUERY: 1, ANSWER: 4, AUTHORITY: 0, ADDITIONAL: 0

;; QUESTION SECTION:
;google.com.                    IN      MX

;; ANSWER SECTION:
google.com.            1895    IN      MX      10 smtp3.google.com.
google.com.            1895    IN      MX      10 smtp4.google.com.
google.com.            1895    IN      MX      10 smtp1.google.com.
google.com.            1895    IN      MX      10 smtp2.google.com.

;; Query time: 12 msec
;; SERVER: 193.231.236.30#53(193.231.236.30)
;; WHEN: Tue Jul  4 13:28:49 2006
;; MSG SIZE  rcvd: 116


Ok so dig works fine, but how do I use it in a script? it shows a lot of usless information (to me)...

timmeke 07-04-2006 06:02 AM

Maybe you can add a little output interpretation to dig?
ie
Code:

dig -t mx google.com | grep -E -v '^;' | grep MX
That should filter out all lines with MX and ignore any comments (lines starting with ';').

An alternative would be to write a simple parser (Perl/awk) that would accept the dig output as input and print
only the "answer section" as output.

Or try adding options like "+short", "+nocomments", "+nostats", "+noquestion", "+noauthority", "+noadditional" to dig.

Edit: see man dig

Braynid 07-04-2006 08:48 AM

Ok so now i have:
Code:

function dns ()

{
echo DNS resolve:

dig +nocmd +nostats +nocomments $1

echo Inregistrari MX:

host -t mx $1
}

Thanks to timmeke and what I found out on my own, but there are still 2 things that bother me..
-How do i do to make the function available for all the users, now it's in the .bashrc of root, and i
don't want to copy it in the .bashrc of all the users?
-How do I do to identify if a DNS or IP is handled by a special name server, as in ns1.host.com and ns2.host.com ( obviously i have the IP for the given nameservers). So i want to list something like: 'The given host is (or is not) handled by ns1.host.com!'

I will try to manage it but I really appreciate the help.
Thanks again.

JimBass 07-04-2006 08:59 AM

To give other users, simply copy the code from root's .bashrc, and paste it into a new file, maybe dns-check or whatever you like. Move that file to /usr/local/bin/, or /usr/bin/, which are included on everyone's PATH. Then just tweak the permissions, probablly to 755 owned by root:root or root:staff. Then anyone can use your script without being able to modify it.

My shells scripts are generally weak, but it seems easy to me to compare the answer returned against the IP addresses you have, and to print something if they match, or don't, whatever is easier. Something like:
Code:

if $ANSWER == W.X.Y.Z
          echo "Hosted by bad server"
      elseif $ANSWER != W.X.Y.Z
          echo "Hosted by good server"

Something along those lines should do it for you.

Peace,
JimBass

Braynid 07-04-2006 09:16 AM

FIrst of all thanks a lot for the usr/bin/ thing, works like a charm!

Then about this:
Quote:

Originally Posted by JimBass
Something like:
Code:

if $ANSWER == W.X.Y.Z
          echo "Hosted by bad server"
      elseif $ANSWER != W.X.Y.Z
          echo "Hosted by good server"

JimBass

It's what I was thinking but the problem is what is $ANSWER, how do i define this, what is it? I mean how do I obtain the $ANSWER variable form let's say 'host' or 'nslookup' or whatever command?

Ok and as an update there seem to be something wrong, when i add the script in the funcion, i execute 'export' and then i relogin i get
Code:

-bash: /root/.bashrc: line 108: syntax error near unexpected token `}'
-bash: /root/.bashrc: line 108: `}'

The exact lines I added are:
Code:

if nslookup $1 == 193.231.236.25
          echo "Hosted by RDS"
        elseif nslookup $1  == 193.231.236.3
                echo "Hosted by RDS"


timmeke 07-04-2006 09:43 AM

Use backticks `` or $(command) syntax to capture the output of commands in shell variables.
I would suggest using grep/cut/sed or something like that to get the server names from the individual lines of output.

In the examples below, I'll demonstrate how you can handle the output of "host". However, for your exact needs, "host"'s output may not be sufficient. But you'll get the general idea...

Code:

ANSWER=`host -t mx $1 |grep 'handled by' | cut -d' ' -f7 | sed -e 's/\.$//';
#followed by JimBass's solution

A small syntactical remark: in Bash, it's not "elseif", it's "elif".

You may also consider using regular expression matching like:
Code:

host -t mx $1 | grep -E 'W\.X\.Y\.Z\.$';
#Now, we can check the error code of grep to see if it found a match or not
RETVAL=$?
if (( $RETVAL == 0 )); then
  #Matching lines were found
elif (( $RETVAL == 1 )); then
  #No matches found
else
  #Error occurred
fi;

An alternative approach to sharing your dns function is to put it in /etc/bashrc, which is the default bashrc that applies to all Bash users.
A separate script, ie in /usr/bin or something, is definitely a better approach though.

Braynid 07-04-2006 10:57 AM

I can realize what you are trying to say but could you please direct me to another source of 'grep' pattern use then 'man' ?

I didn't understand very much of the pattern you used there... ( i am used to C++ as a programming language but i don't know bash syntax..)

So all in all could you please direct me to some source where from i can get more information about bash and grep ?

Thanks!

Braynid 07-04-2006 03:15 PM

Ok now the function looks something like this:
Code:

function dns ()

{
echo DNS resolve:

dig +nocmd +nostats +nocomments $1

echo Inregistrari MX:

host -t mx $1

host $1 | grep -E '193\.231\.236\.10\.$';
#Now, we can check the error code of grep to see if it found a match or not
RETVAL=$?
if (( $RETVAL == 0 )); then echo "Hosted by RDS"
  #Matching lines were found
elif (( $RETVAL == 1 )); then echo "Not hosted by RDS"
  #No matches found
else echo "Eroare"
  #Error occurred
fi;

}

In you could just help me a little bit with the sintax here, i thing the problem is in the 'grep' phrase...

So all i want to do is echo "The domain in handled by Host" if a given host uses the nameservers that i provide.
So how do i do this? I want to test if "www.someone's.host.com" is handled by "given.ns1.com" or "given.ns2.com" and if it is echo "The domain is handled by given.ns1.com", could you please help me do this?

Thanks!

JimBass 07-04-2006 03:46 PM

This line
Quote:

host $1 | grep -E '193\.231\.236\.10\.$';
asks your machine to get the host info for a given domain, then checks the answer to see if the ip address 192.231.236.10 is in it, and answer according to what you set.

Some problems with that - host doesn't tell you a thing about name servers. If you want to find out about the nameservers that are authoritative for a domain, you need to use dig. Issuing the command "host google.com", will spit out the A records for google, and the mail servers, but nothing about DNS.

Your dig command, "dig +nocmd +nostats +nocomments" does give info about the authoritative DNS servers for a domain. You could use things like cut, sed, awk etc to get to the core of that data (get it to isolate the IP addresses or names of the DNS servers, which we have already shown how to do), and then compare those answers to what you are looking for, also shown how.

I would find it somewhat odd to want to be an authoritative DNS for sites, even client's sites. Are you maybe looking for the mail exchangers and not the DNS?

Peace,
JimBass

Braynid 07-04-2006 04:41 PM

Ok, in the light of the new information given by JimBass I have developed a method th achieve what I need, with:
Code:

dig @ns2.rdsnet.ro -t ns +nocmd +nostats +nocomments HOST
I can now see the NS the given HOST uses, but i am so verry lost in 'grep', 'cut' and 'sed', I am really new at this :o !

Code:

root@MainThinkTank:~# dig @ns2.rdsnet.ro -t ns +nocmd +nostats +nocomments rdslink.ro
;rdslink.ro.                    IN      NS
rdslink.ro.            43200  IN      NS      ns2.rdsnet.ro.
rdslink.ro.            43200  IN      NS      ns1.rdsnet.ro.
ns1.rdsnet.ro.          1800    IN      A      193.231.236.17
ns2.rdsnet.ro.          1800    IN      A      193.231.236.10

So i need to search the output of dig for the IP 193.231.236.17, if it can be found VAR=1 if not the IP 193.231.236.10 is searched, if it is found VAR=1, if not VAR=0.
Or as a alternative i could make a variable VAR='dig @ns2.rdsnet.ro -t ns +nocmd +nostats +nocomments HOST' then we cut the dig output so that VAR=193.231.236.17 if it's there, if not VAR =0. But how do i do this?

Due to my clear difficulty of managing this in a timely manner, can you please help me?

So that you know i need this to find out if a client with a given host uses my ISP nameservers :)

Tinkster 07-04-2006 07:01 PM

dig @ns2.rdsnet.ro -t ns +nocmd +nostats +nocomments rdslink.ro | awk ' $4 == "A" {print $5}'

?

I'm not sure I understand what you're trying to achieve, or why you're trying
to grep for fixed IPs in an arbitrary A record.


Cheers,
Tink


All times are GMT -5. The time now is 12:22 AM.