Как получить значащие имена сетевого интерфейса вместо GUID с netifaces под Windows?

Я использую модуль netifaces.

import netifaces
print netifaces.interfaces()

но это показывает результат ниже:

 ['{CDC97813-CC28-4260-BA1E-F0CE3081DEC7}',
 '{846EE342-7039-11DE-9D20-806E6F6E6963}',
 '{A51BA5F0-738B-4405-975F-44E67383513F}',
 '{A646FA85-2EC6-4E57-996E-96E1B1C5CD59}',
'{B5DC7787-26DC-4540-8424-A1D5598DC175}']

Я хочу получить "дружественное" имя интерфейса, например "Подключение по локальной сети" в Windows.

Как я могу это получить?

Ответ 1

Похоже, что netifaces оставляет нам доступ к информации из реестра Windows. Следующие функции работают для меня под Python 3.4 в Windows 8.1.

Чтобы получить имя соединения...

import netifaces as ni
import winreg as wr
from pprint import pprint

def get_connection_name_from_guid(iface_guids):
    iface_names = ['(unknown)' for i in range(len(iface_guids))]
    reg = wr.ConnectRegistry(None, wr.HKEY_LOCAL_MACHINE)
    reg_key = wr.OpenKey(reg, r'SYSTEM\CurrentControlSet\Control\Network\{4d36e972-e325-11ce-bfc1-08002be10318}')
    for i in range(len(iface_guids)):
        try:
            reg_subkey = wr.OpenKey(reg_key, iface_guids[i] + r'\Connection')
            iface_names[i] = wr.QueryValueEx(reg_subkey, 'Name')[0]
        except FileNotFoundError:
            pass
    return iface_names

x = ni.interfaces()
pprint(get_connection_name_from_guid(x))

.. который на моей машине производит:

['Local Area Connection* 12',
 'Bluetooth Network Connection',
 'Wi-Fi',
 'Ethernet',
 'VirtualBox Host-Only Network',
 '(unknown)',
 'isatap.{4E4150B0-643B-42EA-AEEA-A14FBD6B1844}',
 'isatap.{BB05D283-4CBF-4514-B76C-7B7EBB2FC85B}']

Чтобы получить имя драйвера...

import netifaces as ni
import winreg as wr
from pprint import pprint

def get_driver_name_from_guid(iface_guids):
    iface_names = ['(unknown)' for i in range(len(iface_guids))]
    reg = wr.ConnectRegistry(None, wr.HKEY_LOCAL_MACHINE)
    reg_key = wr.OpenKey(reg, r'SYSTEM\CurrentControlSet\Control\Class\{4d36e972-e325-11ce-bfc1-08002be10318}')
    for i in range(wr.QueryInfoKey(reg_key)[0]):
        subkey_name = wr.EnumKey(reg_key, i)
        try:
            reg_subkey = wr.OpenKey(reg_key, subkey_name)
            guid = wr.QueryValueEx(reg_subkey, 'NetCfgInstanceId')[0]
            try:
                idx = iface_guids.index(guid)
                iface_names[idx] = wr.QueryValueEx(reg_subkey, 'DriverDesc')[0]
            except ValueError:
                pass
        except PermissionError:
            pass
    return iface_names

x = ni.interfaces()
pprint(get_driver_name_from_guid(x))

..., который дает мне:

['Microsoft Wi-Fi Direct Virtual Adapter',
 'Bluetooth Device (Personal Area Network)',
 'Dell Wireless 1395 WLAN Mini-Card',
 'Broadcom 440x 10/100 Integrated Controller',
 'VirtualBox Host-Only Ethernet Adapter',
 '(unknown)',
 'Microsoft ISATAP Adapter',
 'Microsoft ISATAP Adapter']

Ответ 2

Мы также можем использовать Windows WMI:

import wmi

c = wmi.WMI()
qry = "select Name from Win32_NetworkAdapter where NetEnabled=True and NetConnectionStatus=2"

lst = [o.Name for o in c.query(qry)]
print(lst)

дает на моей машине:

['Realtek PCIe GBE Family Controller', 'VMware Virtual Ethernet Adapter for VMnet1', 'VMware Virtual Ethernet Adapter for VMnet8', 'VirtualBox Host-Only Ethernet Adapter']

MSDN: класс Win32_NetworkAdapter

Ответ 3

Расширение ответа MaxU

Более точный/уточненный способ

Select Index from Win32_NetworkAdapterConfiguration WHERE IPEnabled = True or (ServiceName<>'' 
                                                    AND ServiceName<>'AsyncMac' 
                                                    AND ServiceName<>'VMnetx' AND ServiceName<>'VMnetadapter' AND ServiceName<>'Rasl2tp' AND ServiceName<>'msloop' AND ServiceName<>'PptpMiniport' 
                                                    AND ServiceName<>'Raspti' AND ServiceName<>'NDISWan' AND ServiceName<>'NdisWan4' AND ServiceName<>'RasPppoe' 
                                                    AND ServiceName<>'NdisIP' AND Description<>'PPP Adapter.') AND MACAddress is not NULL

а затем запустить запрос относительно

SELECT * FROM Win32_NetworkAdapter where index= <Index>