mech-client 0.3.0__py3-none-any.whl → 0.6.0__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.
- mech_client/__init__.py +1 -1
- mech_client/abis/AgentMech.json +718 -0
- mech_client/abis/AgentRegistry.json +1037 -0
- mech_client/abis/AgreementStoreManager.base.json +766 -0
- mech_client/abis/AgreementStoreManager.gnosis.json +766 -0
- mech_client/abis/BalanceTrackerNvmSubscriptionToken.json +660 -0
- mech_client/abis/DIDRegistry.base.json +2476 -0
- mech_client/abis/DIDRegistry.gnosis.json +2476 -0
- mech_client/abis/EscrowPaymentCondition.base.json +717 -0
- mech_client/abis/EscrowPaymentCondition.gnosis.json +717 -0
- mech_client/abis/LockPaymentCondition.base.json +874 -0
- mech_client/abis/LockPaymentCondition.gnosis.json +874 -0
- mech_client/abis/NFTSalesTemplate.base.json +698 -0
- mech_client/abis/NFTSalesTemplate.gnosis.json +698 -0
- mech_client/abis/NeverminedConfig.base.json +587 -0
- mech_client/abis/NeverminedConfig.gnosis.json +587 -0
- mech_client/abis/SubscriptionNFT.base.json +300 -0
- mech_client/abis/SubscriptionNFT.gnosis.json +300 -0
- mech_client/abis/SubscriptionToken.base.json +1393 -0
- mech_client/abis/TransferNFTCondition.base.json +1062 -0
- mech_client/abis/TransferNFTCondition.gnosis.json +1062 -0
- mech_client/cli.py +99 -10
- mech_client/configs/mechs.json +3 -9
- mech_client/interact.py +14 -39
- mech_client/marketplace_interact.py +199 -156
- mech_client/mech_tool_management.py +11 -5
- mech_client/subgraph.py +21 -35
- mech_client/wss.py +7 -6
- {mech_client-0.3.0.dist-info → mech_client-0.6.0.dist-info}/METADATA +45 -13
- {mech_client-0.3.0.dist-info → mech_client-0.6.0.dist-info}/RECORD +33 -13
- {mech_client-0.3.0.dist-info → mech_client-0.6.0.dist-info}/LICENSE +0 -0
- {mech_client-0.3.0.dist-info → mech_client-0.6.0.dist-info}/WHEEL +0 -0
- {mech_client-0.3.0.dist-info → mech_client-0.6.0.dist-info}/entry_points.txt +0 -0
|
@@ -26,8 +26,9 @@ import sys
|
|
|
26
26
|
import time
|
|
27
27
|
from dataclasses import asdict, make_dataclass
|
|
28
28
|
from datetime import datetime
|
|
29
|
+
from enum import Enum
|
|
29
30
|
from pathlib import Path
|
|
30
|
-
from typing import Any, Dict,
|
|
31
|
+
from typing import Any, Dict, Optional, Tuple, cast
|
|
31
32
|
|
|
32
33
|
import requests
|
|
33
34
|
import websocket
|
|
@@ -45,8 +46,8 @@ from mech_client.interact import (
|
|
|
45
46
|
PRIVATE_KEY_FILE_PATH,
|
|
46
47
|
TIMEOUT,
|
|
47
48
|
WAIT_SLEEP,
|
|
48
|
-
calculate_topic_id,
|
|
49
49
|
get_contract,
|
|
50
|
+
get_event_signatures,
|
|
50
51
|
get_mech_config,
|
|
51
52
|
)
|
|
52
53
|
from mech_client.prompt_to_ipfs import push_metadata_to_ipfs
|
|
@@ -54,54 +55,70 @@ from mech_client.wss import (
|
|
|
54
55
|
register_event_handlers,
|
|
55
56
|
wait_for_receipt,
|
|
56
57
|
watch_for_marketplace_data_url_from_wss,
|
|
57
|
-
|
|
58
|
+
watch_for_marketplace_request_ids,
|
|
58
59
|
)
|
|
59
60
|
|
|
60
61
|
|
|
61
62
|
# false positives for [B105:hardcoded_password_string] Possible hardcoded password
|
|
62
|
-
|
|
63
|
-
"
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
"3679d66ef546e66ce9057c4a052f317b135bc8e8c509638f7966edfd4fcf45e9" # nosec
|
|
63
|
+
class PaymentType(Enum):
|
|
64
|
+
"""Payment type."""
|
|
65
|
+
|
|
66
|
+
NATIVE = "ba699a34be8fe0e7725e93dcbce1701b0211a8ca61330aaeb8a05bf2ec7abed1" # nosec
|
|
67
|
+
TOKEN = "3679d66ef546e66ce9057c4a052f317b135bc8e8c509638f7966edfd4fcf45e9" # nosec
|
|
68
|
+
NATIVE_NVM = (
|
|
69
|
+
"803dd08fe79d91027fc9024e254a0942372b92f3ccabc1bd19f4a5c2b251c316" # nosec
|
|
70
|
+
)
|
|
71
|
+
TOKEN_NVM = (
|
|
72
|
+
"0d6fd99afa9c4c580fab5e341922c2a5c4b61d880da60506193d7bf88944dd14" # nosec
|
|
73
|
+
)
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
IPFS_URL_TEMPLATE = "https://gateway.autonolas.tech/ipfs/f01701220{}"
|
|
77
|
+
ABI_DIR_PATH = Path(__file__).parent / "abis"
|
|
78
|
+
IMECH_ABI_PATH = ABI_DIR_PATH / "IMech.json"
|
|
79
|
+
ITOKEN_ABI_PATH = ABI_DIR_PATH / "IToken.json"
|
|
80
|
+
IERC1155_ABI_PATH = ABI_DIR_PATH / "IERC1155.json"
|
|
81
|
+
MARKETPLACE_ABI_PATH = ABI_DIR_PATH / "MechMarketplace.json"
|
|
82
|
+
|
|
83
|
+
BALANCE_TRACKER_NATIVE_ABI_PATH = ABI_DIR_PATH / "BalanceTrackerFixedPriceNative.json"
|
|
84
|
+
BALANCE_TRACKER_TOKEN_ABI_PATH = ABI_DIR_PATH / "BalanceTrackerFixedPriceToken.json"
|
|
85
|
+
BALANCE_TRACKER_NVM_NATIVE_ABI_PATH = (
|
|
86
|
+
ABI_DIR_PATH / "BalanceTrackerNvmSubscriptionNative.json"
|
|
67
87
|
)
|
|
68
|
-
|
|
69
|
-
"
|
|
88
|
+
BALANCE_TRACKER_NVM_TOKEN_ABI_PATH = (
|
|
89
|
+
ABI_DIR_PATH / "BalanceTrackerNvmSubscriptionToken.json"
|
|
70
90
|
)
|
|
71
91
|
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
92
|
+
|
|
93
|
+
PAYMENT_TYPE_TO_ABI_PATH: Dict[str, Path] = {
|
|
94
|
+
PaymentType.NATIVE.value: BALANCE_TRACKER_NATIVE_ABI_PATH,
|
|
95
|
+
PaymentType.TOKEN.value: BALANCE_TRACKER_TOKEN_ABI_PATH,
|
|
96
|
+
PaymentType.NATIVE_NVM.value: BALANCE_TRACKER_NVM_NATIVE_ABI_PATH,
|
|
97
|
+
PaymentType.TOKEN_NVM.value: BALANCE_TRACKER_NVM_TOKEN_ABI_PATH,
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
CHAIN_TO_PRICE_TOKEN = {
|
|
101
|
+
1: "0x0001A500A6B18995B03f44bb040A5fFc28E45CB0",
|
|
102
|
+
10: "0xFC2E6e6BCbd49ccf3A5f029c79984372DcBFE527",
|
|
103
|
+
100: "0xcE11e14225575945b8E6Dc0D4F2dD4C570f79d9f",
|
|
104
|
+
137: "0xFEF5d947472e72Efbb2E388c730B7428406F2F95",
|
|
105
|
+
8453: "0x54330d28ca3357F294334BDC454a032e7f353416",
|
|
106
|
+
42220: "0xFEF5d947472e72Efbb2E388c730B7428406F2F95",
|
|
79
107
|
}
|
|
80
108
|
|
|
81
109
|
|
|
82
110
|
CHAIN_TO_DEFAULT_MECH_MARKETPLACE_REQUEST_CONFIG = {
|
|
83
111
|
100: {
|
|
84
|
-
"mech_marketplace_contract": "0x735FAAb1c4Ec41128c367AFb5c3baC73509f70bB",
|
|
85
|
-
"priority_mech_address": "0x478ad20eD958dCC5AD4ABa6F4E4cc51e07a840E4",
|
|
86
112
|
"response_timeout": 300,
|
|
87
113
|
"payment_data": "0x",
|
|
88
|
-
}
|
|
114
|
+
},
|
|
115
|
+
8453: {
|
|
116
|
+
"response_timeout": 300,
|
|
117
|
+
"payment_data": "0x",
|
|
118
|
+
},
|
|
89
119
|
}
|
|
90
120
|
|
|
91
121
|
|
|
92
|
-
def get_event_signatures(abi: List) -> Tuple[str, str]:
|
|
93
|
-
"""Calculate `Marketplace Request` and `Marketplace Deliver` event topics"""
|
|
94
|
-
marketplace_request, marketplace_deliver = "", ""
|
|
95
|
-
for obj in abi:
|
|
96
|
-
if obj["type"] != "event":
|
|
97
|
-
continue
|
|
98
|
-
if obj["name"] == "MarketplaceDeliver":
|
|
99
|
-
marketplace_deliver = calculate_topic_id(event=obj)
|
|
100
|
-
if obj["name"] == "MarketplaceRequest":
|
|
101
|
-
marketplace_request = calculate_topic_id(event=obj)
|
|
102
|
-
return marketplace_request, marketplace_deliver
|
|
103
|
-
|
|
104
|
-
|
|
105
122
|
def fetch_mech_info(
|
|
106
123
|
ledger_api: EthereumApi,
|
|
107
124
|
mech_marketplace_contract: Web3Contract,
|
|
@@ -120,7 +137,7 @@ def fetch_mech_info(
|
|
|
120
137
|
:rtype: Tuple[str, int, int, str, Contract]
|
|
121
138
|
"""
|
|
122
139
|
|
|
123
|
-
with open(
|
|
140
|
+
with open(IMECH_ABI_PATH, encoding="utf-8") as f:
|
|
124
141
|
abi = json.load(f)
|
|
125
142
|
|
|
126
143
|
mech_contract = get_contract(
|
|
@@ -137,7 +154,7 @@ def fetch_mech_info(
|
|
|
137
154
|
).call()
|
|
138
155
|
)
|
|
139
156
|
|
|
140
|
-
if payment_type not in
|
|
157
|
+
if payment_type not in PaymentType._value2member_map_: # pylint: disable=W0212
|
|
141
158
|
print(" - Invalid mech type detected.")
|
|
142
159
|
sys.exit(1)
|
|
143
160
|
|
|
@@ -175,7 +192,7 @@ def approve_price_tokens(
|
|
|
175
192
|
"""
|
|
176
193
|
sender = crypto.address
|
|
177
194
|
|
|
178
|
-
with open(
|
|
195
|
+
with open(ITOKEN_ABI_PATH, encoding="utf-8") as f:
|
|
179
196
|
abi = json.load(f)
|
|
180
197
|
|
|
181
198
|
token_contract = get_contract(
|
|
@@ -210,6 +227,7 @@ def fetch_requester_nvm_subscription_balance(
|
|
|
210
227
|
requester: str,
|
|
211
228
|
ledger_api: EthereumApi,
|
|
212
229
|
mech_payment_balance_tracker: str,
|
|
230
|
+
payment_type: str,
|
|
213
231
|
) -> int:
|
|
214
232
|
"""
|
|
215
233
|
Fetches the requester nvm subscription balance.
|
|
@@ -220,11 +238,13 @@ def fetch_requester_nvm_subscription_balance(
|
|
|
220
238
|
:type ledger_api: EthereumApi
|
|
221
239
|
:param mech_payment_balance_tracker: Requested mech's balance tracker contract address
|
|
222
240
|
:type mech_payment_balance_tracker: str
|
|
241
|
+
:param payment_type: Requested mech's payment type
|
|
242
|
+
:type payment_type: str
|
|
223
243
|
:return: The requester balance.
|
|
224
244
|
:rtype: int
|
|
225
245
|
"""
|
|
226
246
|
with open(
|
|
227
|
-
|
|
247
|
+
PAYMENT_TYPE_TO_ABI_PATH[payment_type],
|
|
228
248
|
encoding="utf-8",
|
|
229
249
|
) as f:
|
|
230
250
|
abi = json.load(f)
|
|
@@ -239,10 +259,7 @@ def fetch_requester_nvm_subscription_balance(
|
|
|
239
259
|
nvm_balance_tracker_contract.functions.subscriptionTokenId().call()
|
|
240
260
|
)
|
|
241
261
|
|
|
242
|
-
with open(
|
|
243
|
-
Path(__file__).parent / "abis" / "IERC1155.json",
|
|
244
|
-
encoding="utf-8",
|
|
245
|
-
) as f:
|
|
262
|
+
with open(IERC1155_ABI_PATH, encoding="utf-8") as f:
|
|
246
263
|
abi = json.load(f)
|
|
247
264
|
|
|
248
265
|
subscription_nft_contract = get_contract(
|
|
@@ -260,8 +277,8 @@ def send_marketplace_request( # pylint: disable=too-many-arguments,too-many-loc
|
|
|
260
277
|
ledger_api: EthereumApi,
|
|
261
278
|
marketplace_contract: Web3Contract,
|
|
262
279
|
gas_limit: int,
|
|
263
|
-
|
|
264
|
-
|
|
280
|
+
prompts: tuple,
|
|
281
|
+
tools: tuple,
|
|
265
282
|
method_args_data: MechMarketplaceRequestConfig,
|
|
266
283
|
extra_attributes: Optional[Dict[str, Any]] = None,
|
|
267
284
|
price: int = 10_000_000_000_000_000,
|
|
@@ -280,10 +297,10 @@ def send_marketplace_request( # pylint: disable=too-many-arguments,too-many-loc
|
|
|
280
297
|
:type marketplace_contract: Web3Contract
|
|
281
298
|
:param gas_limit: Gas limit.
|
|
282
299
|
:type gas_limit: int
|
|
283
|
-
:param
|
|
284
|
-
:type
|
|
285
|
-
:param
|
|
286
|
-
:type
|
|
300
|
+
:param prompts: The request prompts.
|
|
301
|
+
:type prompts: tuple
|
|
302
|
+
:param tools: The requested tools.
|
|
303
|
+
:type tools: tuple
|
|
287
304
|
:param method_args_data: Method data to use to call the marketplace contract request
|
|
288
305
|
:type method_args_data: MechMarketplaceRequestConfig
|
|
289
306
|
:param extra_attributes: Extra attributes to be included in the request metadata.
|
|
@@ -299,21 +316,40 @@ def send_marketplace_request( # pylint: disable=too-many-arguments,too-many-loc
|
|
|
299
316
|
:return: The transaction hash.
|
|
300
317
|
:rtype: Optional[str]
|
|
301
318
|
"""
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
)
|
|
305
|
-
print(
|
|
306
|
-
f" - Prompt uploaded: https://gateway.autonolas.tech/ipfs/{v1_file_hash_hex}"
|
|
307
|
-
)
|
|
308
|
-
method_name = "request"
|
|
319
|
+
num_requests = len(prompts)
|
|
320
|
+
|
|
309
321
|
method_args = {
|
|
310
|
-
"requestData": v1_file_hash_hex_truncated,
|
|
311
322
|
"maxDeliveryRate": method_args_data.delivery_rate,
|
|
312
323
|
"paymentType": "0x" + cast(str, method_args_data.payment_type),
|
|
313
324
|
"priorityMech": to_checksum_address(method_args_data.priority_mech_address),
|
|
314
325
|
"responseTimeout": method_args_data.response_timeout,
|
|
315
326
|
"paymentData": method_args_data.payment_data,
|
|
316
327
|
}
|
|
328
|
+
|
|
329
|
+
if num_requests == 1:
|
|
330
|
+
v1_file_hash_hex_truncated, v1_file_hash_hex = push_metadata_to_ipfs(
|
|
331
|
+
prompts[0], tools[0], extra_attributes
|
|
332
|
+
)
|
|
333
|
+
print(
|
|
334
|
+
f" - Prompt uploaded: https://gateway.autonolas.tech/ipfs/{v1_file_hash_hex}"
|
|
335
|
+
)
|
|
336
|
+
method_name = "request"
|
|
337
|
+
method_args["requestData"] = v1_file_hash_hex_truncated
|
|
338
|
+
|
|
339
|
+
else:
|
|
340
|
+
request_datas = []
|
|
341
|
+
for prompt, tool in zip(prompts, tools):
|
|
342
|
+
v1_file_hash_hex_truncated, v1_file_hash_hex = push_metadata_to_ipfs(
|
|
343
|
+
prompt, tool, extra_attributes
|
|
344
|
+
)
|
|
345
|
+
print(
|
|
346
|
+
f" - Prompt uploaded: https://gateway.autonolas.tech/ipfs/{v1_file_hash_hex}"
|
|
347
|
+
)
|
|
348
|
+
request_datas.append(v1_file_hash_hex_truncated)
|
|
349
|
+
|
|
350
|
+
method_name = "requestBatch"
|
|
351
|
+
method_args["requestDatas"] = request_datas
|
|
352
|
+
|
|
317
353
|
tx_args = {
|
|
318
354
|
"sender_address": crypto.address,
|
|
319
355
|
"value": price,
|
|
@@ -356,6 +392,7 @@ def send_offchain_marketplace_request( # pylint: disable=too-many-arguments,too
|
|
|
356
392
|
prompt: str,
|
|
357
393
|
tool: str,
|
|
358
394
|
method_args_data: MechMarketplaceRequestConfig,
|
|
395
|
+
nonce: int,
|
|
359
396
|
extra_attributes: Optional[Dict[str, Any]] = None,
|
|
360
397
|
retries: Optional[int] = None,
|
|
361
398
|
timeout: Optional[float] = None,
|
|
@@ -374,6 +411,8 @@ def send_offchain_marketplace_request( # pylint: disable=too-many-arguments,too
|
|
|
374
411
|
:type tool: str
|
|
375
412
|
:param method_args_data: Method data to use to call the marketplace contract request
|
|
376
413
|
:type method_args_data: MechMarketplaceRequestConfig
|
|
414
|
+
:param nonce: Nonce to use to order offchain tasks
|
|
415
|
+
:type nonce: int
|
|
377
416
|
:param extra_attributes: Extra attributes to be included in the request metadata.
|
|
378
417
|
:type extra_attributes: Optional[Dict[str,Any]]
|
|
379
418
|
:param retries: Number of retries for sending a transaction
|
|
@@ -409,7 +448,6 @@ def send_offchain_marketplace_request( # pylint: disable=too-many-arguments,too
|
|
|
409
448
|
while tries < retries and datetime.now().timestamp() < deadline:
|
|
410
449
|
tries += 1
|
|
411
450
|
try:
|
|
412
|
-
nonce = marketplace_contract.functions.mapNonces(crypto.address).call()
|
|
413
451
|
delivery_rate = method_args["maxDeliveryRate"]
|
|
414
452
|
request_id = marketplace_contract.functions.getRequestId(
|
|
415
453
|
method_args["priorityMech"],
|
|
@@ -568,34 +606,12 @@ def check_prepaid_balances(
|
|
|
568
606
|
:type max_delivery_rate: int
|
|
569
607
|
"""
|
|
570
608
|
requester = crypto.address
|
|
571
|
-
if payment_type == PAYMENT_TYPE_NATIVE:
|
|
572
|
-
with open(
|
|
573
|
-
Path(__file__).parent / "abis" / "BalanceTrackerFixedPriceNative.json",
|
|
574
|
-
encoding="utf-8",
|
|
575
|
-
) as f:
|
|
576
|
-
abi = json.load(f)
|
|
577
609
|
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
ledger_api=ledger_api,
|
|
582
|
-
)
|
|
583
|
-
requester_balance = balance_tracker_contract.functions.mapRequesterBalances(
|
|
584
|
-
requester
|
|
585
|
-
).call()
|
|
586
|
-
if requester_balance < max_delivery_rate:
|
|
587
|
-
print(
|
|
588
|
-
f" - Sender Native deposited balance low. Needed: {max_delivery_rate}, Actual: {requester_balance}"
|
|
589
|
-
)
|
|
590
|
-
print(f" - Sender Address: {requester}")
|
|
591
|
-
print(" - Please use scripts/deposit_native.py to add balance")
|
|
592
|
-
sys.exit(1)
|
|
610
|
+
if payment_type in [PaymentType.NATIVE.value, PaymentType.TOKEN.value]:
|
|
611
|
+
payment_type_name = PaymentType(payment_type).name.lower()
|
|
612
|
+
payment_type_abi_path = PAYMENT_TYPE_TO_ABI_PATH[payment_type]
|
|
593
613
|
|
|
594
|
-
|
|
595
|
-
with open(
|
|
596
|
-
Path(__file__).parent / "abis" / "BalanceTrackerFixedPriceToken.json",
|
|
597
|
-
encoding="utf-8",
|
|
598
|
-
) as f:
|
|
614
|
+
with open(payment_type_abi_path, encoding="utf-8") as f:
|
|
599
615
|
abi = json.load(f)
|
|
600
616
|
|
|
601
617
|
balance_tracker_contract = get_contract(
|
|
@@ -608,19 +624,21 @@ def check_prepaid_balances(
|
|
|
608
624
|
).call()
|
|
609
625
|
if requester_balance < max_delivery_rate:
|
|
610
626
|
print(
|
|
611
|
-
f" - Sender
|
|
627
|
+
f" - Sender {payment_type_name} deposited balance low. Needed: {max_delivery_rate}, Actual: {requester_balance}"
|
|
612
628
|
)
|
|
613
629
|
print(f" - Sender Address: {requester}")
|
|
614
|
-
print(
|
|
630
|
+
print(
|
|
631
|
+
f" - Please use scripts/deposit_{payment_type_name}.py to add balance"
|
|
632
|
+
)
|
|
615
633
|
sys.exit(1)
|
|
616
634
|
|
|
617
635
|
|
|
618
636
|
def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals, too-many-statements, too-many-return-statements
|
|
619
|
-
|
|
637
|
+
prompts: tuple,
|
|
620
638
|
priority_mech: str,
|
|
621
639
|
use_prepaid: bool = False,
|
|
622
640
|
use_offchain: bool = False,
|
|
623
|
-
|
|
641
|
+
tools: tuple = (),
|
|
624
642
|
extra_attributes: Optional[Dict[str, Any]] = None,
|
|
625
643
|
private_key_path: Optional[str] = None,
|
|
626
644
|
confirmation_type: ConfirmationType = ConfirmationType.WAIT_FOR_BOTH,
|
|
@@ -632,16 +650,16 @@ def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals
|
|
|
632
650
|
"""
|
|
633
651
|
Interact with mech marketplace contract.
|
|
634
652
|
|
|
635
|
-
:param
|
|
636
|
-
:type
|
|
653
|
+
:param prompts: The interaction prompts.
|
|
654
|
+
:type prompts: tuple
|
|
637
655
|
:param priority_mech: Priority mech address to use (Optional)
|
|
638
656
|
:type priority_mech: str
|
|
639
657
|
:param use_prepaid: Whether to use prepaid model or not.
|
|
640
658
|
:type use_prepaid: bool
|
|
641
659
|
:param use_offchain: Whether to use offchain model or not.
|
|
642
660
|
:type use_offchain: bool
|
|
643
|
-
:param
|
|
644
|
-
:type
|
|
661
|
+
:param tools: The tools to interact with (optional).
|
|
662
|
+
:type tools: tuple
|
|
645
663
|
:param extra_attributes: Extra attributes to be included in the request metadata (optional).
|
|
646
664
|
:type extra_attributes: Optional[Dict[str, Any]]
|
|
647
665
|
:param private_key_path: The path to the private key file (optional).
|
|
@@ -665,21 +683,23 @@ def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals
|
|
|
665
683
|
priority_mech_address = priority_mech
|
|
666
684
|
mech_marketplace_contract = mech_config.mech_marketplace_contract
|
|
667
685
|
chain_id = ledger_config.chain_id
|
|
686
|
+
num_requests = len(prompts)
|
|
668
687
|
|
|
669
688
|
if mech_marketplace_contract == ADDRESS_ZERO:
|
|
670
689
|
print(f"Mech Marketplace not yet supported on {chain_config}")
|
|
671
690
|
return None
|
|
672
691
|
|
|
673
692
|
config_values = CHAIN_TO_DEFAULT_MECH_MARKETPLACE_REQUEST_CONFIG[chain_id].copy()
|
|
674
|
-
if priority_mech_address is
|
|
675
|
-
print("
|
|
676
|
-
|
|
677
|
-
{
|
|
678
|
-
"priority_mech_address": priority_mech_address,
|
|
679
|
-
"mech_marketplace_contract": mech_marketplace_contract,
|
|
680
|
-
}
|
|
681
|
-
)
|
|
693
|
+
if priority_mech_address is None:
|
|
694
|
+
print("Priority Mech Address not provided")
|
|
695
|
+
return None
|
|
682
696
|
|
|
697
|
+
config_values.update(
|
|
698
|
+
{
|
|
699
|
+
"priority_mech_address": priority_mech_address,
|
|
700
|
+
"mech_marketplace_contract": mech_marketplace_contract,
|
|
701
|
+
}
|
|
702
|
+
)
|
|
683
703
|
mech_marketplace_request_config: MechMarketplaceRequestConfig = make_dataclass(
|
|
684
704
|
"MechMarketplaceRequestConfig",
|
|
685
705
|
((k, type(v)) for k, v in config_values.items()),
|
|
@@ -699,9 +719,7 @@ def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals
|
|
|
699
719
|
crypto = EthereumCrypto(private_key_path=private_key_path)
|
|
700
720
|
ledger_api = EthereumApi(**asdict(ledger_config))
|
|
701
721
|
|
|
702
|
-
with open(
|
|
703
|
-
Path(__file__).parent / "abis" / "MechMarketplace.json", encoding="utf-8"
|
|
704
|
-
) as f:
|
|
722
|
+
with open(MARKETPLACE_ABI_PATH, encoding="utf-8") as f:
|
|
705
723
|
abi = json.load(f)
|
|
706
724
|
|
|
707
725
|
mech_marketplace_contract = get_contract(
|
|
@@ -726,26 +744,28 @@ def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals
|
|
|
726
744
|
mech_marketplace_request_config.delivery_rate = max_delivery_rate
|
|
727
745
|
mech_marketplace_request_config.payment_type = payment_type
|
|
728
746
|
|
|
747
|
+
with open(IMECH_ABI_PATH, encoding="utf-8") as f:
|
|
748
|
+
abi = json.load(f)
|
|
749
|
+
|
|
729
750
|
(
|
|
730
751
|
marketplace_request_event_signature,
|
|
731
752
|
marketplace_deliver_event_signature,
|
|
732
753
|
) = get_event_signatures(abi=abi)
|
|
733
|
-
|
|
734
754
|
register_event_handlers(
|
|
735
755
|
wss=wss,
|
|
736
|
-
contract_address=
|
|
756
|
+
contract_address=priority_mech_address,
|
|
737
757
|
crypto=crypto,
|
|
738
758
|
request_signature=marketplace_request_event_signature,
|
|
739
759
|
deliver_signature=marketplace_deliver_event_signature,
|
|
740
760
|
)
|
|
741
761
|
|
|
742
762
|
if not use_prepaid:
|
|
743
|
-
price = max_delivery_rate
|
|
744
|
-
if payment_type ==
|
|
763
|
+
price = max_delivery_rate * num_requests
|
|
764
|
+
if payment_type == PaymentType.TOKEN.value:
|
|
745
765
|
print("Token Mech detected, approving wrapped token for price payment...")
|
|
746
|
-
|
|
766
|
+
price_token = CHAIN_TO_PRICE_TOKEN[chain_id]
|
|
747
767
|
approve_tx = approve_price_tokens(
|
|
748
|
-
crypto, ledger_api,
|
|
768
|
+
crypto, ledger_api, price_token, mech_payment_balance_tracker, price
|
|
749
769
|
)
|
|
750
770
|
if not approve_tx:
|
|
751
771
|
print("Unable to approve allowance")
|
|
@@ -772,11 +792,14 @@ def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals
|
|
|
772
792
|
max_delivery_rate,
|
|
773
793
|
)
|
|
774
794
|
|
|
775
|
-
if payment_type
|
|
776
|
-
|
|
795
|
+
if payment_type in [PaymentType.NATIVE_NVM.value, PaymentType.TOKEN_NVM.value]:
|
|
796
|
+
nvm_mech_type = PaymentType(payment_type).name.lower()
|
|
797
|
+
print(
|
|
798
|
+
f"{nvm_mech_type} Nevermined Mech detected, subscription credits to be used"
|
|
799
|
+
)
|
|
777
800
|
requester = crypto.address
|
|
778
801
|
requester_balance = fetch_requester_nvm_subscription_balance(
|
|
779
|
-
requester, ledger_api, mech_payment_balance_tracker
|
|
802
|
+
requester, ledger_api, mech_payment_balance_tracker, payment_type
|
|
780
803
|
)
|
|
781
804
|
if requester_balance < price:
|
|
782
805
|
print(
|
|
@@ -796,8 +819,8 @@ def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals
|
|
|
796
819
|
marketplace_contract=mech_marketplace_contract,
|
|
797
820
|
gas_limit=mech_config.gas_limit,
|
|
798
821
|
price=price,
|
|
799
|
-
|
|
800
|
-
|
|
822
|
+
prompts=prompts,
|
|
823
|
+
tools=tools,
|
|
801
824
|
method_args_data=mech_marketplace_request_config,
|
|
802
825
|
extra_attributes=extra_attributes,
|
|
803
826
|
retries=retries,
|
|
@@ -815,66 +838,86 @@ def marketplace_interact( # pylint: disable=too-many-arguments, too-many-locals
|
|
|
815
838
|
print(f" - Transaction sent: {transaction_url_formatted}")
|
|
816
839
|
print(" - Waiting for transaction receipt...")
|
|
817
840
|
|
|
818
|
-
|
|
841
|
+
request_ids = watch_for_marketplace_request_ids(
|
|
819
842
|
marketplace_contract=mech_marketplace_contract,
|
|
820
843
|
ledger_api=ledger_api,
|
|
821
844
|
tx_hash=transaction_digest,
|
|
822
845
|
)
|
|
823
|
-
|
|
824
|
-
|
|
846
|
+
request_id_ints = [
|
|
847
|
+
int.from_bytes(bytes.fromhex(request_id), byteorder="big")
|
|
848
|
+
for request_id in request_ids
|
|
849
|
+
]
|
|
850
|
+
if len(request_id_ints) == 1:
|
|
851
|
+
print(f" - Created on-chain request with ID {request_id_ints[0]}")
|
|
852
|
+
else:
|
|
853
|
+
print(
|
|
854
|
+
f" - Created on-chain requests with IDs: {', '.join(str(rid) for rid in request_id_ints)}"
|
|
855
|
+
)
|
|
825
856
|
print("")
|
|
826
857
|
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
858
|
+
for request_id, request_id_int in zip(request_ids, request_id_ints):
|
|
859
|
+
data_url = wait_for_marketplace_data_url(
|
|
860
|
+
request_id=request_id,
|
|
861
|
+
wss=wss,
|
|
862
|
+
mech_contract=mech_contract,
|
|
863
|
+
subgraph_url=mech_config.subgraph_url,
|
|
864
|
+
deliver_signature=marketplace_deliver_event_signature,
|
|
865
|
+
ledger_api=ledger_api,
|
|
866
|
+
crypto=crypto,
|
|
867
|
+
confirmation_type=confirmation_type,
|
|
868
|
+
)
|
|
837
869
|
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
return data
|
|
870
|
+
if data_url:
|
|
871
|
+
print(f" - Data arrived: {data_url}")
|
|
872
|
+
data = requests.get(f"{data_url}/{request_id_int}", timeout=30).json()
|
|
873
|
+
print(" - Data from agent:")
|
|
874
|
+
print(json.dumps(data, indent=2))
|
|
844
875
|
return None
|
|
845
876
|
|
|
846
877
|
print("Sending Offchain Mech Marketplace request...")
|
|
847
|
-
|
|
848
|
-
|
|
849
|
-
marketplace_contract=mech_marketplace_contract,
|
|
850
|
-
prompt=prompt,
|
|
851
|
-
tool=tool,
|
|
852
|
-
method_args_data=mech_marketplace_request_config,
|
|
853
|
-
extra_attributes=extra_attributes,
|
|
854
|
-
retries=retries,
|
|
855
|
-
timeout=timeout,
|
|
856
|
-
sleep=sleep,
|
|
857
|
-
)
|
|
878
|
+
curr_nonce = mech_marketplace_contract.functions.mapNonces(crypto.address).call() # type: ignore
|
|
879
|
+
responses = []
|
|
858
880
|
|
|
859
|
-
|
|
881
|
+
for i in range(num_requests):
|
|
882
|
+
response = send_offchain_marketplace_request(
|
|
883
|
+
crypto=crypto,
|
|
884
|
+
marketplace_contract=mech_marketplace_contract,
|
|
885
|
+
prompt=prompts[0],
|
|
886
|
+
tool=tools[0],
|
|
887
|
+
method_args_data=mech_marketplace_request_config,
|
|
888
|
+
nonce=curr_nonce + i,
|
|
889
|
+
extra_attributes=extra_attributes,
|
|
890
|
+
retries=retries,
|
|
891
|
+
timeout=timeout,
|
|
892
|
+
sleep=sleep,
|
|
893
|
+
)
|
|
894
|
+
responses.append(response)
|
|
895
|
+
|
|
896
|
+
if not responses and len(responses) != num_requests:
|
|
860
897
|
return None
|
|
861
898
|
|
|
862
|
-
|
|
863
|
-
|
|
899
|
+
request_ids = [resp["request_id"] for resp in responses if resp is not None]
|
|
900
|
+
if len(request_ids) == 1:
|
|
901
|
+
print(f" - Created off-chain request with ID {request_ids[0]}")
|
|
902
|
+
else:
|
|
903
|
+
print(
|
|
904
|
+
f" - Created off-chain requests with IDs: {', '.join(str(rid) for rid in request_ids)}"
|
|
905
|
+
)
|
|
864
906
|
print("")
|
|
865
907
|
|
|
866
908
|
# @note as we are directly querying data from done task list, we get the full data instead of the ipfs hash
|
|
867
909
|
print("Waiting for Offchain Mech Marketplace deliver...")
|
|
868
|
-
data = wait_for_offchain_marketplace_data(
|
|
869
|
-
request_id=request_id,
|
|
870
|
-
)
|
|
871
910
|
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
911
|
+
for request_id in request_ids:
|
|
912
|
+
data = wait_for_offchain_marketplace_data(
|
|
913
|
+
request_id=request_id,
|
|
914
|
+
)
|
|
915
|
+
|
|
916
|
+
if data:
|
|
917
|
+
task_result = data["task_result"]
|
|
918
|
+
data_url = IPFS_URL_TEMPLATE.format(task_result)
|
|
919
|
+
print(f" - Data arrived: {data_url}")
|
|
920
|
+
data = requests.get(f"{data_url}/{request_id}", timeout=30).json()
|
|
921
|
+
print(" - Data from agent:")
|
|
922
|
+
print(json.dumps(data, indent=2))
|
|
880
923
|
return None
|
|
@@ -7,7 +7,13 @@ from typing import Any, Dict, List, Optional, Tuple, Union
|
|
|
7
7
|
import requests
|
|
8
8
|
from aea_ledger_ethereum import EthereumApi
|
|
9
9
|
|
|
10
|
-
from mech_client.interact import
|
|
10
|
+
from mech_client.interact import (
|
|
11
|
+
AGENT_REGISTRY_ABI_PATH,
|
|
12
|
+
fetch_tools,
|
|
13
|
+
get_abi,
|
|
14
|
+
get_contract,
|
|
15
|
+
get_mech_config,
|
|
16
|
+
)
|
|
11
17
|
|
|
12
18
|
|
|
13
19
|
def get_total_supply(chain_config: str = "gnosis") -> int:
|
|
@@ -27,7 +33,7 @@ def get_total_supply(chain_config: str = "gnosis") -> int:
|
|
|
27
33
|
ledger_api = EthereumApi(**asdict(ledger_config))
|
|
28
34
|
|
|
29
35
|
# Fetch ABI and create contract instance
|
|
30
|
-
abi = get_abi(
|
|
36
|
+
abi = get_abi(AGENT_REGISTRY_ABI_PATH)
|
|
31
37
|
contract = get_contract(mech_config.agent_registry_contract, abi, ledger_api)
|
|
32
38
|
|
|
33
39
|
# Call the totalSupply function
|
|
@@ -58,7 +64,7 @@ def get_agent_tools(
|
|
|
58
64
|
agent_id=agent_id,
|
|
59
65
|
ledger_api=ledger_api,
|
|
60
66
|
agent_registry_contract=mech_config.agent_registry_contract,
|
|
61
|
-
|
|
67
|
+
contract_abi_path=AGENT_REGISTRY_ABI_PATH,
|
|
62
68
|
include_metadata=include_metadata,
|
|
63
69
|
)
|
|
64
70
|
except (requests.exceptions.RequestException, json.JSONDecodeError, KeyError) as e:
|
|
@@ -155,7 +161,7 @@ def get_tool_description(unique_identifier: str, chain_config: str = "gnosis") -
|
|
|
155
161
|
agent_id=agent_id,
|
|
156
162
|
ledger_api=ledger_api,
|
|
157
163
|
agent_registry_contract=mech_config.agent_registry_contract,
|
|
158
|
-
|
|
164
|
+
contract_abi_path=AGENT_REGISTRY_ABI_PATH,
|
|
159
165
|
include_metadata=True,
|
|
160
166
|
)
|
|
161
167
|
if isinstance(tools_result, tuple) and len(tools_result) == 2:
|
|
@@ -188,7 +194,7 @@ def get_tool_io_schema(
|
|
|
188
194
|
agent_id=agent_id,
|
|
189
195
|
ledger_api=ledger_api,
|
|
190
196
|
agent_registry_contract=mech_config.agent_registry_contract,
|
|
191
|
-
|
|
197
|
+
contract_abi_path=AGENT_REGISTRY_ABI_PATH,
|
|
192
198
|
include_metadata=True,
|
|
193
199
|
)
|
|
194
200
|
if isinstance(tools_result, tuple) and len(tools_result) == 2:
|