agentx-python 0.8.6__py3-none-any.whl → 0.8.7__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
agentx/monitor/client.py CHANGED
@@ -3,7 +3,7 @@ from __future__ import annotations
3
3
  import logging
4
4
  import os
5
5
  import time
6
- from typing import Any, List, Optional
6
+ from typing import Any, Dict, List, Optional
7
7
 
8
8
  import requests
9
9
 
@@ -116,6 +116,10 @@ class MonitorClient:
116
116
  # The human-review queue (list / queue / label / dismiss) - what makes the
117
117
  # label-and-calibrate loop scriptable instead of dashboard-only.
118
118
  self.review_queue = ReviewQueueClient(self)
119
+ from agentx.monitor.rules import MonitorRulesClient
120
+
121
+ # Automation rules: route matching traffic into review / a dataset / a webhook.
122
+ self.rules = MonitorRulesClient(self)
119
123
  from agentx.monitor.scorers import ScorersClient
120
124
  # Scorers-catalog administration as code: template enable/disable, code/external scorer
121
125
  # CRUD and dry runs - full parity with the dashboard's Scorers page (P1.3).
@@ -264,6 +268,28 @@ class MonitorClient:
264
268
  plus deltas vs the prior window and the run-outcome breakdown."""
265
269
  return self._request("GET", "/kpis", params={"window": window})
266
270
 
271
+ def topics(self, window: str = "7d") -> dict:
272
+ """The Topics view's data over a window ("24h", "7d", "30d"): LLM-classified themes of
273
+ sampled production traffic with per-topic counts and sentiment. Empty until Topics is
274
+ enabled project-wide via ``set_topics(True)`` - classification spends one judge call
275
+ per sampled trace, so it is off by default."""
276
+ return self._request(
277
+ "GET", "/agent-monitoring/topics",
278
+ base=self._api_root(), params={"window": window},
279
+ )
280
+
281
+ def set_topics(self, enabled: bool, sample_rate: Optional[float] = None) -> dict:
282
+ """Turn Topics classification on/off for the whole project (Platform Settings >
283
+ Monitoring Defaults). ``sample_rate`` (0-1) optionally bounds what fraction of traffic
284
+ is classified - each classified trace costs one judge call."""
285
+ payload: Dict[str, Any] = {"topicsEnabled": enabled}
286
+ if sample_rate is not None:
287
+ payload["topicsSampleRate"] = sample_rate
288
+ return self._request(
289
+ "PUT", "/agent-monitoring/settings/monitoring-defaults",
290
+ base=self._api_root(), json=payload,
291
+ )
292
+
267
293
  def calibration(self, window: str = "7d") -> "CalibrationSummary":
268
294
  """Project-level judge calibration over a window ("24h", "7d", or "30d"): how often
269
295
  AgentX's own verdicts agreed with real-world ground truth reported later (ops outcomes
