mirror of
https://github.com/home-assistant/core.git
synced 2025-07-19 19:27:45 +00:00
Add tests for cast skill action in Habitica (#129596)
This commit is contained in:
parent
03bc711c51
commit
4e2f5bdb7d
@ -454,7 +454,8 @@
|
||||
"createdAt": "2024-09-21T22:17:19.513Z",
|
||||
"updatedAt": "2024-09-21T22:19:35.576Z",
|
||||
"userId": "5f359083-ef78-4af0-985a-0b2c6d05797c",
|
||||
"id": "2f6fcabc-f670-4ec3-ba65-817e8deea490"
|
||||
"id": "2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
"alias": "pay_bills"
|
||||
},
|
||||
{
|
||||
"_id": "1aa3137e-ef72-4d1f-91ee-41933602f438",
|
||||
|
273
tests/components/habitica/test_services.py
Normal file
273
tests/components/habitica/test_services.py
Normal file
@ -0,0 +1,273 @@
|
||||
"""Test Habitica actions."""
|
||||
|
||||
from collections.abc import Generator
|
||||
from http import HTTPStatus
|
||||
from typing import Any
|
||||
from unittest.mock import patch
|
||||
|
||||
import pytest
|
||||
|
||||
from homeassistant.components.habitica.const import (
|
||||
ATTR_CONFIG_ENTRY,
|
||||
ATTR_SKILL,
|
||||
ATTR_TASK,
|
||||
DEFAULT_URL,
|
||||
DOMAIN,
|
||||
SERVICE_CAST_SKILL,
|
||||
)
|
||||
from homeassistant.config_entries import ConfigEntryState
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.exceptions import HomeAssistantError, ServiceValidationError
|
||||
|
||||
from .conftest import mock_called_with
|
||||
|
||||
from tests.common import MockConfigEntry
|
||||
from tests.test_util.aiohttp import AiohttpClientMocker
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def services_only() -> Generator[None]:
|
||||
"""Enable only services."""
|
||||
with patch(
|
||||
"homeassistant.components.habitica.PLATFORMS",
|
||||
[],
|
||||
):
|
||||
yield
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
async def load_entry(
|
||||
hass: HomeAssistant,
|
||||
config_entry: MockConfigEntry,
|
||||
mock_habitica: AiohttpClientMocker,
|
||||
services_only: Generator,
|
||||
) -> None:
|
||||
"""Load config entry."""
|
||||
config_entry.add_to_hass(hass)
|
||||
await hass.config_entries.async_setup(config_entry.entry_id)
|
||||
await hass.async_block_till_done()
|
||||
|
||||
assert config_entry.state is ConfigEntryState.LOADED
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
("service_data", "item", "target_id"),
|
||||
[
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
ATTR_SKILL: "pickpocket",
|
||||
},
|
||||
"pickPocket",
|
||||
"2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
ATTR_SKILL: "backstab",
|
||||
},
|
||||
"backStab",
|
||||
"2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
ATTR_SKILL: "fireball",
|
||||
},
|
||||
"fireball",
|
||||
"2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
"smash",
|
||||
"2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "Rechnungen bezahlen",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
"smash",
|
||||
"2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "pay_bills",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
"smash",
|
||||
"2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
),
|
||||
],
|
||||
ids=[
|
||||
"cast pickpocket",
|
||||
"cast backstab",
|
||||
"cast fireball",
|
||||
"cast smash",
|
||||
"select task by name",
|
||||
"select task_by_alias",
|
||||
],
|
||||
)
|
||||
async def test_cast_skill(
|
||||
hass: HomeAssistant,
|
||||
config_entry: MockConfigEntry,
|
||||
mock_habitica: AiohttpClientMocker,
|
||||
service_data: dict[str, Any],
|
||||
item: str,
|
||||
target_id: str,
|
||||
) -> None:
|
||||
"""Test Habitica cast skill action."""
|
||||
|
||||
mock_habitica.post(
|
||||
f"{DEFAULT_URL}/api/v3/user/class/cast/{item}?targetId={target_id}",
|
||||
json={"success": True, "data": {}},
|
||||
)
|
||||
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_CAST_SKILL,
|
||||
service_data={
|
||||
ATTR_CONFIG_ENTRY: config_entry.entry_id,
|
||||
**service_data,
|
||||
},
|
||||
return_response=True,
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
assert mock_called_with(
|
||||
mock_habitica,
|
||||
"post",
|
||||
f"{DEFAULT_URL}/api/v3/user/class/cast/{item}?targetId={target_id}",
|
||||
)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
(
|
||||
"service_data",
|
||||
"http_status",
|
||||
"expected_exception",
|
||||
"expected_exception_msg",
|
||||
),
|
||||
[
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "task-not-found",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
HTTPStatus.OK,
|
||||
ServiceValidationError,
|
||||
"Unable to cast skill, could not find the task 'task-not-found",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "Rechnungen bezahlen",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
HTTPStatus.TOO_MANY_REQUESTS,
|
||||
ServiceValidationError,
|
||||
"Currently rate limited, try again later",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "Rechnungen bezahlen",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
HTTPStatus.NOT_FOUND,
|
||||
ServiceValidationError,
|
||||
"Unable to cast skill, your character does not have the skill or spell smash",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "Rechnungen bezahlen",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
HTTPStatus.UNAUTHORIZED,
|
||||
ServiceValidationError,
|
||||
"Unable to cast skill, not enough mana. Your character has 50 MP, but the skill costs 10 MP",
|
||||
),
|
||||
(
|
||||
{
|
||||
ATTR_TASK: "Rechnungen bezahlen",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
HTTPStatus.BAD_REQUEST,
|
||||
HomeAssistantError,
|
||||
"Unable to connect to Habitica, try again later",
|
||||
),
|
||||
],
|
||||
)
|
||||
@pytest.mark.usefixtures("mock_habitica")
|
||||
async def test_cast_skill_exceptions(
|
||||
hass: HomeAssistant,
|
||||
config_entry: MockConfigEntry,
|
||||
mock_habitica: AiohttpClientMocker,
|
||||
service_data: dict[str, Any],
|
||||
http_status: HTTPStatus,
|
||||
expected_exception: Exception,
|
||||
expected_exception_msg: str,
|
||||
) -> None:
|
||||
"""Test Habitica cast skill action exceptions."""
|
||||
|
||||
mock_habitica.post(
|
||||
f"{DEFAULT_URL}/api/v3/user/class/cast/smash?targetId=2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
json={"success": True, "data": {}},
|
||||
status=http_status,
|
||||
)
|
||||
|
||||
with pytest.raises(expected_exception, match=expected_exception_msg):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_CAST_SKILL,
|
||||
service_data={
|
||||
ATTR_CONFIG_ENTRY: config_entry.entry_id,
|
||||
**service_data,
|
||||
},
|
||||
return_response=True,
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
|
||||
@pytest.mark.usefixtures("mock_habitica")
|
||||
async def test_get_config_entry(
|
||||
hass: HomeAssistant,
|
||||
config_entry: MockConfigEntry,
|
||||
mock_habitica: AiohttpClientMocker,
|
||||
) -> None:
|
||||
"""Test Habitica config entry exceptions."""
|
||||
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match="The selected character is not configured in Home Assistant",
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_CAST_SKILL,
|
||||
service_data={
|
||||
ATTR_CONFIG_ENTRY: "0000000000000000",
|
||||
ATTR_TASK: "2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
return_response=True,
|
||||
blocking=True,
|
||||
)
|
||||
|
||||
assert await hass.config_entries.async_unload(config_entry.entry_id)
|
||||
|
||||
with pytest.raises(
|
||||
ServiceValidationError,
|
||||
match="The selected character is currently not loaded or disabled in Home Assistant",
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_CAST_SKILL,
|
||||
service_data={
|
||||
ATTR_CONFIG_ENTRY: config_entry.entry_id,
|
||||
ATTR_TASK: "2f6fcabc-f670-4ec3-ba65-817e8deea490",
|
||||
ATTR_SKILL: "smash",
|
||||
},
|
||||
return_response=True,
|
||||
blocking=True,
|
||||
)
|
Loading…
x
Reference in New Issue
Block a user