简体   繁体   English

如何在python中检查网络接口上的数据传输?

[英]How can I check the data transfer on a network interface in python?

There is a socket method for getting the IP of a given network interface: 有一种socket方法可以获取给定网络接口的IP:

import socket
import fcntl
import struct

def get_ip_address(ifname):
    s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    return socket.inet_ntoa(fcntl.ioctl(
        s.fileno(),
        0x8915,  # SIOCGIFADDR
        struct.pack('256s', ifname[:15])
    )[20:24])

Which returns the following: 返回以下内容:

>>> get_ip_address('lo')
'127.0.0.1'

>>> get_ip_address('eth0')
'38.113.228.130'

Is there a similar method to return the network transfer of that interface? 是否有类似的方法来返回该接口的网络传输? I know I can read /proc/net/dev but I'd love a socket method. 我知道我可以读/proc/net/dev但我喜欢socket方法。

The best way to poll ethernet interface statistics is through SNMP... 轮询以太网接口统计信息的最佳方法是通过SNMP ...

  • It looks like you're using linux... if so, load up your snmpd with these options... after installing snmpd , in your /etc/defaults/snmpd (make sure the line with SNMPDOPTS looks like this): 看起来你正在使用linux ......如果是这样的话,请在你的/ etc / defaults / snmpd中安装snmpd之后加载你的snmpd ...(确保使用SNMPDOPTS的行看起来像这样):

    SNMPDOPTS='-Lsd -Lf /dev/null -u snmp -I -smux,usmConf,iquery,dlmod,diskio,lmSensors,hr_network,snmpEngine,system_mib,at,interface,ifTable,ipAddressTable,ifXTable,ip,cpu,tcpTable,udpTable,ipSystemStatsTable,ip,snmp_mib,tcp,icmp,udp,proc,memory,snmpNotifyTable,inetNetToMediaTable,ipSystemStatsTable,disk -Lsd -p /var/run/snmpd.pid'

  • You might also need to change the ro community to public See Note 1 and set your listening interfaces in /etc/snmp/snmpd.conf (if not on the loopback)... 您可能还需要将ro社区更改为public 参见注释1并在/etc/snmp/snmpd.conf设置您的侦听接口(如果不在环回上)...

  • Assuming you have a functional snmpd , at this point, you can poll ifHCInBytes and ifHCOutBytes See Note 2 for your interface(s) in question using this... 假设你有一个功能性snmpd ,此时你可以使用这个来轮询ifHCInBytesifHCOutBytes 参见注释2你所使用的接口...

poll_bytes.py : poll_bytes.py

from SNMP import v2Manager
import time

def poll_eth0(manager=None):
    # NOTE: 2nd arg to get_index should be a valid ifName value
    in_bytes = manager.get_index('ifHCInOctets', 'eth0')
    out_bytes = manager.get_index('ifHCOutOctets', 'eth0')
    return (time.time(), int(in_bytes), int(out_bytes))

# Prep an SNMP manager object...
mgr = v2Manager('localhost')
mgr.index('ifName')
stats = list()
# Insert condition below, instead of True...
while True:
    stats.append(poll_eth0(mgr))
    print poll_eth0(mgr)
    time.sleep(5)

SNMP.py : SNMP.py

from subprocess import Popen, PIPE
import re

class v2Manager(object):
    def __init__(self, addr='127.0.0.1', community='public'):
        self.addr      = addr
        self.community = community
        self._index = dict()

    def bulkwalk(self, oid='ifName'):
        cmd = 'snmpbulkwalk -v 2c -Osq -c %s %s %s' % (self.community,
            self.addr, oid)
        po = Popen(cmd, shell=True, stdout=PIPE, executable='/bin/bash')
        output = po.communicate()[0]
        result = dict()
        for line in re.split(r'\r*\n', output):
            if line.strip()=="":
                continue
            idx, value = re.split(r'\s+', line, 1)
            idx = idx.replace(oid+".", '')
            result[idx] = value
        return result

    def bulkwalk_index(self, oid='ifOutOctets'):
        result = dict()
        if not (self._index==dict()):
            vals = self.bulkwalk(oid=oid)
            for key, val in vals.items():
                idx = self._index.get(key, None)
                if not (idx is None):
                    result[idx] = val
                else:
                    raise ValueError, "Could not find '%s' in the index (%s)" % self.index
        else:
            raise ValueError, "Call the index() method before calling bulkwalk_index()"
        return result

    def get_index(self, oid='ifOutOctets', index=''):
        # This method is horribly inefficient... improvement left as exercise for the reader...
        if index:
            return self.bulkwalk_index().get(index, "<unknown>")
        else:
            raise ValueError, "Please include an index to get"

    def index(self, oid='ifName'):
        self._index = self.bulkwalk(oid=oid)

END NOTES: 结束说明:

  1. SNMP v2c uses clear-text authentication. SNMP v2c使用明文身份验证。 If you are worried about security / someone sniffing your traffic, change your community and restrict queries to your linux machine by source ip address. 如果您担心安全性/有人嗅探您的流量,请更改您的社区并通过源IP地址限制查询到您的Linux机器。 The perfect world would be to modify the SNMP.py above to use SNMPv3 (which encrypts sensitive data); 完美的世界是修改上面的SNMP.py以使用SNMPv3(它加密敏感数据); most people just use a non-public community and restrict snmp queries by source IP. 大多数人只使用非公共社区并通过源IP限制snmp查询。

  2. ifHCInOctets and ifHCOutOctets provide instantaneous values for the number of bytes transferred through the interface. ifHCInOctetsifHCOutOctets为通过接口传输的字节数提供瞬时值。 If you are looking for data transfer rate, of course there will be some additional math involved. 如果您正在寻找数据传输速率,当然会涉及一些额外的数学。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM