agentx-python 0.6.33__tar.gz → 0.6.34__tar.gz
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_python-0.6.33 → agentx_python-0.6.34}/PKG-INFO +1 -1
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/agentx.py +6 -0
- agentx_python-0.6.34/agentx/export.py +97 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/client.py +11 -0
- agentx_python-0.6.34/agentx/version.py +1 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx_python.egg-info/PKG-INFO +1 -1
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx_python.egg-info/SOURCES.txt +1 -0
- agentx_python-0.6.33/agentx/version.py +0 -1
- {agentx_python-0.6.33 → agentx_python-0.6.34}/LICENSE +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/README.md +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/__init__.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/cli.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/__init__.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/_term.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/adapters/__init__.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/adapters/http_endpoint.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/adapters/precomputed.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/adapters/raw.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/client.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/datasets.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/evaluation_settings.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/models.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/prompts.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/reporting.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/results.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/runner.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/tool_schemas.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/evaluations/tracing.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/exceptions.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/feedback.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/__init__.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/_traced_call.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/anthropic.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/autogen.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/crewai.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/databricks.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/google_adk.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/google_genai.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/langchain.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/litellm.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/llamaindex.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/moveworks.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/openai.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/integrations/openai_agents.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/__init__.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/agents.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/models.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/online_evaluators.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/patterns.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/profile.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/scorers.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/sessions.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/monitor/signals.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/outcomes.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/projects.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/py.typed +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/resources/__init__.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/resources/agent.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/resources/conversation.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/resources/workforce.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/traces.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/tracing/__init__.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/tracing/ci_types.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/tracing/ingest_client.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/tracing/tracer.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx/util.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx_python.egg-info/dependency_links.txt +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx_python.egg-info/entry_points.txt +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx_python.egg-info/not-zip-safe +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx_python.egg-info/requires.txt +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/agentx_python.egg-info/top_level.txt +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/setup.cfg +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/setup.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/tests/test_integration.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/tests/test_integrations.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/tests/test_selfhost_analysis_fallback.py +0 -0
- {agentx_python-0.6.33 → agentx_python-0.6.34}/tests/test_span_tree.py +0 -0
|
@@ -70,6 +70,12 @@ class AgentX:
|
|
|
70
70
|
# The read side of tracing: trace-by-id detail and paginated listing (P1.2).
|
|
71
71
|
self.traces = TracesClient(api_key=self.api_key)
|
|
72
72
|
|
|
73
|
+
from agentx.export import ExportClient
|
|
74
|
+
|
|
75
|
+
# Bulk NDJSON egress for backup/migration (P2.1): manifest, per-entity streaming, and
|
|
76
|
+
# directory dumps. Self-host only.
|
|
77
|
+
self.export = ExportClient(api_key=self.api_key)
|
|
78
|
+
|
|
73
79
|
from agentx.feedback import FeedbackClient
|
|
74
80
|
|
|
75
81
|
# Forward end-user votes ("up"/"down") on traced responses - a "down" raises a signal
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import json
|
|
4
|
+
import logging
|
|
5
|
+
import os
|
|
6
|
+
from typing import Any, Dict, Iterator, List, Optional
|
|
7
|
+
|
|
8
|
+
import requests
|
|
9
|
+
|
|
10
|
+
from agentx.util import api_base, get_headers
|
|
11
|
+
|
|
12
|
+
logger = logging.getLogger(__name__)
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
class AgentXExportError(Exception):
|
|
16
|
+
pass
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
class ExportClient:
|
|
20
|
+
"""Surfaced as ``client.export``: bulk NDJSON egress for backup and migration (self-host).
|
|
21
|
+
|
|
22
|
+
The engine's ``GET /export`` manifest lists every exportable entity (traces, signals,
|
|
23
|
+
events, runs, feedback, outcomes, scorer config, ...) with live row counts;
|
|
24
|
+
``GET /export/<entity>`` streams the rows as NDJSON. Everything is scoped to the API key's
|
|
25
|
+
project, so an export can never cross a tenant boundary.
|
|
26
|
+
|
|
27
|
+
Typical uses::
|
|
28
|
+
|
|
29
|
+
client.export.dump("./backup") # full backup, one .ndjson per entity
|
|
30
|
+
client.export.dump("./nightly", since=yesterday) # incremental
|
|
31
|
+
for row in client.export.iter("traces"): # stream without touching disk
|
|
32
|
+
...
|
|
33
|
+
|
|
34
|
+
Restore paths are documented in the self-host backup runbook: replay traces through
|
|
35
|
+
``client.tracer`` / ``POST /ingest/traces``, or restore at the database level
|
|
36
|
+
(``pg_dump`` / SQLite file copy). There is deliberately no blind row-import endpoint.
|
|
37
|
+
"""
|
|
38
|
+
|
|
39
|
+
def __init__(self, api_key: Optional[str] = None):
|
|
40
|
+
self._api_key = api_key
|
|
41
|
+
|
|
42
|
+
def manifest(self) -> List[Dict[str, Any]]:
|
|
43
|
+
"""The exportable entities with live row counts: ``[{entity, rows, path}, ...]``."""
|
|
44
|
+
resp = requests.get(
|
|
45
|
+
f"{api_base()}/export", headers=get_headers(self._api_key), timeout=30
|
|
46
|
+
)
|
|
47
|
+
if resp.status_code >= 400:
|
|
48
|
+
raise AgentXExportError(f"Export manifest failed ({resp.status_code}): {resp.text[:200]}")
|
|
49
|
+
return resp.json().get("entities", [])
|
|
50
|
+
|
|
51
|
+
def iter(self, entity: str, since: Optional[str] = None) -> Iterator[Dict[str, Any]]:
|
|
52
|
+
"""Stream one entity's rows as dicts without buffering the whole table in memory.
|
|
53
|
+
``since`` is an ISO-8601 date for incremental pulls (filters on the entity's own
|
|
54
|
+
timestamp column, e.g. ``createdAt`` for traces, ``lastSeenAt`` for signals)."""
|
|
55
|
+
params = {"since": since} if since else None
|
|
56
|
+
resp = requests.get(
|
|
57
|
+
f"{api_base()}/export/{entity}",
|
|
58
|
+
headers=get_headers(self._api_key),
|
|
59
|
+
params=params,
|
|
60
|
+
stream=True,
|
|
61
|
+
timeout=120,
|
|
62
|
+
)
|
|
63
|
+
if resp.status_code >= 400:
|
|
64
|
+
raise AgentXExportError(f"Export of {entity!r} failed ({resp.status_code}): {resp.text[:200]}")
|
|
65
|
+
for line in resp.iter_lines(decode_unicode=True):
|
|
66
|
+
if line and line.strip():
|
|
67
|
+
yield json.loads(line)
|
|
68
|
+
|
|
69
|
+
def dump(
|
|
70
|
+
self,
|
|
71
|
+
directory: str,
|
|
72
|
+
entities: Optional[List[str]] = None,
|
|
73
|
+
since: Optional[str] = None,
|
|
74
|
+
) -> Dict[str, int]:
|
|
75
|
+
"""Write ``<entity>.ndjson`` files (plus a ``manifest.json``) into ``directory`` and
|
|
76
|
+
return ``{entity: rows_written}``. Defaults to every entity the engine advertises;
|
|
77
|
+
pass ``entities`` to restrict, ``since`` for an incremental snapshot."""
|
|
78
|
+
os.makedirs(directory, exist_ok=True)
|
|
79
|
+
manifest = self.manifest()
|
|
80
|
+
wanted = [e["entity"] for e in manifest] if entities is None else entities
|
|
81
|
+
written: Dict[str, int] = {}
|
|
82
|
+
for entity in wanted:
|
|
83
|
+
path = os.path.join(directory, f"{entity}.ndjson")
|
|
84
|
+
count = 0
|
|
85
|
+
with open(path, "w", encoding="utf-8") as fh:
|
|
86
|
+
for row in self.iter(entity, since=since):
|
|
87
|
+
fh.write(json.dumps(row, ensure_ascii=False) + "\n")
|
|
88
|
+
count += 1
|
|
89
|
+
written[entity] = count
|
|
90
|
+
logger.debug("Exported %d %s rows to %s", count, entity, path)
|
|
91
|
+
with open(os.path.join(directory, "manifest.json"), "w", encoding="utf-8") as fh:
|
|
92
|
+
json.dump(
|
|
93
|
+
{"entities": manifest, "written": written, **({"since": since} if since else {})},
|
|
94
|
+
fh,
|
|
95
|
+
indent=2,
|
|
96
|
+
)
|
|
97
|
+
return written
|
|
@@ -213,6 +213,17 @@ class MonitorClient:
|
|
|
213
213
|
plus deltas vs the prior window and the run-outcome breakdown."""
|
|
214
214
|
return self._request("GET", "/kpis", params={"window": window})
|
|
215
215
|
|
|
216
|
+
def calibration(self, window: str = "7d") -> dict:
|
|
217
|
+
"""Project-level judge calibration over a window ("24h", "7d", or "30d"): how often
|
|
218
|
+
AgentX's own verdicts agreed with real-world ground truth reported later (ops outcomes
|
|
219
|
+
via ``client.outcomes`` and end-user downvotes). Returns the dashboard's Judge
|
|
220
|
+
Calibration numbers: compared count, agreement, falsePositiveRate, falseNegativeRate.
|
|
221
|
+
Per-evaluator calibration lives on ``client.monitor.online_evaluators.calibration``."""
|
|
222
|
+
return self._request(
|
|
223
|
+
"GET", "/agent-monitoring/calibration",
|
|
224
|
+
base=self._api_root(), params={"window": window},
|
|
225
|
+
)
|
|
226
|
+
|
|
216
227
|
# ------------------------------------------------------------------
|
|
217
228
|
# Signal endpoints
|
|
218
229
|
# ------------------------------------------------------------------
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
VERSION = "0.6.34"
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
VERSION = "0.6.33"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|