|
27 | 27 | ) |
28 | 28 | from homeassistant.core import HomeAssistant |
29 | 29 | from homeassistant.exceptions import HomeAssistantError |
| 30 | +from homeassistant.helpers import issue_registry as ir |
30 | 31 | from homeassistant.helpers.backup import async_initialize_backup |
31 | 32 | from homeassistant.setup import async_setup_component |
32 | 33 |
|
33 | 34 | from .common import ( |
34 | 35 | LOCAL_AGENT_ID, |
35 | 36 | TEST_BACKUP_ABC123, |
36 | 37 | TEST_BACKUP_DEF456, |
| 38 | + mock_backup_agent, |
37 | 39 | setup_backup_integration, |
| 40 | + setup_backup_platform, |
38 | 41 | ) |
39 | 42 |
|
40 | 43 | from tests.common import async_fire_time_changed, async_mock_service |
@@ -3244,6 +3247,185 @@ async def test_config_retention_days_logic( |
3244 | 3247 | await hass.async_block_till_done() |
3245 | 3248 |
|
3246 | 3249 |
|
| 3250 | +async def test_configured_agents_unavailable_repair( |
| 3251 | + hass: HomeAssistant, |
| 3252 | + hass_ws_client: WebSocketGenerator, |
| 3253 | + issue_registry: ir.IssueRegistry, |
| 3254 | + hass_storage: dict[str, Any], |
| 3255 | +) -> None: |
| 3256 | + """Test creating and deleting repair issue for configured unavailable agents.""" |
| 3257 | + issue_id = "automatic_backup_agents_unavailable_test.agent" |
| 3258 | + ws_client = await hass_ws_client(hass) |
| 3259 | + hass_storage.update( |
| 3260 | + { |
| 3261 | + "backup": { |
| 3262 | + "data": { |
| 3263 | + "backups": [], |
| 3264 | + "config": { |
| 3265 | + "agents": {}, |
| 3266 | + "automatic_backups_configured": True, |
| 3267 | + "create_backup": { |
| 3268 | + "agent_ids": ["test.agent"], |
| 3269 | + "include_addons": None, |
| 3270 | + "include_all_addons": False, |
| 3271 | + "include_database": False, |
| 3272 | + "include_folders": None, |
| 3273 | + "name": None, |
| 3274 | + "password": None, |
| 3275 | + }, |
| 3276 | + "retention": {"copies": None, "days": None}, |
| 3277 | + "last_attempted_automatic_backup": None, |
| 3278 | + "last_completed_automatic_backup": None, |
| 3279 | + "schedule": { |
| 3280 | + "days": ["mon"], |
| 3281 | + "recurrence": "custom_days", |
| 3282 | + "state": "never", |
| 3283 | + "time": None, |
| 3284 | + }, |
| 3285 | + }, |
| 3286 | + }, |
| 3287 | + "key": DOMAIN, |
| 3288 | + "version": store.STORAGE_VERSION, |
| 3289 | + "minor_version": store.STORAGE_VERSION_MINOR, |
| 3290 | + }, |
| 3291 | + } |
| 3292 | + ) |
| 3293 | + |
| 3294 | + await setup_backup_integration(hass) |
| 3295 | + get_agents_mock = AsyncMock(return_value=[mock_backup_agent("agent")]) |
| 3296 | + register_listener_mock = Mock() |
| 3297 | + await setup_backup_platform( |
| 3298 | + hass, |
| 3299 | + domain="test", |
| 3300 | + platform=Mock( |
| 3301 | + async_get_backup_agents=get_agents_mock, |
| 3302 | + async_register_backup_agents_listener=register_listener_mock, |
| 3303 | + ), |
| 3304 | + ) |
| 3305 | + await hass.async_block_till_done() |
| 3306 | + |
| 3307 | + reload_backup_agents = register_listener_mock.call_args[1]["listener"] |
| 3308 | + |
| 3309 | + await ws_client.send_json_auto_id({"type": "backup/agents/info"}) |
| 3310 | + resp = await ws_client.receive_json() |
| 3311 | + assert resp["result"]["agents"] == [ |
| 3312 | + {"agent_id": "backup.local", "name": "local"}, |
| 3313 | + {"agent_id": "test.agent", "name": "agent"}, |
| 3314 | + ] |
| 3315 | + |
| 3316 | + assert not issue_registry.async_get_issue(domain=DOMAIN, issue_id=issue_id) |
| 3317 | + |
| 3318 | + # Reload the agents with no agents returned. |
| 3319 | + |
| 3320 | + get_agents_mock.return_value = [] |
| 3321 | + reload_backup_agents() |
| 3322 | + await hass.async_block_till_done() |
| 3323 | + |
| 3324 | + await ws_client.send_json_auto_id({"type": "backup/agents/info"}) |
| 3325 | + resp = await ws_client.receive_json() |
| 3326 | + assert resp["result"]["agents"] == [ |
| 3327 | + {"agent_id": "backup.local", "name": "local"}, |
| 3328 | + ] |
| 3329 | + |
| 3330 | + assert issue_registry.async_get_issue(domain=DOMAIN, issue_id=issue_id) |
| 3331 | + |
| 3332 | + await ws_client.send_json_auto_id({"type": "backup/config/info"}) |
| 3333 | + result = await ws_client.receive_json() |
| 3334 | + assert result["result"]["config"]["create_backup"]["agent_ids"] == ["test.agent"] |
| 3335 | + |
| 3336 | + # Update the automatic backup configuration removing the unavailable agent. |
| 3337 | + |
| 3338 | + await ws_client.send_json_auto_id( |
| 3339 | + { |
| 3340 | + "type": "backup/config/update", |
| 3341 | + "create_backup": {"agent_ids": ["backup.local"]}, |
| 3342 | + } |
| 3343 | + ) |
| 3344 | + result = await ws_client.receive_json() |
| 3345 | + |
| 3346 | + assert not issue_registry.async_get_issue(domain=DOMAIN, issue_id=issue_id) |
| 3347 | + |
| 3348 | + await ws_client.send_json_auto_id({"type": "backup/config/info"}) |
| 3349 | + result = await ws_client.receive_json() |
| 3350 | + assert result["result"]["config"]["create_backup"]["agent_ids"] == ["backup.local"] |
| 3351 | + |
| 3352 | + # Reload the agents with one agent returned |
| 3353 | + # but not configured for automatic backups. |
| 3354 | + |
| 3355 | + get_agents_mock.return_value = [mock_backup_agent("agent")] |
| 3356 | + reload_backup_agents() |
| 3357 | + await hass.async_block_till_done() |
| 3358 | + |
| 3359 | + await ws_client.send_json_auto_id({"type": "backup/agents/info"}) |
| 3360 | + resp = await ws_client.receive_json() |
| 3361 | + assert resp["result"]["agents"] == [ |
| 3362 | + {"agent_id": "backup.local", "name": "local"}, |
| 3363 | + {"agent_id": "test.agent", "name": "agent"}, |
| 3364 | + ] |
| 3365 | + |
| 3366 | + assert not issue_registry.async_get_issue(domain=DOMAIN, issue_id=issue_id) |
| 3367 | + |
| 3368 | + await ws_client.send_json_auto_id({"type": "backup/config/info"}) |
| 3369 | + result = await ws_client.receive_json() |
| 3370 | + assert result["result"]["config"]["create_backup"]["agent_ids"] == ["backup.local"] |
| 3371 | + |
| 3372 | + # Update the automatic backup configuration and configure the test agent. |
| 3373 | + |
| 3374 | + await ws_client.send_json_auto_id( |
| 3375 | + { |
| 3376 | + "type": "backup/config/update", |
| 3377 | + "create_backup": {"agent_ids": ["backup.local", "test.agent"]}, |
| 3378 | + } |
| 3379 | + ) |
| 3380 | + result = await ws_client.receive_json() |
| 3381 | + |
| 3382 | + assert not issue_registry.async_get_issue(domain=DOMAIN, issue_id=issue_id) |
| 3383 | + |
| 3384 | + await ws_client.send_json_auto_id({"type": "backup/config/info"}) |
| 3385 | + result = await ws_client.receive_json() |
| 3386 | + assert result["result"]["config"]["create_backup"]["agent_ids"] == [ |
| 3387 | + "backup.local", |
| 3388 | + "test.agent", |
| 3389 | + ] |
| 3390 | + |
| 3391 | + # Reload the agents with no agents returned again. |
| 3392 | + |
| 3393 | + get_agents_mock.return_value = [] |
| 3394 | + reload_backup_agents() |
| 3395 | + await hass.async_block_till_done() |
| 3396 | + |
| 3397 | + await ws_client.send_json_auto_id({"type": "backup/agents/info"}) |
| 3398 | + resp = await ws_client.receive_json() |
| 3399 | + assert resp["result"]["agents"] == [ |
| 3400 | + {"agent_id": "backup.local", "name": "local"}, |
| 3401 | + ] |
| 3402 | + |
| 3403 | + assert issue_registry.async_get_issue(domain=DOMAIN, issue_id=issue_id) |
| 3404 | + |
| 3405 | + await ws_client.send_json_auto_id({"type": "backup/config/info"}) |
| 3406 | + result = await ws_client.receive_json() |
| 3407 | + assert result["result"]["config"]["create_backup"]["agent_ids"] == [ |
| 3408 | + "backup.local", |
| 3409 | + "test.agent", |
| 3410 | + ] |
| 3411 | + |
| 3412 | + # Update the automatic backup configuration removing all agents. |
| 3413 | + |
| 3414 | + await ws_client.send_json_auto_id( |
| 3415 | + { |
| 3416 | + "type": "backup/config/update", |
| 3417 | + "create_backup": {"agent_ids": []}, |
| 3418 | + } |
| 3419 | + ) |
| 3420 | + result = await ws_client.receive_json() |
| 3421 | + |
| 3422 | + assert not issue_registry.async_get_issue(domain=DOMAIN, issue_id=issue_id) |
| 3423 | + |
| 3424 | + await ws_client.send_json_auto_id({"type": "backup/config/info"}) |
| 3425 | + result = await ws_client.receive_json() |
| 3426 | + assert result["result"]["config"]["create_backup"]["agent_ids"] == [] |
| 3427 | + |
| 3428 | + |
3247 | 3429 | async def test_subscribe_event( |
3248 | 3430 | hass: HomeAssistant, |
3249 | 3431 | hass_ws_client: WebSocketGenerator, |
|
0 commit comments