web-dev-qa-db-fra.com

Comment vérifier si un port réseau est ouvert sur Linux?

Comment puis-je savoir si un certain port est ouvert/fermé sur Linux Ubuntu, pas un système distant, en utilisant python? Comment puis-je lister ces ports ouverts en python?

  • Netstat: Y a-t-il un moyen d'intégrer la sortie netstat avec python?
59
Fatima

Vous pouvez utiliser le module de socket pour vérifier simplement si un port est ouvert ou non.

Cela ressemblerait à quelque chose comme ça.

import socket
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
result = sock.connect_ex(('127.0.0.1',80))
if result == 0:
   print "Port is open"
else:
   print "Port is not open"
sock.close()
109
mrjandro

Si vous souhaitez utiliser ceci dans un contexte plus général, vous devez vous assurer que le socket que vous ouvrez est également fermé. Donc, le contrôle devrait ressembler davantage à ceci:

import socket
from contextlib import closing

def check_socket(Host, port):
    with closing(socket.socket(socket.AF_INET, socket.SOCK_STREAM)) as sock:
        if sock.connect_ex((Host, port)) == 0:
            print "Port is open"
        else:
            print "Port is not open"
68
Michael

Pour moi, les exemples ci-dessus seraient bloqués si le port n'était pas ouvert. La ligne 4 montre l’utilisation de settimeout pour empêcher la pendaison

import socket

sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(2)                                      #2 Second Timeout
result = sock.connect_ex(('127.0.0.1',80))
if result == 0:
  print 'port OPEN'
else:
  print 'port CLOSED, connect_ex returned: '+str(result)
31
Brent Kinser

Si vous ne vous souciez que de la machine locale, vous pouvez compter sur le paquet psutil. Vous pouvez soit:

  1. Vérifiez tous les ports utilisés par un pid spécifique:

    proc = psutil.Process(pid)
    print proc.connections()
    
  2. Vérifiez tous les ports utilisés sur la machine locale:

    print psutil.net_connections()
    

Cela fonctionne aussi sous Windows.

http://pythonhosted.org/psutil/

18
Joe

Dans le cas où vous testez TCP ports avec l'intention d'écouter dessus, il est préférable d'appeler réellement listen. L'approche avec tring pour se connecter ne "voit" pas les ports client des connexions établies, car personne ne écoutez sur ses notes, mais ces ports ne peuvent pas être utilisés pour les écouter.

import socket


def check_port(port, rais=True):
    """ True -- it's possible to listen on this port for TCP/IPv4 or TCP/IPv6
    connections. False -- otherwise.
    """
    try:
        sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        sock.bind(('127.0.0.1', port))
        sock.listen(5)
        sock.close()
        sock = socket.socket(socket.AF_INET6, socket.SOCK_STREAM)
        sock.bind(('::1', port))
        sock.listen(5)
        sock.close()
    except socket.error as e:
        return False
        if rais:
            raise RuntimeError(
                "The server is already running on port {0}".format(port))
    return True
2

L'outil Netstat analyse simplement certains fichiers/proc tels que/proc/net/tcp et les combine avec le contenu d'autres fichiers. Oui, c'est très spécifique à la plate-forme, mais vous pouvez vous en tenir à une solution exclusivement Linux. La documentation du noyau Linux décrit ces fichiers en détail afin que vous puissiez trouver comment les lire.

Veuillez également noter que votre question est trop ambiguë car "port" peut également signifier un port série (/ dev/ttyS * et analogues), un port parallèle, etc. J'ai utilisé à nouveau une compréhension d'une autre réponse, à savoir le port réseau, mais je vous demanderais de formuler vos questions avec plus de précision.

2
Netch

Nous venons d'ajouter à la solution de mrjandro un rapide piratage pour se débarrasser des simples erreurs de connexion/délais d'attente.

Vous pouvez ajuster le seuil en modifiant la valeur de la variable max_error_count et ajouter des notifications de tout type.

import socket

max_error_count = 10

def increase_error_count():
    # Quick hack to handle false Port not open errors 
    with open('ErrorCount.log') as f:
        for line in f:
            error_count = line
    error_count = int(error_count)
    print "Error counter: " + str(error_count)
    file = open('ErrorCount.log', 'w')
    file.write(str(error_count + 1))
    file.close()
    if error_count == max_error_count:
        # Send email, pushover, slack or do any other fancy stuff
        print "Sending out notification"
        # Reset error counter so it won't flood you with notifications
        file = open('ErrorCount.log', 'w')
        file.write('0')
        file.close()

sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(2) 
result = sock.connect_ex(('127.0.0.1',80))
if result == 0:
        print "Port is open"
else:
        print "Port is not open"
        increase_error_count()

Et vous trouverez ici une version Python 3 (syntaxe d'impression fixe)):

import socket

max_error_count = 10

def increase_error_count():
    # Quick hack to handle false Port not open errors
    with open('ErrorCount.log') as f:
        for line in f:
            error_count = line
    error_count = int(error_count)
    print ("Error counter: " + str(error_count))
    file = open('ErrorCount.log', 'w')
    file.write(str(error_count + 1))
    file.close()
    if error_count == max_error_count:
        # Send email, pushover, slack or do any other fancy stuff
        print ("Sending out notification")
        # Reset error counter so it won't flood you with notifications
        file = open('ErrorCount.log', 'w')
        file.write('0')
        file.close()

sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(2) 
result = sock.connect_ex(('127.0.0.1',80))
if result == 0:
        print ("Port is open")
else:
        print ("Port is not open")
        increase_error_count()
1
Pitto

S'il vous plaît vérifier la réponse de Michael et voter pour elle. C'est la bonne façon de vérifier les ports ouverts. Netstat et d'autres outils ne sont d'aucune utilité si vous développez des services ou des démons. Par exemple, je crée modbus TCP serveur et services client pour un réseau industriel. Les services peuvent écouter n'importe quel port, mais la question est de savoir si ce port est ouvert? Le programme va être utilisé dans différents endroits, et je ne peux pas tous les vérifier manuellement, alors voici ce que j'ai fait:

from contextlib import closing
import socket
class example:
    def __init__():

       self.machine_ip = socket.gethostbyname(socket.gethostname())
       self.ready:bool = self.check_socket()

    def check_socket(self)->bool:
        result:bool = True
        with closing(socket.socket(socket.AF_INET, socket.SOCK_STREAM)) as sock:
        modbus_tcp_port:int = 502
        if not sock.connect_ex((self.machine_ip, modbus_tcp_port)) == 0:
            result = False
        return result
1
Hadi

Voici un scanner de port multi-thread rapide:

from time import sleep
import socket, ipaddress, threading

max_threads = 50
final = {}
def check_port(ip, port):
    try:
        sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) # TCP
        #sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) # UDP
        socket.setdefaulttimeout(2.0) # seconds (float)
        result = sock.connect_ex((ip,port))
        if result == 0:
            # print ("Port is open")
            final[ip] = "OPEN"
        else:
            # print ("Port is closed/filtered")
            final[ip] = "CLOSED"
        sock.close()
    except:
        pass
port = 80
for ip in ipaddress.IPv4Network('192.168.1.0/24'): 
    threading.Thread(target=check_port, args=[str(ip), port]).start()
    #sleep(0.1)

# limit the number of threads.
while threading.active_count() > max_threads :
    sleep(1)

print(final)

Démo en direct

0
Pedro Lobito