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
11 changes: 11 additions & 0 deletions pyfritzhome/fritzhome.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ def __init__(self, host, user, password, ssl_verify=True):
self._session = Session()
self._ssl_verify = ssl_verify
self._has_getdeviceinfos = True
self._has_txbusy = True

def _request(self, url, params=None, timeout=10):
"""Send a request with parameters."""
Expand Down Expand Up @@ -200,9 +201,13 @@ def _get_listinfo_elements(self, entity_type):

def wait_device_txbusy(self, ain, retries=10):
"""Wait for device to finish command execution."""
if not self._has_txbusy:
return True

for _ in range(retries):
if self._has_getdeviceinfos:
try:
# getdeviceinfos was added in FritzOS 7.24
plain = self.get_device_infos(ain)
dom = ElementTree.fromstring(plain)
except exceptions.HTTPError:
Expand All @@ -213,8 +218,14 @@ def wait_device_txbusy(self, ain, retries=10):
dom = self.get_device_element(ain)

txbusy = dom.findall("txbusy")
if not txbusy:
# txbusy was added in FritzOS 7.20
self._has_txbusy = False
return True

if txbusy[0].text == "0":
return True

time.sleep(0.2)
return False

Expand Down
25 changes: 25 additions & 0 deletions tests/responses/base/device_list_no_txbusy.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
<?xml version="1.0" ?>
<devicelist version="1">
<device functionbitmask="320" fwversion="03.54" id="18" identifier="32960 0089208" manufacturer="AVM" productname="Comet DECT">
<present>0</present>
<name>Kitchen</name>
<temperature>
<celsius/>
<offset/>
</temperature>
<hkr>
<tist/>
<tsoll/>
<absenk/>
<komfort/>
<lock/>
<devicelock/>
<errorcode>0</errorcode>
<batterylow>0</batterylow>
<nextchange>
<endperiod>0</endperiod>
<tchange>255</tchange>
</nextchange>
</hkr>
</device>
</devicelist>
30 changes: 30 additions & 0 deletions tests/test_fritzhome.py
Original file line number Diff line number Diff line change
Expand Up @@ -345,15 +345,44 @@ def test_wait_tx_busy(self):
]

assert self.fritz.wait_device_txbusy("11960 0089208")
assert self.mock.call_count == 2

def test_wait_tx_busy_fallback(self):
"""FritzOS <7.24 has no getdeviceinfos"""
self.mock.side_effect = [
HTTPError("400 Client Error: Bad Request"),
Helper.response("base/device_list_txbusy"),
Helper.response("base/device_list_not_txbusy"),
]

# first call will set _has_getdeviceinfos to False
# so sub-sequent calls won't try getdeviceinfos anymore
assert self.fritz.wait_device_txbusy("22960 0089208")
assert self.mock.call_count == 3

self.mock.reset_mock()
self.mock.side_effect = [
Helper.response("base/device_list_txbusy"),
Helper.response("base/device_list_not_txbusy"),
]

assert self.fritz.wait_device_txbusy("22960 0089208")
assert self.mock.call_count == 2

def test_wait_tx_busy_no_txbusy(self):
"""FritzOS <7.20 has no txbusy and no getdeviceinfos"""
self.mock.side_effect = [
HTTPError("400 Client Error: Bad Request"),
Helper.response("base/device_list_no_txbusy"),
]

# first call will set _has_txbusy to False, those skip all sub-sequent calls
assert self.fritz.wait_device_txbusy("32960 0089208")
assert self.mock.call_count == 2
self.mock.reset_mock()

assert self.fritz.wait_device_txbusy("32960 0089208")
assert self.mock.call_count == 0

def test_wait_tx_busy_failed(self):
self.mock.side_effect = [
Expand All @@ -362,3 +391,4 @@ def test_wait_tx_busy_failed(self):
]

assert not self.fritz.wait_device_txbusy("11960 0089208", 1)
assert self.mock.call_count == 1
Loading