Skip to content

Commit 56b427d

Browse files
committed
test(tools): add Azure Monitor Logs tool unit tests
1 parent 72dc93b commit 56b427d

1 file changed

Lines changed: 160 additions & 0 deletions

File tree

Lines changed: 160 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,160 @@
1+
"""Tests for AzureMonitorLogsTool (function-based, @tool decorated)."""
2+
3+
from __future__ import annotations
4+
5+
from typing import Any, cast
6+
from unittest.mock import MagicMock
7+
8+
import pytest
9+
10+
from app.tools.AzureMonitorLogsTool import (
11+
_bounded_limit,
12+
query_azure_monitor_logs,
13+
)
14+
from tests.tools.conftest import BaseToolContract
15+
16+
17+
def _registered_tool() -> Any:
18+
return cast(Any, query_azure_monitor_logs).__opensre_registered_tool__
19+
20+
21+
class TestAzureMonitorLogsToolContract(BaseToolContract):
22+
def get_tool_under_test(self):
23+
return _registered_tool()
24+
25+
26+
@pytest.mark.parametrize(
27+
"sources,expected",
28+
[
29+
(
30+
{
31+
"azure": {
32+
"connection_verified": True,
33+
"workspace_id": "workspace-123",
34+
"access_token": "token-abc",
35+
}
36+
},
37+
True,
38+
),
39+
(
40+
{
41+
"azure": {
42+
"connection_verified": False,
43+
"workspace_id": "workspace-123",
44+
"access_token": "token-abc",
45+
}
46+
},
47+
False,
48+
),
49+
(
50+
{
51+
"azure": {
52+
"connection_verified": True,
53+
"workspace_id": "",
54+
"access_token": "token-abc",
55+
}
56+
},
57+
False,
58+
),
59+
(
60+
{
61+
"azure": {
62+
"connection_verified": True,
63+
"workspace_id": "workspace-123",
64+
"access_token": "",
65+
}
66+
},
67+
False,
68+
),
69+
],
70+
)
71+
def test_is_available_requires_verified_workspace_and_token(sources: dict, expected: bool) -> None:
72+
rt = _registered_tool()
73+
assert rt.is_available(sources) is expected
74+
75+
76+
def test_extract_params_maps_fields_and_defaults() -> None:
77+
rt = _registered_tool()
78+
params = rt.extract_params(
79+
{
80+
"azure": {
81+
"workspace_id": " workspace-123 ",
82+
"access_token": " token-abc ",
83+
"endpoint": " https://api.loganalytics.io ",
84+
}
85+
}
86+
)
87+
88+
assert params["workspace_id"] == "workspace-123"
89+
assert params["access_token"] == "token-abc"
90+
assert params["endpoint"] == "https://api.loganalytics.io"
91+
assert params["time_range_minutes"] == 60
92+
assert params["limit"] == 50
93+
94+
95+
def test_bounded_limit_caps_requested_limit() -> None:
96+
assert _bounded_limit(300, 100) == 100
97+
98+
99+
def test_run_happy_path(monkeypatch: pytest.MonkeyPatch) -> None:
100+
mocked_response = MagicMock()
101+
mocked_response.raise_for_status.return_value = None
102+
mocked_response.json.return_value = {
103+
"tables": [
104+
{
105+
"columns": [
106+
{"name": "TimeGenerated"},
107+
{"name": "Message"},
108+
],
109+
"rows": [
110+
["2026-04-27T10:00:00Z", "error: failed to connect"],
111+
["2026-04-27T10:01:00Z", "info: retry succeeded"],
112+
],
113+
}
114+
]
115+
}
116+
117+
monkeypatch.setattr(
118+
"app.tools.AzureMonitorLogsTool.httpx.post",
119+
lambda *_args, **_kwargs: mocked_response,
120+
)
121+
122+
result = query_azure_monitor_logs(
123+
workspace_id="workspace-123",
124+
access_token="token-abc",
125+
query="AppTraces | order by TimeGenerated desc",
126+
limit=2,
127+
)
128+
129+
assert result["available"] is True
130+
assert result["source"] == "azure"
131+
assert result["total_returned"] == 2
132+
assert result["rows"][0]["Message"] == "error: failed to connect"
133+
134+
135+
def test_run_http_error_path(monkeypatch: pytest.MonkeyPatch) -> None:
136+
mocked_response = MagicMock()
137+
mocked_response.raise_for_status.side_effect = Exception("401 Client Error: Unauthorized")
138+
mocked_response.json.return_value = {}
139+
140+
monkeypatch.setattr(
141+
"app.tools.AzureMonitorLogsTool.httpx.post",
142+
lambda *_args, **_kwargs: mocked_response,
143+
)
144+
145+
result = query_azure_monitor_logs(
146+
workspace_id="workspace-123",
147+
access_token="token-abc",
148+
query="AppTraces",
149+
)
150+
151+
assert "error" in result
152+
assert "401" in result["error"]
153+
assert result["source"] == "azure"
154+
155+
156+
def test_run_unavailable_without_credentials() -> None:
157+
result = query_azure_monitor_logs(workspace_id="", access_token="", query="AppTraces")
158+
159+
assert result["available"] is False
160+
assert "missing azure credentials" in result["error"].lower()

0 commit comments

Comments
 (0)