web-dev-qa-db-fra.com

Vérifier la validité de l'IP

Comment vérifier la validité d'une adresse IP dans un script Shell, comprise entre 0.0.0.0 et 255.255.255.255

19
AlwaysALearner

Si vous utilisez bash, vous pouvez faire une simple correspondance regex pour le motif, sans valider les quads:

#!/usr/bin/env bash

ip=1.2.3.4

if [[ $ip =~ ^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
  echo "success"
else
  echo "fail"
fi

Si vous êtes coincé avec un shell POSIX, vous pouvez utiliser expr pour faire la même chose, en utilisant BRE au lieu de ERE:

#!/bin/sh

ip=1.2.3.4

if expr "$ip" : '[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*$' >/dev/null; then
  echo "success"
else
  echo "fail"
fi

Notez que expr suppose que votre expression rationnelle est ancrée à gauche de la chaîne, de sorte que le ^ initial est inutile.

S'il est important de vérifier que chaque quad est inférieur à 256, vous aurez évidemment besoin de plus de code:

#!/bin/sh

ip=${1:-1.2.3.4}

if expr "$ip" : '[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*$' >/dev/null; then
  for i in 1 2 3 4; do
    if [ $(echo "$ip" | cut -d. -f$i) -gt 255 ]; then
      echo "fail ($ip)"
      exit 1
    fi
  done
  echo "success ($ip)"
  exit 0
else
  echo "fail ($ip)"
  exit 1
fi

Ou peut-être même avec moins de tuyaux:

#!/bin/sh

ip=${1:-1.2.3.4}

if expr "$ip" : '[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*\.[0-9][0-9]*$' >/dev/null; then
  IFS=.
  set $ip
  for quad in 1 2 3 4; do
    if eval [ \$$quad -gt 255 ]; then
      echo "fail ($ip)"
      exit 1
    fi
  done
  echo "success ($ip)"
  exit 0
else
  echo "fail ($ip)"
  exit 1
fi

Ou encore, si votre shell est bash, vous pouvez utiliser une expression régulière fastidieuse pour la validation quad, si vous n'aimez pas l'arithmétique:

#!/usr/bin/env bash

ip=${1:-1.2.3.4}

re='^(0*(1?[0-9]{1,2}|2([0-4][0-9]|5[0-5]))\.){3}'
 re+='0*(1?[0-9]{1,2}|2([‌​0-4][0-9]|5[0-5]))$'

if [[ $ip =~ $re ]]; then
  echo "success"
else
  echo "fail"
fi

Cela pourrait également être exprimé en BRE, mais c'est plus typant que j'ai dans mes doigts.

Et enfin, si vous aimez l’idée de mettre cette fonctionnalité ... dans une fonction:

#!/usr/bin/env bash

ip=${1:-1.2.3.4}

ipvalid() {
  # Set up local variables
  local ip=${1:-1.2.3.4}
  local IFS=.; local -a a=($ip)
  # Start with a regex format test
  [[ $ip =~ ^[0-9]+(\.[0-9]+){3}$ ]] || return 1
  # Test values of quads
  local quad
  for quad in {0..3}; do
    [[ "${a[$quad]}" -gt 255 ]] && return 1
  done
  return 0
}

if ipvalid "$ip"; then
  echo "success ($ip)"
  exit 0
else
  echo "fail ($ip)"
  exit 1
fi

Vous pouvez le faire de plusieurs façons. Je vous en ai montré quelques-uns.

37
ghoti

Utilisez ipcalc

$ ipcalc -cs 10.10.10.257 && echo vail_ip || echo invalid_ip
invalid_ip
6
Nasimuddin Ansari

Je crois que ce script fait ce que vous voulez: http://www.linuxjournal.com/content/validating-ip-address-bash-script

Modifier, y compris le code comme suggéré ci-dessous:

function valid_ip()
{
local  ip=$1
local  stat=1

if [[ $ip =~ ^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$ ]]; then
    OIFS=$IFS
    IFS='.'
    ip=($ip)
    IFS=$OIFS
    [[ ${ip[0]} -le 255 && ${ip[1]} -le 255 \
        && ${ip[2]} -le 255 && ${ip[3]} -le 255 ]]
    stat=$?
fi
return $stat
}
4
shannonman

Cette seule expression rationnelle doit valider uniquement les adresses comprises entre 0.0.0.0 et 255.255.255.255:

#!/bin/bash

ip="1.2.3.4"

if [[ "$ip" =~ ^(([1-9]?[0-9]|1[0-9][0-9]|2([0-4][0-9]|5[0-5]))\.){3}([1-9]?[0-9]|1[0-9][0-9]|2([0-4][0-9]|5[0-5]))$ ]]; then
  echo "success"
else
  echo "fail"
fi
2
Jon

Les solutions typiques à cela semblent toutes utiliser des expressions régulières, mais il me semble que ce serait une meilleure approche de faire quelque chose comme:

if echo "$ip" | { IFS=. read a b c d e;
    test "$a" -ge 0 && test "$a" -le 255 &&
    test "$b" -ge 0 && test "$b" -le 255 &&
    test "$c" -ge 0 && test "$c" -le 255 &&
    test "$d" -ge 0 && test "$d" -le 255 &&
    test -z "$e"; }; then echo is valid; fi
1
William Pursell

j'ai modifié tous les codes et trouvé que cela était utile.

#!/bin/bash

ip="256.10.10.100"

if [[ "$ip" =~ (([01]{,1}[0-9]{1,2}|2[0-4][0-9]|25[0-5])\.([01]{,1}[0-9]{1,2}|2[0-4][0-9]|25[0-5])\.([01]{,1}[0-9]{1,2}|2[0-4][0-9]|25[0-5])\.([01]{,1}[0-9]{1,2}|2[0-4][0-9]|25[0-5]))$ ]]; then
  echo "success"
else
  echo "fail"
fi
1
DirectedSoul

J'ai trouvé en dessous de scrip ICI que je me suis senti très utile.

#!/bin/bash

# Test an IP address for validity:
# Usage:
#      valid_ip IP_ADDRESS
#      if [[ $? -eq 0 ]]; then echo good; else echo bad; fi
#   OR
#      if valid_ip IP_ADDRESS; then echo good; else echo bad; fi
#
function valid_ip()
{
    local  ip=$1
    local  stat=1

    if [[ $ip =~ ^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$ ]]; then
        OIFS=$IFS
        IFS='.'
        ip=($ip)
        IFS=$OIFS
        [[ ${ip[0]} -le 255 && ${ip[1]} -le 255 \
            && ${ip[2]} -le 255 && ${ip[3]} -le 255 ]]
        stat=$?
    fi
    return $stat
}
1

Pour ce faire, je préfère utiliser ipcalc, à condition que mon script ne soit pas nécessairement portable. 

ipcalc 1.1.1.355                                                                         
INVALID ADDRESS: 1.1.1.355

Address:   192.168.1.1          11000000.10101000.00000001. 00000001
Netmask:   255.255.255.0 = 24   11111111.11111111.11111111. 00000000
Wildcard:  0.0.0.255            00000000.00000000.00000000. 11111111
=>
Network:   192.168.1.0/24       11000000.10101000.00000001. 00000000
HostMin:   192.168.1.1          11000000.10101000.00000001. 00000001
HostMax:   192.168.1.254        11000000.10101000.00000001. 11111110
Broadcast: 192.168.1.255        11000000.10101000.00000001. 11111111
Hosts/Net: 254                   Class C, Private Internet

Il y a une belle page montrant comment l'utiliser dans les scripts, etc., ici: Notes de SleeplessBeastie

0
Adam Bowen
#!/bin/bash
read -p " ip: " req_ipadr
#
ip_full=$(echo $req_ipadr | sed -n 's/^\(\(\([1-9][0-9]\?\|[1][0-9]\{0,2\}\|[2][0-4][0-9]\|[2][5][0-4]\)\.\)\{3\}\([1-9][0-9]\?\|[1][0-9]\{0,2\}\|[2][0-4][0-9]\|[2][5][0-4]\)\)$/\1/p')
#
[ "$ip_full" != "" ] && echo "$req_ipadr vaild ip" || echo "$req_ipadr invaild ip"
0
TJW

Perl a un excellent module Regexp :: Common pour valider diverses choses:

Perl -MRegexp::Common=net -e 'exit(shift() !~ /^$RE{net}{IPv4}$/)' $ipaddr

Vous devrez peut-être d'abord Sudo cpan install Regexp::Common

Je l'envelopperais dans une fonction:

valid_ip() {
  Perl -MRegexp::Common=net -e 'exit(shift() !~ /^$RE{net}{IPv4}$/)' "$1"
}

if valid_ip 123.234.345.456; then
  echo OK
else
  echo INVALID
fi
0
glenn jackman