Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,12 @@
build/
*.pyc
*.pyo
Thumbs.db
.DS_Store
.project
.pydevproject
.settings
.idea
.vslick
.cache

1 change: 1 addition & 0 deletions setup.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -5,3 +5,4 @@ universal = 1
show-source = 1
import-order-style=google
application-import-names=zeroconf
max-line-length=110
97 changes: 81 additions & 16 deletions test_zeroconf.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,17 +7,16 @@
import logging
import socket
import struct
import time
import unittest
from threading import Event

from mock import Mock
from six import indexbytes
from six.moves import xrange

import zeroconf as r
from zeroconf import (
DNSText,
Listener,
ServiceBrowser,
ServiceInfo,
ServiceStateChange,
Expand Down Expand Up @@ -151,6 +150,84 @@ def test_launch_and_close(self):
rv.close()


class Exceptions(unittest.TestCase):

def test_bad_service_info_name(self):
browser = Zeroconf()
self.assertRaises(r.BadTypeInNameException,
browser.get_service_info, "type", "type_not")
browser.close()


class Listener(unittest.TestCase):

def test_integration_with_listener_class(self):

service_added = Event()
service_removed = Event()

type_ = "_http._tcp.local."
name = "xxxyyy"
registration_name = "%s.%s" % (name, type_)

class MyListener(object):
def add_service(self, zeroconf, type, name):
zeroconf.get_service_info(type, name)
service_added.set()

def remove_service(self, zeroconf, type, name):
service_removed.set()

zeroconf_browser = Zeroconf()
zeroconf_browser.add_service_listener(type_, MyListener())

properties = dict(
prop_none=None,
prop_string=b'a_prop',
prop_float=1.0,
prop_blank=b'a blanked string',
prop_true=1,
prop_false=0,
)

zeroconf_registrar = Zeroconf()
desc = {'path': '/~paulsm/'}
desc.update(properties)
info = ServiceInfo(
type_, registration_name,
socket.inet_aton("10.0.1.2"), 80, 0, 0,
desc, "ash-2.local.")
zeroconf_registrar.register_service(info)

try:
service_added.wait(1)
assert service_added.is_set()

# short pause to allow multicast timers to expire
time.sleep(2)

# clear the answer cache to force query
for record in zeroconf_browser.cache.entries():
zeroconf_browser.cache.remove(record)

# get service info without answer cache
info = zeroconf_browser.get_service_info(type_, registration_name)

assert info.properties[b'prop_none'] is False
assert info.properties[b'prop_string'] == properties['prop_string']
assert info.properties[b'prop_float'] is False
assert info.properties[b'prop_blank'] == properties['prop_blank']
assert info.properties[b'prop_true'] is True
assert info.properties[b'prop_false'] is False

zeroconf_registrar.unregister_service(info)
service_removed.wait(1)
assert service_removed.is_set()
finally:
zeroconf_registrar.close()
zeroconf_browser.close()


def test_integration():
service_added = Event()
service_removed = Event()
Expand Down Expand Up @@ -179,26 +256,14 @@ def on_service_state_change(zeroconf, service_type, state_change, name):
try:
service_added.wait(1)
assert service_added.is_set()
zeroconf_registrar.unregister_service(info)
service_removed.wait(1)
assert service_removed.is_set()
# Don't remove service, allow close() to cleanup

finally:
zeroconf_registrar.close()
browser.cancel()
zeroconf_browser.close()


def test_listener_handles_closed_socket_situation_gracefully():
error = socket.error(socket.EBADF)
error.errno = socket.EBADF

zeroconf = Mock()
zeroconf.socket.recvfrom.side_effect = error

listener = Listener(zeroconf)
listener.handle_read(zeroconf.socket)


def test_dnstext_repr_works():
# There was an issue on Python 3 that prevented DNSText's repr
# from working when the text was longer than 10 bytes
Expand Down
Loading