agent0-sdk 0.2.2__py3-none-any.whl → 0.3rc1__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.
- agent0_sdk/__init__.py +1 -1
- agent0_sdk/core/contracts.py +7 -0
- agent0_sdk/core/feedback_manager.py +101 -1
- agent0_sdk/core/indexer.py +733 -11
- agent0_sdk/core/models.py +3 -2
- agent0_sdk/core/sdk.py +207 -4
- agent0_sdk/core/subgraph_client.py +23 -3
- {agent0_sdk-0.2.2.dist-info → agent0_sdk-0.3rc1.dist-info}/METADATA +1 -2
- {agent0_sdk-0.2.2.dist-info → agent0_sdk-0.3rc1.dist-info}/RECORD +14 -12
- tests/discover_test_data.py +445 -0
- tests/test_multi_chain.py +588 -0
- {agent0_sdk-0.2.2.dist-info → agent0_sdk-0.3rc1.dist-info}/WHEEL +0 -0
- {agent0_sdk-0.2.2.dist-info → agent0_sdk-0.3rc1.dist-info}/licenses/LICENSE +0 -0
- {agent0_sdk-0.2.2.dist-info → agent0_sdk-0.3rc1.dist-info}/top_level.txt +0 -0
agent0_sdk/__init__.py
CHANGED
agent0_sdk/core/contracts.py
CHANGED
|
@@ -477,6 +477,11 @@ DEFAULT_REGISTRIES: Dict[int, Dict[str, str]] = {
|
|
|
477
477
|
"REPUTATION": "0x8004bd8daB57f14Ed299135749a5CB5c42d341BF",
|
|
478
478
|
"VALIDATION": "0x8004C269D0A5647E51E121FeB226200ECE932d55",
|
|
479
479
|
},
|
|
480
|
+
80002: { # Polygon Amoy
|
|
481
|
+
"IDENTITY": "0x8004ad19E14B9e0654f73353e8a0B600D46C2898",
|
|
482
|
+
"REPUTATION": "0x8004B12F4C2B42d00c46479e859C92e39044C930",
|
|
483
|
+
"VALIDATION": "0x8004C11C213ff7BaD36489bcBDF947ba5eee289B",
|
|
484
|
+
},
|
|
480
485
|
59141: { # Linea Sepolia
|
|
481
486
|
"IDENTITY": "0x8004aa7C931bCE1233973a0C6A667f73F66282e7",
|
|
482
487
|
"REPUTATION": "0x8004bd8483b99310df121c46ED8858616b2Bba02",
|
|
@@ -487,4 +492,6 @@ DEFAULT_REGISTRIES: Dict[int, Dict[str, str]] = {
|
|
|
487
492
|
# Default subgraph URLs for different chains
|
|
488
493
|
DEFAULT_SUBGRAPH_URLS: Dict[int, str] = {
|
|
489
494
|
11155111: "https://gateway.thegraph.com/api/00a452ad3cd1900273ea62c1bf283f93/subgraphs/id/6wQRC7geo9XYAhckfmfo8kbMRLeWU8KQd3XsJqFKmZLT", # Ethereum Sepolia
|
|
495
|
+
84532: "https://gateway.thegraph.com/api/00a452ad3cd1900273ea62c1bf283f93/subgraphs/id/GjQEDgEKqoh5Yc8MUgxoQoRATEJdEiH7HbocfR1aFiHa", # Base Sepolia
|
|
496
|
+
80002: "https://gateway.thegraph.com/api/00a452ad3cd1900273ea62c1bf283f93/subgraphs/id/2A1JB18r1mF2VNP4QBH4mmxd74kbHoM6xLXC8ABAKf7j", # Polygon Amoy
|
|
490
497
|
}
|
|
@@ -703,7 +703,46 @@ class FeedbackManager:
|
|
|
703
703
|
groupBy: Optional[List[str]] = None,
|
|
704
704
|
) -> Dict[str, Any]:
|
|
705
705
|
"""Get reputation summary for an agent with optional grouping."""
|
|
706
|
-
# Parse
|
|
706
|
+
# Parse chainId from agentId
|
|
707
|
+
chain_id = None
|
|
708
|
+
if ":" in agentId:
|
|
709
|
+
try:
|
|
710
|
+
chain_id = int(agentId.split(":", 1)[0])
|
|
711
|
+
except ValueError:
|
|
712
|
+
chain_id = None
|
|
713
|
+
|
|
714
|
+
# Try subgraph first (if available and indexer supports it)
|
|
715
|
+
if self.indexer and self.subgraph_client:
|
|
716
|
+
# Get correct subgraph client for the chain
|
|
717
|
+
subgraph_client = None
|
|
718
|
+
full_agent_id = agentId
|
|
719
|
+
|
|
720
|
+
if chain_id is not None:
|
|
721
|
+
subgraph_client = self.indexer._get_subgraph_client_for_chain(chain_id)
|
|
722
|
+
else:
|
|
723
|
+
# No chainId in agentId, use SDK's default
|
|
724
|
+
# Construct full agentId format for subgraph query
|
|
725
|
+
default_chain_id = self.web3_client.chain_id
|
|
726
|
+
token_id = agentId.split(":")[-1] if ":" in agentId else agentId
|
|
727
|
+
full_agent_id = f"{default_chain_id}:{token_id}"
|
|
728
|
+
subgraph_client = self.subgraph_client
|
|
729
|
+
|
|
730
|
+
if subgraph_client:
|
|
731
|
+
# Use subgraph to calculate reputation
|
|
732
|
+
return self._get_reputation_summary_from_subgraph(
|
|
733
|
+
full_agent_id, clientAddresses, tag1, tag2, groupBy
|
|
734
|
+
)
|
|
735
|
+
|
|
736
|
+
# Fallback to blockchain (requires chain-specific web3 client)
|
|
737
|
+
# For now, only works if chain matches SDK's default
|
|
738
|
+
if chain_id is not None and chain_id != self.web3_client.chain_id:
|
|
739
|
+
raise ValueError(
|
|
740
|
+
f"Blockchain reputation summary not supported for chain {chain_id}. "
|
|
741
|
+
f"SDK is configured for chain {self.web3_client.chain_id}. "
|
|
742
|
+
f"Use subgraph-based summary instead."
|
|
743
|
+
)
|
|
744
|
+
|
|
745
|
+
# Parse agent ID for blockchain call
|
|
707
746
|
if ":" in agentId:
|
|
708
747
|
tokenId = int(agentId.split(":")[-1])
|
|
709
748
|
else:
|
|
@@ -765,6 +804,67 @@ class FeedbackManager:
|
|
|
765
804
|
except Exception as e:
|
|
766
805
|
raise ValueError(f"Failed to get reputation summary: {e}")
|
|
767
806
|
|
|
807
|
+
def _get_reputation_summary_from_subgraph(
|
|
808
|
+
self,
|
|
809
|
+
agentId: AgentId,
|
|
810
|
+
clientAddresses: Optional[List[Address]] = None,
|
|
811
|
+
tag1: Optional[str] = None,
|
|
812
|
+
tag2: Optional[str] = None,
|
|
813
|
+
groupBy: Optional[List[str]] = None,
|
|
814
|
+
) -> Dict[str, Any]:
|
|
815
|
+
"""Get reputation summary from subgraph."""
|
|
816
|
+
# Build tags list
|
|
817
|
+
tags = []
|
|
818
|
+
if tag1:
|
|
819
|
+
tags.append(tag1)
|
|
820
|
+
if tag2:
|
|
821
|
+
tags.append(tag2)
|
|
822
|
+
|
|
823
|
+
# Get all feedback for the agent using indexer (which handles multi-chain)
|
|
824
|
+
# Use searchFeedback with a large limit to get all feedback
|
|
825
|
+
all_feedback = self.searchFeedback(
|
|
826
|
+
agentId=agentId,
|
|
827
|
+
clientAddresses=clientAddresses,
|
|
828
|
+
tags=tags if tags else None,
|
|
829
|
+
include_revoked=False,
|
|
830
|
+
first=1000, # Large limit to get all feedback
|
|
831
|
+
skip=0
|
|
832
|
+
)
|
|
833
|
+
|
|
834
|
+
# Calculate summary statistics
|
|
835
|
+
count = len(all_feedback)
|
|
836
|
+
scores = [fb.score for fb in all_feedback if fb.score is not None]
|
|
837
|
+
average_score = sum(scores) / len(scores) if scores else 0.0
|
|
838
|
+
|
|
839
|
+
# If no grouping requested, return simple summary
|
|
840
|
+
if not groupBy:
|
|
841
|
+
return {
|
|
842
|
+
"agentId": agentId,
|
|
843
|
+
"count": count,
|
|
844
|
+
"averageScore": average_score,
|
|
845
|
+
"filters": {
|
|
846
|
+
"clientAddresses": clientAddresses,
|
|
847
|
+
"tag1": tag1,
|
|
848
|
+
"tag2": tag2
|
|
849
|
+
}
|
|
850
|
+
}
|
|
851
|
+
|
|
852
|
+
# Group feedback by requested dimensions
|
|
853
|
+
grouped_data = self._groupFeedback(all_feedback, groupBy)
|
|
854
|
+
|
|
855
|
+
return {
|
|
856
|
+
"agentId": agentId,
|
|
857
|
+
"totalCount": count,
|
|
858
|
+
"totalAverageScore": average_score,
|
|
859
|
+
"groupedData": grouped_data,
|
|
860
|
+
"filters": {
|
|
861
|
+
"clientAddresses": clientAddresses,
|
|
862
|
+
"tag1": tag1,
|
|
863
|
+
"tag2": tag2
|
|
864
|
+
},
|
|
865
|
+
"groupBy": groupBy
|
|
866
|
+
}
|
|
867
|
+
|
|
768
868
|
def _groupFeedback(self, feedbackList: List[Feedback], groupBy: List[str]) -> Dict[str, Any]:
|
|
769
869
|
"""Group feedback by specified dimensions."""
|
|
770
870
|
grouped = {}
|