Я сделал класс Тун, который оборачивает pytun.TunTapDevice:Туннельный интерфейс модульного тестирования
from pytun import TunTapDevice
class Tun(object):
def __init__(self,name='tun',addr=None,dstaddr=None,netmask=None,mtu=None):
tun = TunTapDevice(name=name)
if addr : tun.addr = addr
if dstaddr : tun.dstaddr = dstaddr
if netmask : tun.netmask = netmask
if mtu : tun.mtu = mtu
self._tun = tun
self.up = self._tun.up
self.down = self._tun.down
self.read = self._tun.read
self.write = self._tun.write
self.close = self._tun.close
@property
def name(self):
return self._tun.name
@property
def mtu(self):
return self._tun.mtu
Вопрос не о том, как написать туннель, а о том, как написать тест-случай, чтобы гарантировать ее работы правильно в unix-подобных oses, используя python unit-testing.
Что я должен выписать ему для обеспечения работы? Может быть, запрос ARP, ICMP, DNS пакет или что-нибудь еще:
class TestTunnel(unittest.TestCase):
def setUp(self):
self.tun = Tun(name='tun0', addr='192.168.0.23', netmask='255.255.255.0',mtu=1500)
def test_tunnel(self):
self.tun.write(?????)
self.assertEqual(self.tun.read(),????)
EDIT 1:
наконец я получил его этим кодом:
from select import select
import dpkt
import struct
class TunnelTestCase(unittest.TestCase):
def setUp(self):
self.tun = Tun(name='testtun',
addr='192.168.6.92',
dstaddr='192.168.6.93',
netmask='255.255.255.0',
mtu=1500)
self.tun.up()
def _ip2str(self,ip):
return '.'.join([str(i) for i in struct.unpack('!BBBB',ip)])
def test_echo(self):
reqPack = dpkt.ip.IP('E\x00\x00T\x00\[email protected]\[email protected]\x01\xac\x9f\xc0\xa8\x06]\xc0\xa8\x06\\\x08\x00\x1c\xae\t\xc7\x00\x01\x0f\x8adQq\xab\x01\x00\x08\t\n\x0b\x0c\r\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f !"#$%&\'()*+,-./')
self.tun.write(reqPack.pack())
r,_w,_ex = select([self.tun],[],[],4)
if len(r) and r[0] == self.tun:
replyPack = dpkt.ip.IP(self.tun.read())
self.assertEqual(self._ip2str(replyPack.src), self.tun.addr)
self.assertEqual(self._ip2str(replyPack.dst), self.tun.dstaddr)
return
self.assert_(False, 'ICMP Echo timeout, the tunnel interface may not works properly in your system.')
Заранее спасибо – pylover
Мне нужно проверить туннель автоматически, тест montag необходимо запустить из командной строки и передать некоторые аргументы для работы. поэтому я планирую писать два сокета в режиме клиент-сервер, для связи через интерфейс туннеля. клиент отправляет что-нибудь, а сервер просто отдает все, что получает. какая у тебя идея? – pylover
Я бы просто выполнил настройку сервера внутри метода setUp и передал то, что ранее было бы передано вручную через командную строку. Возможно, вам придется разветвлять его на другом потоке, поскольку он может блокироваться (это также означает, что вам нужен способ убить этот другой поток). Да, просто сделайте простое эхо «Hello World» от клиента и утвердитесь против этого при чтении данных из сокета как для сервера, так и для клиента. Вы можете сделать все настройки в автоматическом режиме, не нужно настраивать сервер вручную, передавая аргументы командной строки только для запуска теста. –