Skip to content

Commit d859823

Browse files
committed
Implement provisional zigpy network management API
1 parent 4ac608c commit d859823

15 files changed

+240
-538
lines changed

tests/application/test_connect.py

Lines changed: 8 additions & 60 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@
44

55
import zigpy_znp.config as conf
66
from zigpy_znp.uart import connect as uart_connect
7-
from zigpy_znp.zigbee.application import ControllerApplication
87

98
from ..conftest import FORMED_DEVICES, FormedLaunchpadCC26X2R1, swap_attribute
109

@@ -50,60 +49,9 @@ def count_connected():
5049
assert count_connected() == 0
5150

5251

53-
async def test_probe_unsuccessful():
54-
assert not (
55-
await ControllerApplication.probe(
56-
conf.SCHEMA_DEVICE({conf.CONF_DEVICE_PATH: "/dev/null"})
57-
)
58-
)
59-
60-
61-
@pytest.mark.parametrize("device", FORMED_DEVICES)
62-
async def test_probe_unsuccessful_slow(device, make_znp_server, mocker):
63-
znp_server = make_znp_server(server_cls=device)
64-
65-
# Don't respond to anything
66-
znp_server._listeners.clear()
67-
68-
mocker.patch("zigpy_znp.zigbee.application.PROBE_TIMEOUT", new=0.1)
69-
70-
assert not (
71-
await ControllerApplication.probe(
72-
conf.SCHEMA_DEVICE({conf.CONF_DEVICE_PATH: znp_server.serial_port})
73-
)
74-
)
75-
76-
assert not any([t._is_connected for t in znp_server._transports])
77-
78-
79-
@pytest.mark.parametrize("device", FORMED_DEVICES)
80-
async def test_probe_successful(device, make_znp_server):
81-
znp_server = make_znp_server(server_cls=device)
82-
83-
assert await ControllerApplication.probe(
84-
conf.SCHEMA_DEVICE({conf.CONF_DEVICE_PATH: znp_server.serial_port})
85-
)
86-
assert not any([t._is_connected for t in znp_server._transports])
87-
88-
89-
@pytest.mark.parametrize("device", FORMED_DEVICES)
90-
async def test_probe_multiple(device, make_znp_server):
91-
# Make sure that our listeners don't get cleaned up after each probe
92-
znp_server = make_znp_server(server_cls=device)
93-
znp_server.close = lambda: None
94-
95-
config = conf.SCHEMA_DEVICE({conf.CONF_DEVICE_PATH: znp_server.serial_port})
96-
97-
assert await ControllerApplication.probe(config)
98-
assert await ControllerApplication.probe(config)
99-
assert await ControllerApplication.probe(config)
100-
assert await ControllerApplication.probe(config)
101-
assert not any([t._is_connected for t in znp_server._transports])
102-
103-
10452
@pytest.mark.parametrize("device", FORMED_DEVICES)
10553
async def test_reconnect(device, event_loop, make_application):
106-
app, znp_server = make_application(
54+
app, znp_server = await make_application(
10755
server_cls=device,
10856
client_config={
10957
# Make auto-reconnection happen really fast
@@ -144,7 +92,7 @@ async def test_reconnect(device, event_loop, make_application):
14492

14593
@pytest.mark.parametrize("device", FORMED_DEVICES)
14694
async def test_shutdown_from_app(device, mocker, make_application):
147-
app, znp_server = make_application(server_cls=device)
95+
app, znp_server = await make_application(server_cls=device)
14896

14997
await app.startup(auto_form=False)
15098

@@ -160,7 +108,7 @@ async def test_shutdown_from_app(device, mocker, make_application):
160108

161109

162110
async def test_clean_shutdown(make_application):
163-
app, znp_server = make_application(server_cls=FormedLaunchpadCC26X2R1)
111+
app, znp_server = await make_application(server_cls=FormedLaunchpadCC26X2R1)
164112
await app.startup(auto_form=False)
165113

166114
# This should not throw
@@ -171,7 +119,7 @@ async def test_clean_shutdown(make_application):
171119

172120

173121
async def test_multiple_shutdown(make_application):
174-
app, znp_server = make_application(server_cls=FormedLaunchpadCC26X2R1)
122+
app, znp_server = await make_application(server_cls=FormedLaunchpadCC26X2R1)
175123
await app.startup(auto_form=False)
176124

177125
await app.shutdown()
@@ -183,7 +131,7 @@ async def test_multiple_shutdown(make_application):
183131
async def test_reconnect_lockup(device, event_loop, make_application, mocker):
184132
mocker.patch("zigpy_znp.zigbee.application.WATCHDOG_PERIOD", 0.1)
185133

186-
app, znp_server = make_application(
134+
app, znp_server = await make_application(
187135
server_cls=device,
188136
client_config={
189137
# Make auto-reconnection happen really fast
@@ -224,7 +172,7 @@ async def test_reconnect_lockup(device, event_loop, make_application, mocker):
224172
async def test_reconnect_lockup_pyserial(device, event_loop, make_application, mocker):
225173
mocker.patch("zigpy_znp.zigbee.application.WATCHDOG_PERIOD", 0.1)
226174

227-
app, znp_server = make_application(
175+
app, znp_server = await make_application(
228176
server_cls=device,
229177
client_config={
230178
conf.CONF_ZNP_CONFIG: {
@@ -245,9 +193,9 @@ async def test_reconnect_lockup_pyserial(device, event_loop, make_application, m
245193

246194
did_load_info = asyncio.get_running_loop().create_future()
247195

248-
async def patched_load_network_info(*, old_load=app.load_network_info):
196+
async def patched_load_network_info(old_load=app.load_network_info, **kwargs):
249197
try:
250-
return await old_load()
198+
return await old_load(**kwargs)
251199
finally:
252200
did_load_info.set_result(True)
253201

tests/application/test_joining.py

Lines changed: 15 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ async def test_permit_join(device, fixed_joining_bug, mocker, make_application):
2727
if fixed_joining_bug:
2828
mocker.patch.object(device, "code_revision", 20210708)
2929

30-
app, znp_server = make_application(server_cls=device)
30+
app, znp_server = await make_application(server_cls=device)
3131

3232
# Handle us opening joins on the coordinator
3333
permit_join_coordinator = znp_server.reply_once_to(
@@ -68,7 +68,7 @@ async def test_permit_join(device, fixed_joining_bug, mocker, make_application):
6868

6969
@pytest.mark.parametrize("device", FORMED_DEVICES)
7070
async def test_join_coordinator(device, make_application):
71-
app, znp_server = make_application(server_cls=device)
71+
app, znp_server = await make_application(server_cls=device)
7272

7373
# Handle us opening joins on the coordinator
7474
permit_join_coordinator = znp_server.reply_once_to(
@@ -82,7 +82,7 @@ async def test_join_coordinator(device, make_application):
8282
)
8383

8484
await app.startup(auto_form=False)
85-
await app.permit(node=app.ieee)
85+
await app.permit(node=app.state.node_info.ieee)
8686

8787
await permit_join_coordinator
8888

@@ -92,7 +92,7 @@ async def test_join_coordinator(device, make_application):
9292
@pytest.mark.parametrize("device", FORMED_ZSTACK3_DEVICES)
9393
@pytest.mark.parametrize("permit_result", [None, asyncio.TimeoutError()])
9494
async def test_permit_join_with_key(device, permit_result, make_application, mocker):
95-
app, znp_server = make_application(server_cls=device)
95+
app, znp_server = await make_application(server_cls=device)
9696

9797
# Consciot bulb
9898
ieee = t.EUI64.convert("EC:1B:BD:FF:FE:54:4F:40")
@@ -114,10 +114,6 @@ async def test_permit_join_with_key(device, permit_result, make_application, moc
114114
],
115115
)
116116

117-
mocker.patch.object(
118-
app, "permit", new=CoroutineMock(side_effect=[None, permit_result])
119-
)
120-
121117
join_disable_install_code = znp_server.reply_once_to(
122118
c.AppConfig.BDBSetJoinUsesInstallCodeKey.Req(BdbJoinUsesInstallCodeKey=False),
123119
responses=[
@@ -127,14 +123,16 @@ async def test_permit_join_with_key(device, permit_result, make_application, moc
127123

128124
await app.startup(auto_form=False)
129125

126+
mocker.patch.object(app, "permit", new=CoroutineMock(side_effect=permit_result))
127+
130128
with contextlib.nullcontext() if permit_result is None else pytest.raises(
131129
asyncio.TimeoutError
132130
):
133131
await app.permit_with_key(node=ieee, code=code, time_s=1)
134132

135133
await bdb_add_install_code
136134
await join_enable_install_code
137-
assert app.permit.call_count == 2
135+
assert app.permit.call_count == 1
138136

139137
# The install code policy is reset right after
140138
await join_disable_install_code
@@ -144,7 +142,7 @@ async def test_permit_join_with_key(device, permit_result, make_application, moc
144142

145143
@pytest.mark.parametrize("device", FORMED_ZSTACK3_DEVICES)
146144
async def test_permit_join_with_invalid_key(device, make_application):
147-
app, znp_server = make_application(server_cls=device)
145+
app, znp_server = await make_application(server_cls=device)
148146

149147
# Consciot bulb
150148
ieee = t.EUI64.convert("EC:1B:BD:FF:FE:54:4F:40")
@@ -158,7 +156,7 @@ async def test_permit_join_with_invalid_key(device, make_application):
158156

159157
@pytest.mark.parametrize("device", FORMED_DEVICES)
160158
async def test_on_zdo_device_join(device, make_application, mocker):
161-
app, znp_server = make_application(server_cls=device)
159+
app, znp_server = await make_application(server_cls=device)
162160
await app.startup(auto_form=False)
163161

164162
mocker.patch.object(app, "handle_join")
@@ -178,7 +176,7 @@ async def test_on_zdo_device_join(device, make_application, mocker):
178176

179177
@pytest.mark.parametrize("device", FORMED_DEVICES)
180178
async def test_on_zdo_device_join_and_announce_fast(device, make_application, mocker):
181-
app, znp_server = make_application(server_cls=device)
179+
app, znp_server = await make_application(server_cls=device)
182180
await app.startup(auto_form=False)
183181

184182
mocker.patch.object(app, "handle_join")
@@ -215,7 +213,7 @@ async def test_on_zdo_device_join_and_announce_fast(device, make_application, mo
215213

216214
@pytest.mark.parametrize("device", FORMED_DEVICES)
217215
async def test_on_zdo_device_join_and_announce_slow(device, make_application, mocker):
218-
app, znp_server = make_application(server_cls=device)
216+
app, znp_server = await make_application(server_cls=device)
219217
await app.startup(auto_form=False)
220218

221219
mocker.patch.object(app, "handle_join")
@@ -253,7 +251,7 @@ async def test_on_zdo_device_join_and_announce_slow(device, make_application, mo
253251

254252
@pytest.mark.parametrize("device", FORMED_DEVICES)
255253
async def test_new_device_join_and_bind_complex(device, make_application, mocker):
256-
app, znp_server = make_application(server_cls=device)
254+
app, znp_server = await make_application(server_cls=device)
257255
await app.startup(auto_form=False)
258256

259257
nwk = 0x6A7C
@@ -504,7 +502,7 @@ def bind_req_callback(request):
504502
ep = device.endpoints[request.SrcEndpoint]
505503
assert cluster in ep.in_clusters or cluster in ep.out_clusters
506504

507-
assert request.Address.ieee == app.ieee
505+
assert request.Address.ieee == app.state.node_info.ieee
508506
assert request.Address.addrmode == 0x03
509507

510508
# Make sure the endpoint profiles match up
@@ -530,7 +528,7 @@ def bind_req_callback(request):
530528

531529
@pytest.mark.parametrize("device", FORMED_DEVICES)
532530
async def test_unknown_device_discovery(device, make_application, mocker):
533-
app, znp_server = make_application(server_cls=device)
531+
app, znp_server = await make_application(server_cls=device)
534532
await app.startup(auto_form=False)
535533

536534
mocker.spy(app, "handle_join")
@@ -604,4 +602,4 @@ async def test_unknown_device_discovery(device, make_application, mocker):
604602
assert new_dev.nwk == new_nwk
605603
assert new_dev.ieee == new_ieee
606604

607-
await app.pre_shutdown()
605+
await app.shutdown()

tests/application/test_nvram_migration.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ async def test_addrmgr_rewrite_fix(device, make_application, mocker):
6262
extAddr=t.EUI64.convert("FF:FF:FF:FF:FF:FF:FF:FF"),
6363
)
6464

65-
app, znp_server = make_application(server_cls=device)
65+
app, znp_server = await make_application(server_cls=device)
6666
znp_server.callback_for_response(
6767
c.SYS.OSALNVReadExt.Req(Id=OsalNvIds.ADDRMGR, Offset=0), addrmgr_reads.append
6868
)
@@ -96,6 +96,7 @@ async def test_addrmgr_rewrite_fix(device, make_application, mocker):
9696

9797
# Will not be read again
9898
assert len(addrmgr_reads) == 2
99+
await app.connect()
99100
await app.startup()
100101
await app.shutdown()
101102
assert len(addrmgr_reads) == 2
@@ -106,6 +107,7 @@ async def test_addrmgr_rewrite_fix(device, make_application, mocker):
106107
old_addrmgr2 = nvram[OsalNvIds.ADDRMGR]
107108

108109
assert len(addrmgr_reads) == 2
110+
await app.connect()
109111
await app.startup()
110112
await app.shutdown()
111113
assert len(addrmgr_reads) == 3

0 commit comments

Comments
 (0)