Skip to content

Commit e7d60ab

Browse files
authored
Merge pull request #393 from tonyseek/hotfix/handle-children-watch-nonode
Close the ChildrenWatch if the node doesn't exist.
2 parents 1b4bca7 + 2016924 commit e7d60ab

3 files changed

Lines changed: 58 additions & 3 deletions

File tree

kazoo/recipe/watchers.py

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -315,8 +315,13 @@ def _get_children(self, event=None):
315315
if self._stopped:
316316
return
317317

318-
children = self._client.retry(self._client.get_children,
319-
self._path, self._watcher)
318+
try:
319+
children = self._client.retry(self._client.get_children,
320+
self._path, self._watcher)
321+
except NoNodeError:
322+
self._stopped = True
323+
return
324+
320325
if not self._watch_established:
321326
self._watch_established = True
322327

kazoo/tests/test_watchers.py

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -171,6 +171,54 @@ def changed(d, stat):
171171

172172
eq_(args, [None, None])
173173

174+
def test_no_such_node_for_children_watch(self):
175+
args = []
176+
path = self.path + '/test_no_such_node_for_children_watch'
177+
update = threading.Event()
178+
179+
def changed(children):
180+
args.append(children)
181+
update.set()
182+
183+
# watch a node which does not exist
184+
children_watch = self.client.ChildrenWatch(path, changed)
185+
eq_(update.is_set(), False)
186+
eq_(children_watch._stopped, True)
187+
eq_(args, [])
188+
189+
# watch a node which exists
190+
self.client.create(path, b'')
191+
children_watch = self.client.ChildrenWatch(path, changed)
192+
update.wait(3)
193+
eq_(args, [[]])
194+
update.clear()
195+
196+
# watch changes
197+
self.client.create(path + '/fred', b'')
198+
update.wait(3)
199+
eq_(args, [[], ['fred']])
200+
update.clear()
201+
202+
# delete children
203+
self.client.delete(path + '/fred')
204+
update.wait(3)
205+
eq_(args, [[], ['fred'], []])
206+
update.clear()
207+
208+
# delete watching
209+
self.client.delete(path)
210+
211+
# a hack for waiting the watcher stop
212+
for retry in range(5):
213+
if children_watch._stopped:
214+
break
215+
children_watch._run_lock.acquire()
216+
children_watch._run_lock.release()
217+
time.sleep(retry / 10.0)
218+
219+
eq_(update.is_set(), False)
220+
eq_(children_watch._stopped, True)
221+
174222
def test_bad_watch_func2(self):
175223
counter = 0
176224

tox.ini

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,9 @@ commands = flake8 {posargs}
1818
[testenv]
1919
usedevelop = True
2020
install_command = pip install {opts} {packages}
21-
setenv = VIRTUAL_ENV={envdir}
21+
setenv =
22+
VIRTUAL_ENV={envdir}
23+
ZOOKEEPER_VERSION={env:ZOOKEEPER_VERSION:}
2224
deps = -r{toxinidir}/requirements.txt
2325
-r{toxinidir}/requirements_sphinx.txt
2426
commands = {toxinidir}/ensure-zookeeper-env.sh nosetests {posargs: -d -v --with-coverage kazoo.tests}

0 commit comments

Comments
 (0)