@@ -0,0 +1,78 @@
1
+ from __future__ import annotations
2
+
3
+ import logging
4
+ from typing import Any, Dict, List, Optional, TYPE_CHECKING
5
+
6
+ if TYPE_CHECKING:
7
+ from agentx.monitor.client import MonitorClient
8
+
9
+ logger = logging.getLogger(__name__)
10
+
11
+
12
+ class MonitorRule(dict):
13
+ """Wire object for one automation rule (dict subclass so unknown fields round-trip)."""
14
+
15
+ @property
16
+ def id(self) -> str:
17
+ return self["_id"]
18
+
19
+ @property
20
+ def enabled(self) -> bool:
21
+ return bool(self.get("enabled"))
22
+
23
+
24
+ class MonitorRulesClient:
25
+ """Surfaced as ``client.monitor.rules``: automation rules, evaluated on every ingested root
26
+ trace. A RULE routes traffic somewhere (it never scores): ``action`` is one of
27
+
28
+ - ``"review"`` - sample matching traces into the human-review queue (the stream that feeds
29
+ judge calibration and tuning),
30
+ - ``"dataset"`` - append matching traces as cases on a dataset (``action_config
31
+ {"datasetId": ...}``),
32
+ - ``"webhook"`` - POST the matching trace to your URL (``action_config {"url": ...}``).
33
+
34
+ ``filter`` narrows what matches: ``{"model": ..., "status": "error"|"any", "contains": ...,
35
+ "scopeMode": "all"|"selected", "agentIds": [...]}``; ``sample_rate`` (0-1, default 1)
36
+ down-samples the matches.
37
+ """
38
+
39
+ def __init__(self, client: "MonitorClient"):
40
+ self._client = client
41
+
42
+ def _request(self, method: str, path: str, **kwargs: Any) -> Any:
43
+ return self._client._request(method, path, base=self._client._api_root(), **kwargs)
44
+
45
+ def list(self) -> List[MonitorRule]:
46
+ data = self._request("GET", "/agent-monitoring/rules")
47
+ return [MonitorRule(r) for r in data.get("rules", [])]
48
+
49
+ def create(
50
+ self,
51
+ name: str,
52
+ action: str,
53
+ *,
54
+ filter: Optional[Dict[str, Any]] = None,
55
+ sample_rate: Optional[float] = None,
56
+ action_config: Optional[Dict[str, Any]] = None,
57
+ enabled: bool = True,
58
+ ) -> MonitorRule:
59
+ payload: Dict[str, Any] = {"name": name, "action": action, "enabled": enabled}
60
+ if filter is not None:
61
+ payload["filter"] = filter
62
+ if sample_rate is not None:
63
+ payload["sampleRate"] = sample_rate
64
+ if action_config is not None:
65
+ payload["actionConfig"] = action_config
66
+ data = self._request("POST", "/agent-monitoring/rules", json=payload)
67
+ return MonitorRule(data.get("rule", data))
68
+
69
+ def update(self, rule_id: str, **fields: Any) -> MonitorRule:
70
+ """Sparse update. snake_case keys are mapped to the wire (``sample_rate`` ->
71
+ ``sampleRate``, ``action_config`` -> ``actionConfig``)."""
72
+ aliases = {"sample_rate": "sampleRate", "action_config": "actionConfig"}
73
+ payload = {aliases.get(k, k): v for k, v in fields.items()}
74
+ data = self._request("PUT", f"/agent-monitoring/rules/{rule_id}", json=payload)
75
+ return MonitorRule(data.get("rule", data))
76
+
77
+ def delete(self, rule_id: str) -> None:
78
+ self._request("DELETE", f"/agent-monitoring/rules/{rule_id}")
agentx/version.py CHANGED
@@ -1 +1 @@
1
- VERSION = "0.8.6"
1
+ VERSION = "0.8.7"
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: agentx-python
3
- Version: 0.8.6
3
+ Version: 0.8.7
4
4
  Summary: Official Python SDK for AgentX (https://www.agentx.so/)
5
5
  Home-page: https://github.com/AgentX-ai/AgentX-python
6
6
  Author: Robin Wang and AgentX Team
@@ -10,7 +10,7 @@ agentx/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
10
10
  agentx/testing.py,sha256=0shZEid_vhJgBegpO_loUq6APYDxQrUgD3jvcRdIDV8,7372
11
11
  agentx/traces.py,sha256=sz9gxutlDKNgf0fdCkyzKsGwK5eMAJuIEl3NIwGrsuo,2287
12
12
  agentx/util.py,sha256=lt2Kpg4Fj8whrSuAhLEahcPEIYRVpK9RCC5y9ShdTJs,703
13
- agentx/version.py,sha256=hmHiHLKwWDl96GTl8BU-lEqkwGqsS8wHvMMNnaUkHZc,18
13
+ agentx/version.py,sha256=kG_bb-Ryd4AoiM5iOElOryBDv_WEdw73ouYtbd5SIQE,18
14
14
  agentx/evaluations/__init__.py,sha256=Erv7RGFlRxGTG4rVb2uHhCqLLEX_iAWKqkZKzK6CumE,262
15
15
  agentx/evaluations/_term.py,sha256=WFpiNzdgDBeJJ-Gg-6X7TwwxllobuE4OqFUTuDQvS3Y,2529
16
16
  agentx/evaluations/client.py,sha256=miUmEq4IthUDl-QVAczqT7iaOu4X6QMbHhlm2rSSJpg,31239
@@ -43,13 +43,14 @@ agentx/integrations/openai.py,sha256=1KLs-hJaeW2emHPwNkmC3zcGksL3zd87uWbcLGRW704
43
43
  agentx/integrations/openai_agents.py,sha256=tCa3kPxqux5LnNNDQ6zA05OybQrjkc_LeE08YuNPJEs,12742
44
44
  agentx/monitor/__init__.py,sha256=MLiASSvQnCy2jqVNRTgPWFhUSf8lGYRQeEgEVVhE5Tg,574
45
45
  agentx/monitor/agents.py,sha256=8Xk4jWmNTvdtjFixHiLmw4jj96uqIXWIT6KW8zXoWrc,1006
46
- agentx/monitor/client.py,sha256=PNhtuBRrJvrtgA3gjm4ZN7dpb0BFTi-samNCo15hr2M,18336
46
+ agentx/monitor/client.py,sha256=XUecRuhWM80_dlKFCHORp9TPWN80XM5SApkGRTFedX4,19724
47
47
  agentx/monitor/judge_scorers.py,sha256=Mu6OOnfjp1SRkZMcOyriO7zPawv-O2H2l2X-0io5WLM,15025
48
48
  agentx/monitor/models.py,sha256=yTC3WTdTziHMkdeAXlTro-4YiSbBUHMgf9kNZHGfPDA,8470
49
49
  agentx/monitor/online_evaluators.py,sha256=YWnsBmlIbYvj4LCaX4guwx4HS5y3oEzCQfo6ae9VH_w,8693
50
50
  agentx/monitor/patterns.py,sha256=ruBqLoA2T2KQuqRbbn1kWkIEkiOal3SvyPl9opGyhzI,4185
51
51
  agentx/monitor/profile.py,sha256=uGk-4bXT2vmnEQiY5u6rWhAfzZchHBXL74VD3piVHvU,3102
52
52
  agentx/monitor/review_queue.py,sha256=Tr3GDMJLJzyFKEEeB8HPmZBsNzzYVJYElDlfBC4qd68,3766
53
+ agentx/monitor/rules.py,sha256=oLQ5RPgMPUKJFTSZzcBEMLzDlICElUNJTyIqxZMAGmQ,3040
53
54
  agentx/monitor/scorers.py,sha256=huIZBszrfLKI8I7VV6NFpW6piRsj9HI03rXUwWs2tgs,7336
54
55
  agentx/monitor/sessions.py,sha256=gePcL284m3UITxQAtHxwrKFl6bRjmRib1QK6JbZeS9s,815
55
56
  agentx/monitor/signals.py,sha256=Ld11lW2lbg8NHBUHdgoY6iwCvJDK-eg4ge4qQ9y7nGY,1432
@@ -62,9 +63,9 @@ agentx/tracing/ci_types.py,sha256=zFVcZGvc1qbVDdOlEPQ1i5R6terqJHxCzFF4ZjouxxI,14
62
63
  agentx/tracing/eval_scope.py,sha256=ElMbPxpqpQBVuaUnHNlw9RIQu71oyOpd0yR55bDH8eI,2144
63
64
  agentx/tracing/ingest_client.py,sha256=5X6RyxtMq1XYgOzsMd3b2f2qpmYpsMnhKm7NB3oup00,17664
64
65
  agentx/tracing/tracer.py,sha256=qQojU-T4O8IJKyf9vue0Em66qPBTZKl3FMyr3KJKPnI,53770
65
- agentx_python-0.8.6.dist-info/licenses/LICENSE,sha256=gZVsM-nLsE8vlaY6NXXsVoo6IlCClxkToAWmhgT3y_s,10762
66
- agentx_python-0.8.6.dist-info/METADATA,sha256=TtgnRoXPHmbRAmTFBQpjX7iN4Eq5-g6znYgTgZHc0uY,20992
67
- agentx_python-0.8.6.dist-info/WHEEL,sha256=aeYiig01lYGDzBgS8HxWXOg3uV61G9ijOsup-k9o1sk,91
68
- agentx_python-0.8.6.dist-info/entry_points.txt,sha256=rQqF1JTY3T1yfviBU1r8PU-5mBdfOk6P4bZ1L4BskIM,172
69
- agentx_python-0.8.6.dist-info/top_level.txt,sha256=s-q-HB9Gb_QdrZNacSeQyF_c25gQooMy7DlxzgLOHPk,7
70
- agentx_python-0.8.6.dist-info/RECORD,,
66
+ agentx_python-0.8.7.dist-info/licenses/LICENSE,sha256=gZVsM-nLsE8vlaY6NXXsVoo6IlCClxkToAWmhgT3y_s,10762
67
+ agentx_python-0.8.7.dist-info/METADATA,sha256=aZ0vtzylZ2kxkbb5f5jdSDaNmchZreVE-dzKnl33yCA,20992
68
+ agentx_python-0.8.7.dist-info/WHEEL,sha256=aeYiig01lYGDzBgS8HxWXOg3uV61G9ijOsup-k9o1sk,91
69
+ agentx_python-0.8.7.dist-info/entry_points.txt,sha256=rQqF1JTY3T1yfviBU1r8PU-5mBdfOk6P4bZ1L4BskIM,172
70
+ agentx_python-0.8.7.dist-info/top_level.txt,sha256=s-q-HB9Gb_QdrZNacSeQyF_c25gQooMy7DlxzgLOHPk,7
71
+ agentx_python-0.8.7.dist-info/RECORD,,