diff --git a/packages/gnosis/customs/ofv_market_resolver/component.yaml b/packages/gnosis/customs/ofv_market_resolver/component.yaml index ea08996c..c2ae3fab 100644 --- a/packages/gnosis/customs/ofv_market_resolver/component.yaml +++ b/packages/gnosis/customs/ofv_market_resolver/component.yaml @@ -7,7 +7,6 @@ license: Apache-2.0 aea_version: '>=1.0.0, <2.0.0' fingerprint: __init__.py: bafybeie2727utrijcawhgm5bgj7p5lfah2pzepaufnk6m5swuwyduhf2eu - log/factcheck_dev.log: bafybeihwremece5odkxdjxk4pt2htbpszrxheccxaqs3czogne3t7rblme ofv_market_resolver.py: bafybeic6kxngm3mdkpmcjucrrerhyex7kizn7tw7qmpehaiycnc7cb6umu fingerprint_ignore_patterns: [] entry_point: ofv_market_resolver.py diff --git a/packages/packages.json b/packages/packages.json index 14576a2c..4e2e0efb 100644 --- a/packages/packages.json +++ b/packages/packages.json @@ -30,21 +30,23 @@ "custom/gnosis/omen_tools/0.1.0": "bafybeiglmyy3esctsejdqmz63juvaridbbjwjw3ch4mqudicsrgoir4qrq", "custom/victorpolisetty/dalle_request/0.1.0": "bafybeieqqtd6gtlry7vheix54nj3ok4cag3uy47yoxlufhi6y3u5i6doti", "custom/jhehemann/prediction_sentence_embeddings/0.1.0": "bafybeifyyb2wpa77tl7a7fs3fabns45llivhgccbnrpupubojmq2fwe4si", - "custom/gnosis/ofv_market_resolver/0.1.0": "bafybeidsiwakhj4w4rsvpf6agbwr76dh2r73eu6wrnwmoctgwlupgh46am", + "custom/gnosis/ofv_market_resolver/0.1.0": "bafybeigapoti2ysukapphspjawktkb4qkeltlollt4d2z4u7mrddk3u3rq", + "custom/valory/tee_openai_request/0.1.0": "bafybeictmezaorzxelsy4dztbxh5n2343zio3rk6vo7wc5lptxlobhdnku", "protocol/valory/acn_data_share/0.1.0": "bafybeih5ydonnvrwvy2ygfqgfabkr47s4yw3uqxztmwyfprulwfsoe7ipq", "protocol/valory/websocket_client/0.1.0": "bafybeifjk254sy65rna2k32kynzenutujwqndap2r222afvr3zezi27mx4", "contract/valory/agent_mech/0.1.0": "bafybeiah6b5epo2hlvzg5rr2cydgpp2waausoyrpnoarf7oa7bw33rex34", "contract/valory/agent_registry/0.1.0": "bafybeiarzhzs2wm2sl47qg37tqoc3qok54enxlcj6vx3hldozg537uslnq", "contract/valory/hash_checkpoint/0.1.0": "bafybeicbycr6rxods7sg3f2qlhgkjqrbh7kymmy2yw7bewxdwjyp7ibtg4", + "contract/valory/mech_marketplace/0.1.0": "bafybeich3a3oh5w4u533w6y7ideojudqp2m5gxta7pqmsfiaohdhuw7yz4", "connection/valory/websocket_client/0.1.0": "bafybeic4ag3gqc7kd3k2o3pucddj2odck5yrfbgmwh5veqny7zao5qayli", "skill/valory/contract_subscription/0.1.0": "bafybeiefuemlp75obgpxrp6iuleb3hn6vcviwh5oetk5djbuprf4xsmgjy", - "skill/valory/mech_abci/0.1.0": "bafybeicvbtbmtdps7lsbsutojiic4sam3jmi3prev5u22tps6pxy4du7nq", - "skill/valory/task_submission_abci/0.1.0": "bafybeihvvp6ovstb7po7kx6o7dno6kvjmffnmlerfw6qxhhzyrxmktd67e", - "skill/valory/task_execution/0.1.0": "bafybeie5obeuqn2g2rgtubqmdfxgyiri2yb5gbkvpvnyw7xapkqykoxmj4", + "skill/valory/mech_abci/0.1.0": "bafybeidkwahhblv6d6shzrk665yguyfar3w6qbld5ryjolw4zibdwr73vi", + "skill/valory/task_submission_abci/0.1.0": "bafybeifkd76popxwociq2ryojbcjyesmxoagqyjrbs73qoyd5o4szz6cgu", + "skill/valory/task_execution/0.1.0": "bafybeicg7rvme6dajqzwval3igq352mjor6k4lnw3tachrml66o7cm7mvm", "skill/valory/websocket_client/0.1.0": "bafybeif7rrvsu6z4evqkhblxj3u6wwv2eqou576hgkyoehxuj7cntw7o2m", "skill/valory/subscription_abci/0.1.0": "bafybeihtortmv4fqua5wrnshpnvqsbpaf52frwynrmpuv2uw5j7wkauhze", - "agent/valory/mech/0.1.0": "bafybeicbjm4qzztawekdr55gpbtntc6lu2sig6cfttss4zcu4tdnbypyhq", - "service/valory/mech/0.1.0": "bafybeidlte5wznzrusil2xuyd6kgvavlkkhr4agdutw5as6euvzlwr2ovi" + "agent/valory/mech/0.1.0": "bafybeib4ptljwzt34isrcmbkloexgp2wdmbrinl5a57xxvgjqub2ikhzvm", + "service/valory/mech/0.1.0": "bafybeieetllbqkol5nsreusrra553diyc3ec5n3lw5p23d5sromggarsc4" }, "third_party": { "protocol/valory/default/1.0.0": "bafybeifqcqy5hfbnd7fjv4mqdjrtujh2vx3p2xhe33y67zoxa6ph7wdpaq", diff --git a/packages/valory/agents/mech/aea-config.yaml b/packages/valory/agents/mech/aea-config.yaml index a3b619e0..3ba2b2cc 100644 --- a/packages/valory/agents/mech/aea-config.yaml +++ b/packages/valory/agents/mech/aea-config.yaml @@ -22,6 +22,7 @@ contracts: - valory/hash_checkpoint:0.1.0:bafybeicbycr6rxods7sg3f2qlhgkjqrbh7kymmy2yw7bewxdwjyp7ibtg4 - valory/multisend:0.1.0:bafybeig5byt5urg2d2bsecufxe5ql7f4mezg3mekfleeh32nmuusx66p4y - valory/service_registry:0.1.0:bafybeicbxmbzt757lbmyh6762lrkcrp3oeum6dk3z7pvosixasifsk6xlm +- valory/mech_marketplace:0.1.0:bafybeich3a3oh5w4u533w6y7ideojudqp2m5gxta7pqmsfiaohdhuw7yz4 protocols: - open_aea/signing:1.0.0:bafybeihv62fim3wl2bayavfcg3u5e5cxu3b7brtu4cn5xoxd6lqwachasi - valory/abci:0.1.0:bafybeiaqmp7kocbfdboksayeqhkbrynvlfzsx4uy4x6nohywnmaig4an7u @@ -38,12 +39,12 @@ skills: - valory/abstract_abci:0.1.0:bafybeihat4giyc4bz6zopvahcj4iw53356pbtwfn7p4d5yflwly2qhahum - valory/abstract_round_abci:0.1.0:bafybeih3enhagoql7kzpeyzzu2scpkif6y3ubakpralfnwxcvxexdyvy5i - valory/contract_subscription:0.1.0:bafybeiefuemlp75obgpxrp6iuleb3hn6vcviwh5oetk5djbuprf4xsmgjy -- valory/mech_abci:0.1.0:bafybeicvbtbmtdps7lsbsutojiic4sam3jmi3prev5u22tps6pxy4du7nq +- valory/mech_abci:0.1.0:bafybeidkwahhblv6d6shzrk665yguyfar3w6qbld5ryjolw4zibdwr73vi - valory/registration_abci:0.1.0:bafybeiek7zcsxbucjwzgqfftafhfrocvc7q4yxllh2q44jeemsjxg3rcfm - valory/reset_pause_abci:0.1.0:bafybeidw4mbx3os3hmv7ley7b3g3gja7ydpitr7mxbjpwzxin2mzyt5yam - valory/subscription_abci:0.1.0:bafybeihtortmv4fqua5wrnshpnvqsbpaf52frwynrmpuv2uw5j7wkauhze -- valory/task_execution:0.1.0:bafybeie5obeuqn2g2rgtubqmdfxgyiri2yb5gbkvpvnyw7xapkqykoxmj4 -- valory/task_submission_abci:0.1.0:bafybeihvvp6ovstb7po7kx6o7dno6kvjmffnmlerfw6qxhhzyrxmktd67e +- valory/task_execution:0.1.0:bafybeicg7rvme6dajqzwval3igq352mjor6k4lnw3tachrml66o7cm7mvm +- valory/task_submission_abci:0.1.0:bafybeifkd76popxwociq2ryojbcjyesmxoagqyjrbs73qoyd5o4szz6cgu - valory/termination_abci:0.1.0:bafybeihq6qtbwt6i53ayqym63vhjexkcppy26gguzhhjqywfmiuqghvv44 - valory/transaction_settlement_abci:0.1.0:bafybeigtzlk4uakmd54rxnznorcrstsr52kta474lgrnvx5ovr546vj7sq - valory/websocket_client:0.1.0:bafybeif7rrvsu6z4evqkhblxj3u6wwv2eqou576hgkyoehxuj7cntw7o2m @@ -208,6 +209,8 @@ models: round_timeout_seconds: ${float:30.0} reset_period_count: ${int:1000} on_chain_service_id: ${int:1} + mech_staking_instance_address: ${str:0x0000000000000000000000000000000000000000} + mech_marketplace_address: ${str:0x0000000000000000000000000000000000000000} agent_registry_address: ${str:0x0000000000000000000000000000000000000000} agent_id: ${int:3} metadata_hash: ${str:0000000000000000000000000000000000000000000000000000000000000000} @@ -247,7 +250,8 @@ models: agent_index: ${int:0} num_agents: ${int:4} from_block_range: ${int:50000} - mech_to_config: ${list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"]]]} + mech_marketplace_address: ${str:0x0000000000000000000000000000000000000000} + mech_to_config: ${list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"],["is_marketplace_mech","false"]]]} timeout_limit: ${int:3} max_block_window: ${int:500} --- diff --git a/packages/valory/contracts/mech_marketplace/BatchPriorityPassedCheck.sol b/packages/valory/contracts/mech_marketplace/BatchPriorityPassedCheck.sol new file mode 100644 index 00000000..6f762ce0 --- /dev/null +++ b/packages/valory/contracts/mech_marketplace/BatchPriorityPassedCheck.sol @@ -0,0 +1,59 @@ +// SPDX-License-Identifier: UNLICENSED +pragma solidity ^0.8.23; + + +struct MechDelivery { + // Priority mech address + address priorityMech; + // Delivery mech address + address deliveryMech; + // Requester address + address requester; + // Response timeout window + uint32 responseTimeout; +} + +interface IMechMarketplace { + function mapRequestIdDeliveries(uint256) external view returns (MechDelivery memory); +} + +contract BatchPriorityPassedCheck { + constructor(IMechMarketplace _marketplace, uint256[] memory _requestIds) { + // cache requestIds length + uint256 requestIdsLength = _requestIds.length; + + // create temporary array with requestIds length to populate only with requestIds that have passed the priority timeout + uint256[] memory tempRequestIds = new uint256[](requestIdsLength); + + // declare counter to know how many of the request are eligible + uint256 eligibleRequestIdsCount; + + for (uint256 _i; _i < requestIdsLength;) { + MechDelivery memory delivery = _marketplace.mapRequestIdDeliveries(_requestIds[_i]); + if (block.timestamp >= delivery.responseTimeout) { + tempRequestIds[eligibleRequestIdsCount] = _requestIds[_i]; + ++eligibleRequestIdsCount; + } + unchecked {++_i;} + } + + // create a new array with the actual length of the eligible to not corrupt memory with a wrong length + uint256[] memory eligibleRequestIds = new uint256[](eligibleRequestIdsCount); + + // populate the array with the eligible requestIds + for (uint256 _i; _i < eligibleRequestIdsCount;) { + eligibleRequestIds[_i] = tempRequestIds[_i]; + unchecked {++_i;} + } + + // encode eligible referrers to ensure a proper layout in memory + bytes memory data = abi.encode(eligibleRequestIds); + + assembly { + // pointer to the beginning of the data containing the eligible referrers in memory + let _dataStartPointer := add(data, 32) + // return everything from the start of the data to the end of memory + return (_dataStartPointer, sub(msize(), _dataStartPointer)) + } + } +} \ No newline at end of file diff --git a/packages/valory/contracts/mech_marketplace/__init__.py b/packages/valory/contracts/mech_marketplace/__init__.py new file mode 100644 index 00000000..ec1ae35b --- /dev/null +++ b/packages/valory/contracts/mech_marketplace/__init__.py @@ -0,0 +1,20 @@ +# -*- coding: utf-8 -*- +# ------------------------------------------------------------------------------ +# +# Copyright 2023-2024 Valory AG +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +# ------------------------------------------------------------------------------ + +"""This module contains the support resources for the agent mech contract.""" diff --git a/packages/valory/contracts/mech_marketplace/build/MechMarketplace.json b/packages/valory/contracts/mech_marketplace/build/MechMarketplace.json new file mode 100644 index 00000000..d525100b --- /dev/null +++ b/packages/valory/contracts/mech_marketplace/build/MechMarketplace.json @@ -0,0 +1,837 @@ +{ + "_format": "hh-sol-artifact-1", + "contractName": "MechMarketplace", + "sourceName": "contracts/MechMarketplace.sol", + "abi": [ + { + "inputs": [ + { + "internalType": "address", + "name": "_stakingFactory", + "type": "address" + }, + { + "internalType": "address", + "name": "_karmaProxy", + "type": "address" + }, + { + "internalType": "uint256", + "name": "_minResponseTimeout", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "_maxResponseTimeout", + "type": "uint256" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + } + ], + "name": "AlreadyDelivered", + "type": "error" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "provided", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "min", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "max", + "type": "uint256" + } + ], + "name": "OutOfBounds", + "type": "error" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "provided", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "max", + "type": "uint256" + } + ], + "name": "Overflow", + "type": "error" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "sender", + "type": "address" + }, + { + "internalType": "address", + "name": "owner", + "type": "address" + } + ], + "name": "OwnerOnly", + "type": "error" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "expected", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "current", + "type": "uint256" + } + ], + "name": "PriorityMechResponseTimeout", + "type": "error" + }, + { + "inputs": [], + "name": "ReentrancyGuard", + "type": "error" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "stakingInstance", + "type": "address" + }, + { + "internalType": "uint256", + "name": "serviceId", + "type": "uint256" + } + ], + "name": "ServiceNotStaked", + "type": "error" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "UnauthorizedAccount", + "type": "error" + }, + { + "inputs": [], + "name": "ZeroAddress", + "type": "error" + }, + { + "inputs": [], + "name": "ZeroValue", + "type": "error" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "factory", + "type": "address" + } + ], + "name": "FactoryUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "priorityMech", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "actualMech", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "requester", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "data", + "type": "bytes" + } + ], + "name": "MarketplaceDeliver", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "requester", + "type": "address" + }, + { + "indexed": true, + "internalType": "address", + "name": "requestedMech", + "type": "address" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "bytes", + "name": "data", + "type": "bytes" + } + ], + "name": "MarketplaceRequest", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "mech", + "type": "address" + }, + { + "indexed": false, + "internalType": "bool", + "name": "status", + "type": "bool" + } + ], + "name": "MechRegistrationStatusChanged", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": false, + "internalType": "uint256", + "name": "minResponseTimeout", + "type": "uint256" + }, + { + "indexed": false, + "internalType": "uint256", + "name": "maxResponseTimeout", + "type": "uint256" + } + ], + "name": "MinMaxResponseTimeoutUpdated", + "type": "event" + }, + { + "anonymous": false, + "inputs": [ + { + "indexed": true, + "internalType": "address", + "name": "owner", + "type": "address" + } + ], + "name": "OwnerUpdated", + "type": "event" + }, + { + "inputs": [], + "name": "DOMAIN_SEPARATOR_TYPE_HASH", + "outputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "VERSION", + "outputs": [ + { + "internalType": "string", + "name": "", + "type": "string" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "chainId", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "mech", + "type": "address" + }, + { + "internalType": "address", + "name": "mechStakingInstance", + "type": "address" + }, + { + "internalType": "uint256", + "name": "mechServiceId", + "type": "uint256" + } + ], + "name": "checkMech", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "requester", + "type": "address" + }, + { + "internalType": "address", + "name": "requesterStakingInstance", + "type": "address" + }, + { + "internalType": "uint256", + "name": "requesterServiceId", + "type": "uint256" + } + ], + "name": "checkRequester", + "outputs": [], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "stakingInstance", + "type": "address" + }, + { + "internalType": "uint256", + "name": "serviceId", + "type": "uint256" + } + ], + "name": "checkStakingInstance", + "outputs": [], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + }, + { + "internalType": "bytes", + "name": "requestData", + "type": "bytes" + }, + { + "internalType": "address", + "name": "deliveryMechStakingInstance", + "type": "address" + }, + { + "internalType": "uint256", + "name": "deliveryMechServiceId", + "type": "uint256" + } + ], + "name": "deliverMarketplace", + "outputs": [], + "stateMutability": "nonpayable", + "type": "function" + }, + { + "inputs": [], + "name": "domainSeparator", + "outputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "getDeliveriesCount", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "getDomainSeparator", + "outputs": [ + { + "internalType": "bytes32", + "name": "", + "type": "bytes32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + } + ], + "name": "getMechDeliveryInfo", + "outputs": [ + { + "components": [ + { + "internalType": "address", + "name": "priorityMech", + "type": "address" + }, + { + "internalType": "address", + "name": "deliveryMech", + "type": "address" + }, + { + "internalType": "address", + "name": "requester", + "type": "address" + }, + { + "internalType": "uint32", + "name": "responseTimeout", + "type": "uint32" + } + ], + "internalType": "struct MechDelivery", + "name": "", + "type": "tuple" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "mechService", + "type": "address" + } + ], + "name": "getMechServiceDeliveriesCount", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + }, + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "uint256", + "name": "nonce", + "type": "uint256" + } + ], + "name": "getRequestId", + "outputs": [ + { + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + } + ], + "name": "getRequestStatus", + "outputs": [ + { + "internalType": "enum MechMarketplace.RequestStatus", + "name": "status", + "type": "uint8" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "account", + "type": "address" + } + ], + "name": "getRequestsCount", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "karmaProxy", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "mapDeliveryCounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "mapMechServiceDeliveryCounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "mapNonces", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "name": "mapRequestCounts", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "name": "mapRequestIdDeliveries", + "outputs": [ + { + "internalType": "address", + "name": "priorityMech", + "type": "address" + }, + { + "internalType": "address", + "name": "deliveryMech", + "type": "address" + }, + { + "internalType": "address", + "name": "requester", + "type": "address" + }, + { + "internalType": "uint32", + "name": "responseTimeout", + "type": "uint32" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "maxResponseTimeout", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "minResponseTimeout", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "numTotalRequests", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [], + "name": "numUndeliveredRequests", + "outputs": [ + { + "internalType": "uint256", + "name": "", + "type": "uint256" + } + ], + "stateMutability": "view", + "type": "function" + }, + { + "inputs": [ + { + "internalType": "bytes", + "name": "data", + "type": "bytes" + }, + { + "internalType": "address", + "name": "priorityMech", + "type": "address" + }, + { + "internalType": "address", + "name": "priorityMechStakingInstance", + "type": "address" + }, + { + "internalType": "uint256", + "name": "priorityMechServiceId", + "type": "uint256" + }, + { + "internalType": "address", + "name": "requesterStakingInstance", + "type": "address" + }, + { + "internalType": "uint256", + "name": "requesterServiceId", + "type": "uint256" + }, + { + "internalType": "uint256", + "name": "responseTimeout", + "type": "uint256" + } + ], + "name": "request", + "outputs": [ + { + "internalType": "uint256", + "name": "requestId", + "type": "uint256" + } + ], + "stateMutability": "payable", + "type": "function" + }, + { + "inputs": [], + "name": "stakingFactory", + "outputs": [ + { + "internalType": "address", + "name": "", + "type": "address" + } + ], + "stateMutability": "view", + "type": "function" + } + ], + "bytecode": "0x60c0604052600080553480156200001557600080fd5b506040516200318d3803806200318d833981016040819052620000389162000494565b828282828260008282604051602001620000679291906001600160a01b03929092168252602082015260400190565b60408051601f198184030181529190529050620000848162000174565b5050506001600160a01b038316620000af5760405163d92e233d60e01b815260040160405180910390fd5b6040516331a9108f60e11b8152600481018390526000906001600160a01b03851690636352211e90602401602060405180830381865afa158015620000f8573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906200011e9190620004cc565b90506001600160a01b0381166200015057604051630ede975960e01b8152600481018490526024015b60405180910390fd5b60018290554660a05262000163620001dc565b60805250620005f195505050505050565b6200017e620002a7565b5115620001ce5760405162461bcd60e51b815260206004820152601360248201527f416c726561647920696e697469616c697a656400000000000000000000000000604482015260640162000147565b620001d98162000314565b50565b60007f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f7f493aeac1d921aa02a044029e7fe4be43b1a4e80b40706fa5819e8fbb0d093525604051806040016040528060058152602001640312e302e360dc1b81525060405160200162000250919062000517565b60408051601f1981840301815282825280516020918201209083019490945281019190915260608101919091524660808201523060a082015260c00160405160208183030381529060405280519060200120905090565b60606200030f62000309604051606b60f91b6020820152602560fa1b60218201526001600160601b03193060601b166022820152600160f81b60368201526000906037016040516020818303038152906040528051906020012060001c905090565b620003e2565b905090565b600062000321826200043b565b905060008151602083016000f090506200038c604051606b60f91b6020820152602560fa1b60218201526001600160601b03193060601b166022820152600160f81b60368201526000906037016040516020818303038152906040528051906020012060001c905090565b6001600160a01b0316816001600160a01b031614620003dd5760405162461bcd60e51b815260206004820152600c60248201526b15dc9a5d194819985a5b195960a21b604482015260640162000147565b505050565b6060813b6001811162000405575050604080516020810190915260008152919050565b80620004118162000562565b9150506040519150601f19601f602083010116820160405280825280600160208401853c50919050565b6060815160016200044d91906200057c565b826040516020016200046192919062000598565b6040516020818303038152906040529050919050565b80516001600160a01b03811681146200048f57600080fd5b919050565b600080600060608486031215620004aa57600080fd5b620004b58462000477565b925060208401519150604084015190509250925092565b600060208284031215620004df57600080fd5b620004ea8262000477565b9392505050565b60005b838110156200050e578181015183820152602001620004f4565b50506000910152565b602081526000825180602084015262000538816040850160208701620004f1565b601f01601f19169190910160400192915050565b634e487b7160e01b600052601160045260246000fd5b6000816200057457620005746200054c565b506000190190565b808201808211156200059257620005926200054c565b92915050565b606360f81b815260e083901b6001600160e01b03191660018201526880600e6000396000f360b81b60058201526000600e82018190528251620005e381600f850160208701620004f1565b91909101600f019392505050565b60805160a051612b68620006256000396000818161049d015261124f01526000818161078301526112840152612b686000f3fe6080604052600436106102375760003560e01c8063b0d691fe11610138578063ed24911d116100b0578063f698da251161007f578063fc0c546a11610064578063fc0c546a146107c5578063fe266bb9146107da578063ffa1ad74146107fa57600080fd5b8063f698da2514610771578063fba5c56b146107a557600080fd5b8063ed24911d146106c2578063f23a6e61146106d7578063f5dcb7bb1461071d578063f6171e441461075157600080fd5b8063c7dec3fc11610107578063d843b7f4116100ec578063d843b7f414610632578063d8a4676f14610675578063e00b9118146106a257600080fd5b8063c7dec3fc146105d8578063cbd6407a1461060557600080fd5b8063b0d691fe1461050a578063b94207d314610552578063bc197c811461057a578063bdf86317146105c257600080fd5b80635e988032116101cb57806391b7f5ed1161019a578063a035b1fe1161017f578063a035b1fe146104bf578063a4f9edbf146104d5578063affed0e0146104f557600080fd5b806391b7f5ed1461046b5780639a8a05921461048b57600080fd5b80635e988032146103ae5780635fee6085146103db5780636d70f7ae146104085780637af734731461042857600080fd5b80633a871cdd116102075780633a871cdd1461032857806341a7726a146103485780634ada3e611461036b57806358ce09091461038157600080fd5b806223de2914610243578063150b7a021461026a5780631626ba7e146102e557806317d70f7c1461030557600080fd5b3661023e57005b600080fd5b34801561024f57600080fd5b5061026861025e3660046120c9565b5050505050505050565b005b34801561027657600080fd5b506102af61028536600461217a565b7f150b7a020000000000000000000000000000000000000000000000000000000095945050505050565b6040517fffffffff0000000000000000000000000000000000000000000000000000000090911681526020015b60405180910390f35b3480156102f157600080fd5b506102af6103003660046122c7565b610843565b34801561031157600080fd5b5061031a6109ec565b6040519081526020016102dc565b34801561033457600080fd5b5061031a61034336600461230e565b610a11565b61035b610356366004612362565b610a4f565b60405190151581526020016102dc565b34801561037757600080fd5b5061031a60035481565b34801561038d57600080fd5b506103a161039c36600461237f565b610ae7565b6040516102dc91906123a1565b3480156103ba57600080fd5b5061031a6103c9366004612362565b60086020526000908152604090205481565b3480156103e757600080fd5b5061031a6103f6366004612362565b60046020526000908152604090205481565b34801561041457600080fd5b5061035b610423366004612362565b610c57565b34801561043457600080fd5b5061031a610443366004612362565b73ffffffffffffffffffffffffffffffffffffffff1660009081526004602052604090205490565b34801561047757600080fd5b506102686104863660046123e5565b610d2d565b34801561049757600080fd5b5061031a7f000000000000000000000000000000000000000000000000000000000000000081565b3480156104cb57600080fd5b5061031a60015481565b3480156104e157600080fd5b506102686104f03660046123fe565b610e1b565b34801561050157600080fd5b5060005461031a565b34801561051657600080fd5b50730576a174d229e3cfa37253523e645a78a0c91b575b60405173ffffffffffffffffffffffffffffffffffffffff90911681526020016102dc565b6105656105603660046123fe565b610e97565b604080519283526020830191909152016102dc565b34801561058657600080fd5b506102af610595366004612480565b7fbc197c810000000000000000000000000000000000000000000000000000000098975050505050505050565b3480156105ce57600080fd5b5061031a60025481565b3480156105e457600080fd5b506105f86105f336600461251e565b611034565b6040516102dc9190612604565b34801561061157600080fd5b5061031a610620366004612362565b60076020526000908152604090205481565b34801561063e57600080fd5b5061052d61064d3660046123e5565b60066020526000908152604090205473ffffffffffffffffffffffffffffffffffffffff1681565b34801561068157600080fd5b506106956106903660046123e5565b61111f565b6040516102dc9190612646565b3480156106ae57600080fd5b5061031a6106bd366004612687565b6111f9565b3480156106ce57600080fd5b5061031a61124b565b3480156106e357600080fd5b506102af6106f23660046126c1565b7ff23a6e61000000000000000000000000000000000000000000000000000000009695505050505050565b34801561072957600080fd5b5061031a7f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f81565b34801561075d57600080fd5b5061031a61076c36600461237f565b6112a6565b34801561077d57600080fd5b5061031a7f000000000000000000000000000000000000000000000000000000000000000081565b3480156107b157600080fd5b5061031a6107c036600461273d565b6112cb565b3480156107d157600080fd5b5061052d611380565b3480156107e657600080fd5b506102686107f5366004612796565b61139e565b34801561080657600080fd5b506105f86040518060400160405280600581526020017f312e302e3000000000000000000000000000000000000000000000000000000081525081565b600080600080610866856020810151604082015160609092015160001a92909190565b9094509250905060ff811660000361097f578285830160200161088882610c57565b1580156108ab575073ffffffffffffffffffffffffffffffffffffffff82163014155b156108de57507fffffffff0000000000000000000000000000000000000000000000000000000094506109e69350505050565b6040517f1626ba7e00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff831690631626ba7e90610932908b9085906004016127e6565b602060405180830381865afa15801561094f573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061097391906127ff565b955050505050506109e6565b61098e610423878386866115cb565b156109bf57507f1626ba7e0000000000000000000000000000000000000000000000000000000092506109e6915050565b507fffffffff00000000000000000000000000000000000000000000000000000000925050505b92915050565b6000806109f76115e9565b806020019051810190610a0a9190612841565b9392505050565b6000610a1b6116ba565b610a258484611739565b9050610a34604085018561286f565b9050600003610a4657610a4684611810565b610a0a8261188f565b73ffffffffffffffffffffffffffffffffffffffff8116600090815260086020526040812080543491908390610a86908490612903565b90915550506040805133815273ffffffffffffffffffffffffffffffffffffffff84166020820152348183015290517f4d1db39debc799df6a6a3bad1c8809c46cbe6eb3b784df03f50a061c487994c69181900360600190a1506001919050565b6002546060906000849003610afa578093505b80610b058486612903565b1115610b5757610b158385612903565b6040517f7ae596850000000000000000000000000000000000000000000000000000000081526004810191909152602481018290526044015b60405180910390fd5b8315610c50578367ffffffffffffffff811115610b7657610b766121ed565b604051908082528060200260200182016040528015610b9f578160200160208202803683370190505b50600080805260056020527f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bd549193505b84811015610bfc576000828152600560205260409020600101549150610bf581612945565b9050610bd0565b5060005b85811015610c4d5781848281518110610c1b57610c1b612916565b60209081029190910181019190915260009283526005905260409091206001015490610c4681612945565b9050610c00565b50505b5092915050565b6000806000610c646115e9565b806020019051810190610c779190612841565b915091508373ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16636352211e836040518263ffffffff1660e01b8152600401610ccd91815260200190565b602060405180830381865afa158015610cea573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610d0e919061297d565b73ffffffffffffffffffffffffffffffffffffffff1614949350505050565b610d3633610c57565b80610d54575033730576a174d229e3cfa37253523e645a78a0c91b57145b610de0576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152603e60248201527f4f6e6c792063616c6c61626c6520627920746865206d656368206f706572617460448201527f6f72206f722074686520656e74727920706f696e7420636f6e747261637400006064820152608401610b4e565b60018190556040518181527f66cbca4f3c64fecf1dcb9ce094abcf7f68c3450a1d4e3a8e917dd621edb4ebe09060200160405180910390a150565b610e236115e9565b5115610e8b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601360248201527f416c726561647920696e697469616c697a6564000000000000000000000000006044820152606401610b4e565b610e9481611906565b50565b600080610ea433846111f9565b33600081815260076020526040902054919350610ec29185906112cb565b9050610ecf348285611a80565b336000908152600460205260408120805491610eea83612945565b9091555050600081815260066020908152604080832080547fffffffffffffffffffffffff00000000000000000000000000000000000000001633908117909155835260079091528120805491610f4083612945565b90915550506005602052600081815260408082207f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bd80546001830181905590859055808452918320849055600280547f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bc94929392909190610fc083612945565b909155505060038054906000610fd583612945565b91905055503373ffffffffffffffffffffffffffffffffffffffff167f415baea36dd0457eaf27cbe8dd3691cb1d0b387aac1539c4d118198aba024db38686896040516110249392919061299a565b60405180910390a2505050915091565b606061103f33610c57565b8061105d575033730576a174d229e3cfa37253523e645a78a0c91b57145b6110e9576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152603e60248201527f4f6e6c792063616c6c61626c6520627920746865206d656368206f706572617460448201527f6f72206f722074686520656e74727920706f696e7420636f6e747261637400006064820152608401610b4e565b60006111048787878787156110fe5787611adb565b5a611adb565b925090508061111557815160208301fd5b5095945050505050565b60008181526006602052604081205473ffffffffffffffffffffffffffffffffffffffff16156111f4576000828152600560205260408082208151808301928390529160029082845b81548152602001906001019080831161116857505050505090508060006002811061119557611195612916565b60200201511580156111a957506020810151155b80156111df57506000805260056020527f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bc548314155b156111ed57600291506111f2565b600191505b505b919050565b6000828260405160200161120e9291906129c2565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe081840301815291905280516020909101209392505050565b60007f000000000000000000000000000000000000000000000000000000000000000046146112815761127c611be5565b905090565b507f000000000000000000000000000000000000000000000000000000000000000090565b600560205281600052604060002081600281106112c257600080fd5b01549150829050565b60006112d561124b565b8484846040516020016112ea939291906129f1565b604051602081830303815290604052805190602001206040516020016113429291907f190100000000000000000000000000000000000000000000000000000000000081526002810192909252602282015260420190565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08184030181529190528051602090910120949350505050565b60008061138b6115e9565b8060200190518101906109e6919061297d565b6113a733610c57565b806113c5575033730576a174d229e3cfa37253523e645a78a0c91b57145b611451576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152603e60248201527f4f6e6c792063616c6c61626c6520627920746865206d656368206f706572617460448201527f6f72206f722074686520656e74727920706f696e7420636f6e747261637400006064820152608401610b4e565b60008281526005602052604080822081518083019283905284939290919060029082845b8154815260200190600101908083116114755750505050509050806000600281106114a2576114a2612916565b60200201511580156114b657506020810151155b80156114ec57506000805260056020527f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bc548414155b15611526576040517ffe23980400000000000000000000000000000000000000000000000000000000815260048101859052602401610b4e565b6020818101805183516000908152600590935260408084206001908101929092558451925184528084209290925586835290822082815501819055600280549161156f83612a30565b91905055503373ffffffffffffffffffffffffffffffffffffffff167f0cd979445339c62199996f208428d987b1cea24d18e62b79ec24d94b636e8b7086846040516115bc9291906127e6565b60405180910390a25050505050565b60008060006115dc87878787611ce4565b9150915061111581611dd3565b606061127c6116b56040517fd60000000000000000000000000000000000000000000000000000000000000060208201527f940000000000000000000000000000000000000000000000000000000000000060218201527fffffffffffffffffffffffffffffffffffffffff0000000000000000000000003060601b1660228201527f010000000000000000000000000000000000000000000000000000000000000060368201526000906037016040516020818303038152906040528051906020012060001c905090565b611f86565b33730576a174d229e3cfa37253523e645a78a0c91b5714611737576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601c60248201527f6163636f756e743a206e6f742066726f6d20456e747279506f696e74000000006044820152606401610b4e565b565b7f19457468657265756d205369676e6564204d6573736167653a0a3332000000006000908152601c829052603c81207f1626ba7e000000000000000000000000000000000000000000000000000000006117d58261179b61014088018861286f565b8080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061084392505050565b7fffffffff0000000000000000000000000000000000000000000000000000000016146118065760019150506109e6565b5060009392505050565b600080546020830135918061182483612945565b9190505514610e94576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600d60248201527f496e76616c6964206e6f6e6365000000000000000000000000000000000000006044820152606401610b4e565b8015610e945760405160009033907fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff90849084818181858888f193505050503d80600081146118fa576040519150601f19603f3d011682016040523d82523d6000602084013e6118ff565b606091505b5050505050565b600061191182611fdc565b905060008151602083016000f090506119e76040517fd60000000000000000000000000000000000000000000000000000000000000060208201527f940000000000000000000000000000000000000000000000000000000000000060218201527fffffffffffffffffffffffffffffffffffffffff0000000000000000000000003060601b1660228201527f010000000000000000000000000000000000000000000000000000000000000060368201526000906037016040516020818303038152906040528051906020012060001c905090565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614611a7b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600c60248201527f5772697465206661696c656400000000000000000000000000000000000000006044820152606401610b4e565b505050565b82158015611a9f57503360009081526008602052604090205460015411155b15611ad0576001543360009081526008602052604081208054909190611ac6908490612a65565b9091555050505050565b611a7b838383612014565b600060606001846001811115611af357611af3612617565b03611b6a578673ffffffffffffffffffffffffffffffffffffffff168386604051611b1e9190612a78565b6000604051808303818686f4925050503d8060008114611b5a576040519150601f19603f3d011682016040523d82523d6000602084013e611b5f565b606091505b509092509050611bdb565b8673ffffffffffffffffffffffffffffffffffffffff16838787604051611b919190612a78565b600060405180830381858888f193505050503d8060008114611bcf576040519150601f19603f3d011682016040523d82523d6000602084013e611bd4565b606091505b5090925090505b9550959350505050565b60007f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f7f493aeac1d921aa02a044029e7fe4be43b1a4e80b40706fa5819e8fbb0d0935256040518060400160405280600581526020017f312e302e30000000000000000000000000000000000000000000000000000000815250604051602001611c6f9190612604565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe081840301815282825280516020918201209083019490945281019190915260608101919091524660808201523060a082015260c00160405160208183030381529060405280519060200120905090565b6000807f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a0831115611d1b5750600090506003611dca565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa158015611d6f573d6000803e3d6000fd5b50506040517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0015191505073ffffffffffffffffffffffffffffffffffffffff8116611dc357600060019250925050611dca565b9150600090505b94509492505050565b6000816004811115611de757611de7612617565b03611def5750565b6001816004811115611e0357611e03612617565b03611e6a576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601860248201527f45434453413a20696e76616c6964207369676e617475726500000000000000006044820152606401610b4e565b6002816004811115611e7e57611e7e612617565b03611ee5576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610b4e565b6003816004811115611ef957611ef9612617565b03610e94576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c60448201527f75650000000000000000000000000000000000000000000000000000000000006064820152608401610b4e565b6060813b60018111611fa8575050604080516020810190915260008152919050565b80611fb281612a30565b9150506040519150601f19601f602083010116820160405280825280600160208401853c50919050565b606081516001611fec9190612903565b82604051602001611ffe929190612a94565b6040516020818303038152906040529050919050565b600154831015611a7b576001546040517fb4897828000000000000000000000000000000000000000000000000000000008152610b4e918591600401918252602082015260400190565b73ffffffffffffffffffffffffffffffffffffffff81168114610e9457600080fd5b60008083601f84011261209257600080fd5b50813567ffffffffffffffff8111156120aa57600080fd5b6020830191508360208285010111156120c257600080fd5b9250929050565b60008060008060008060008060c0898b0312156120e557600080fd5b88356120f08161205e565b975060208901356121008161205e565b965060408901356121108161205e565b955060608901359450608089013567ffffffffffffffff8082111561213457600080fd5b6121408c838d01612080565b909650945060a08b013591508082111561215957600080fd5b506121668b828c01612080565b999c989b5096995094979396929594505050565b60008060008060006080868803121561219257600080fd5b853561219d8161205e565b945060208601356121ad8161205e565b935060408601359250606086013567ffffffffffffffff8111156121d057600080fd5b6121dc88828901612080565b969995985093965092949392505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b600082601f83011261222d57600080fd5b813567ffffffffffffffff80821115612248576122486121ed565b604051601f83017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0908116603f0116810190828211818310171561228e5761228e6121ed565b816040528381528660208588010111156122a757600080fd5b836020870160208301376000602085830101528094505050505092915050565b600080604083850312156122da57600080fd5b82359150602083013567ffffffffffffffff8111156122f857600080fd5b6123048582860161221c565b9150509250929050565b60008060006060848603121561232357600080fd5b833567ffffffffffffffff81111561233a57600080fd5b8401610160818703121561234d57600080fd5b95602085013595506040909401359392505050565b60006020828403121561237457600080fd5b8135610a0a8161205e565b6000806040838503121561239257600080fd5b50508035926020909101359150565b6020808252825182820181905260009190848201906040850190845b818110156123d9578351835292840192918401916001016123bd565b50909695505050505050565b6000602082840312156123f757600080fd5b5035919050565b60006020828403121561241057600080fd5b813567ffffffffffffffff81111561242757600080fd5b6124338482850161221c565b949350505050565b60008083601f84011261244d57600080fd5b50813567ffffffffffffffff81111561246557600080fd5b6020830191508360208260051b85010111156120c257600080fd5b60008060008060008060008060a0898b03121561249c57600080fd5b88356124a78161205e565b975060208901356124b78161205e565b9650604089013567ffffffffffffffff808211156124d457600080fd5b6124e08c838d0161243b565b909850965060608b01359150808211156124f957600080fd5b6125058c838d0161243b565b909650945060808b013591508082111561215957600080fd5b600080600080600060a0868803121561253657600080fd5b85356125418161205e565b945060208601359350604086013567ffffffffffffffff81111561256457600080fd5b6125708882890161221c565b93505060608601356002811061258557600080fd5b949793965091946080013592915050565b60005b838110156125b1578181015183820152602001612599565b50506000910152565b600081518084526125d2816020860160208601612596565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169290920160200192915050565b602081526000610a0a60208301846125ba565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b6020810160038310612681577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b91905290565b6000806040838503121561269a57600080fd5b82356126a58161205e565b9150602083013567ffffffffffffffff8111156122f857600080fd5b60008060008060008060a087890312156126da57600080fd5b86356126e58161205e565b955060208701356126f58161205e565b94506040870135935060608701359250608087013567ffffffffffffffff81111561271f57600080fd5b61272b89828a01612080565b979a9699509497509295939492505050565b60008060006060848603121561275257600080fd5b833561275d8161205e565b9250602084013567ffffffffffffffff81111561277957600080fd5b6127858682870161221c565b925050604084013590509250925092565b6000806000606084860312156127ab57600080fd5b8335925060208401359150604084013567ffffffffffffffff8111156127d057600080fd5b6127dc8682870161221c565b9150509250925092565b82815260406020820152600061243360408301846125ba565b60006020828403121561281157600080fd5b81517fffffffff0000000000000000000000000000000000000000000000000000000081168114610a0a57600080fd5b6000806040838503121561285457600080fd5b825161285f8161205e565b6020939093015192949293505050565b60008083357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe18436030181126128a457600080fd5b83018035915067ffffffffffffffff8211156128bf57600080fd5b6020019150368190038213156120c257600080fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b808201808211156109e6576109e66128d4565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8203612976576129766128d4565b5060010190565b60006020828403121561298f57600080fd5b8151610a0a8161205e565b8381528260208201526060604082015260006129b960608301846125ba565b95945050505050565b73ffffffffffffffffffffffffffffffffffffffff8316815260406020820152600061243360408301846125ba565b73ffffffffffffffffffffffffffffffffffffffff84168152606060208201526000612a2060608301856125ba565b9050826040830152949350505050565b600081612a3f57612a3f6128d4565b507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0190565b818103818111156109e6576109e66128d4565b60008251612a8a818460208701612596565b9190910192915050565b7f630000000000000000000000000000000000000000000000000000000000000081527fffffffff000000000000000000000000000000000000000000000000000000008360e01b1660018201527f80600e6000396000f3000000000000000000000000000000000000000000000060058201526000600e82015260008251612b2481600f850160208701612596565b91909101600f01939250505056fea26469706673582212209a0ab5e2ee30980a5f0e6bb806a575bc80cefff6d9d9a6dba6545ff1c3ef9df864736f6c63430008150033", + "deployedBytecode": "0x6080604052600436106102375760003560e01c8063b0d691fe11610138578063ed24911d116100b0578063f698da251161007f578063fc0c546a11610064578063fc0c546a146107c5578063fe266bb9146107da578063ffa1ad74146107fa57600080fd5b8063f698da2514610771578063fba5c56b146107a557600080fd5b8063ed24911d146106c2578063f23a6e61146106d7578063f5dcb7bb1461071d578063f6171e441461075157600080fd5b8063c7dec3fc11610107578063d843b7f4116100ec578063d843b7f414610632578063d8a4676f14610675578063e00b9118146106a257600080fd5b8063c7dec3fc146105d8578063cbd6407a1461060557600080fd5b8063b0d691fe1461050a578063b94207d314610552578063bc197c811461057a578063bdf86317146105c257600080fd5b80635e988032116101cb57806391b7f5ed1161019a578063a035b1fe1161017f578063a035b1fe146104bf578063a4f9edbf146104d5578063affed0e0146104f557600080fd5b806391b7f5ed1461046b5780639a8a05921461048b57600080fd5b80635e988032146103ae5780635fee6085146103db5780636d70f7ae146104085780637af734731461042857600080fd5b80633a871cdd116102075780633a871cdd1461032857806341a7726a146103485780634ada3e611461036b57806358ce09091461038157600080fd5b806223de2914610243578063150b7a021461026a5780631626ba7e146102e557806317d70f7c1461030557600080fd5b3661023e57005b600080fd5b34801561024f57600080fd5b5061026861025e3660046120c9565b5050505050505050565b005b34801561027657600080fd5b506102af61028536600461217a565b7f150b7a020000000000000000000000000000000000000000000000000000000095945050505050565b6040517fffffffff0000000000000000000000000000000000000000000000000000000090911681526020015b60405180910390f35b3480156102f157600080fd5b506102af6103003660046122c7565b610843565b34801561031157600080fd5b5061031a6109ec565b6040519081526020016102dc565b34801561033457600080fd5b5061031a61034336600461230e565b610a11565b61035b610356366004612362565b610a4f565b60405190151581526020016102dc565b34801561037757600080fd5b5061031a60035481565b34801561038d57600080fd5b506103a161039c36600461237f565b610ae7565b6040516102dc91906123a1565b3480156103ba57600080fd5b5061031a6103c9366004612362565b60086020526000908152604090205481565b3480156103e757600080fd5b5061031a6103f6366004612362565b60046020526000908152604090205481565b34801561041457600080fd5b5061035b610423366004612362565b610c57565b34801561043457600080fd5b5061031a610443366004612362565b73ffffffffffffffffffffffffffffffffffffffff1660009081526004602052604090205490565b34801561047757600080fd5b506102686104863660046123e5565b610d2d565b34801561049757600080fd5b5061031a7f000000000000000000000000000000000000000000000000000000000000000081565b3480156104cb57600080fd5b5061031a60015481565b3480156104e157600080fd5b506102686104f03660046123fe565b610e1b565b34801561050157600080fd5b5060005461031a565b34801561051657600080fd5b50730576a174d229e3cfa37253523e645a78a0c91b575b60405173ffffffffffffffffffffffffffffffffffffffff90911681526020016102dc565b6105656105603660046123fe565b610e97565b604080519283526020830191909152016102dc565b34801561058657600080fd5b506102af610595366004612480565b7fbc197c810000000000000000000000000000000000000000000000000000000098975050505050505050565b3480156105ce57600080fd5b5061031a60025481565b3480156105e457600080fd5b506105f86105f336600461251e565b611034565b6040516102dc9190612604565b34801561061157600080fd5b5061031a610620366004612362565b60076020526000908152604090205481565b34801561063e57600080fd5b5061052d61064d3660046123e5565b60066020526000908152604090205473ffffffffffffffffffffffffffffffffffffffff1681565b34801561068157600080fd5b506106956106903660046123e5565b61111f565b6040516102dc9190612646565b3480156106ae57600080fd5b5061031a6106bd366004612687565b6111f9565b3480156106ce57600080fd5b5061031a61124b565b3480156106e357600080fd5b506102af6106f23660046126c1565b7ff23a6e61000000000000000000000000000000000000000000000000000000009695505050505050565b34801561072957600080fd5b5061031a7f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f81565b34801561075d57600080fd5b5061031a61076c36600461237f565b6112a6565b34801561077d57600080fd5b5061031a7f000000000000000000000000000000000000000000000000000000000000000081565b3480156107b157600080fd5b5061031a6107c036600461273d565b6112cb565b3480156107d157600080fd5b5061052d611380565b3480156107e657600080fd5b506102686107f5366004612796565b61139e565b34801561080657600080fd5b506105f86040518060400160405280600581526020017f312e302e3000000000000000000000000000000000000000000000000000000081525081565b600080600080610866856020810151604082015160609092015160001a92909190565b9094509250905060ff811660000361097f578285830160200161088882610c57565b1580156108ab575073ffffffffffffffffffffffffffffffffffffffff82163014155b156108de57507fffffffff0000000000000000000000000000000000000000000000000000000094506109e69350505050565b6040517f1626ba7e00000000000000000000000000000000000000000000000000000000815273ffffffffffffffffffffffffffffffffffffffff831690631626ba7e90610932908b9085906004016127e6565b602060405180830381865afa15801561094f573d6000803e3d6000fd5b505050506040513d601f19601f8201168201806040525081019061097391906127ff565b955050505050506109e6565b61098e610423878386866115cb565b156109bf57507f1626ba7e0000000000000000000000000000000000000000000000000000000092506109e6915050565b507fffffffff00000000000000000000000000000000000000000000000000000000925050505b92915050565b6000806109f76115e9565b806020019051810190610a0a9190612841565b9392505050565b6000610a1b6116ba565b610a258484611739565b9050610a34604085018561286f565b9050600003610a4657610a4684611810565b610a0a8261188f565b73ffffffffffffffffffffffffffffffffffffffff8116600090815260086020526040812080543491908390610a86908490612903565b90915550506040805133815273ffffffffffffffffffffffffffffffffffffffff84166020820152348183015290517f4d1db39debc799df6a6a3bad1c8809c46cbe6eb3b784df03f50a061c487994c69181900360600190a1506001919050565b6002546060906000849003610afa578093505b80610b058486612903565b1115610b5757610b158385612903565b6040517f7ae596850000000000000000000000000000000000000000000000000000000081526004810191909152602481018290526044015b60405180910390fd5b8315610c50578367ffffffffffffffff811115610b7657610b766121ed565b604051908082528060200260200182016040528015610b9f578160200160208202803683370190505b50600080805260056020527f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bd549193505b84811015610bfc576000828152600560205260409020600101549150610bf581612945565b9050610bd0565b5060005b85811015610c4d5781848281518110610c1b57610c1b612916565b60209081029190910181019190915260009283526005905260409091206001015490610c4681612945565b9050610c00565b50505b5092915050565b6000806000610c646115e9565b806020019051810190610c779190612841565b915091508373ffffffffffffffffffffffffffffffffffffffff168273ffffffffffffffffffffffffffffffffffffffff16636352211e836040518263ffffffff1660e01b8152600401610ccd91815260200190565b602060405180830381865afa158015610cea573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190610d0e919061297d565b73ffffffffffffffffffffffffffffffffffffffff1614949350505050565b610d3633610c57565b80610d54575033730576a174d229e3cfa37253523e645a78a0c91b57145b610de0576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152603e60248201527f4f6e6c792063616c6c61626c6520627920746865206d656368206f706572617460448201527f6f72206f722074686520656e74727920706f696e7420636f6e747261637400006064820152608401610b4e565b60018190556040518181527f66cbca4f3c64fecf1dcb9ce094abcf7f68c3450a1d4e3a8e917dd621edb4ebe09060200160405180910390a150565b610e236115e9565b5115610e8b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601360248201527f416c726561647920696e697469616c697a6564000000000000000000000000006044820152606401610b4e565b610e9481611906565b50565b600080610ea433846111f9565b33600081815260076020526040902054919350610ec29185906112cb565b9050610ecf348285611a80565b336000908152600460205260408120805491610eea83612945565b9091555050600081815260066020908152604080832080547fffffffffffffffffffffffff00000000000000000000000000000000000000001633908117909155835260079091528120805491610f4083612945565b90915550506005602052600081815260408082207f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bd80546001830181905590859055808452918320849055600280547f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bc94929392909190610fc083612945565b909155505060038054906000610fd583612945565b91905055503373ffffffffffffffffffffffffffffffffffffffff167f415baea36dd0457eaf27cbe8dd3691cb1d0b387aac1539c4d118198aba024db38686896040516110249392919061299a565b60405180910390a2505050915091565b606061103f33610c57565b8061105d575033730576a174d229e3cfa37253523e645a78a0c91b57145b6110e9576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152603e60248201527f4f6e6c792063616c6c61626c6520627920746865206d656368206f706572617460448201527f6f72206f722074686520656e74727920706f696e7420636f6e747261637400006064820152608401610b4e565b60006111048787878787156110fe5787611adb565b5a611adb565b925090508061111557815160208301fd5b5095945050505050565b60008181526006602052604081205473ffffffffffffffffffffffffffffffffffffffff16156111f4576000828152600560205260408082208151808301928390529160029082845b81548152602001906001019080831161116857505050505090508060006002811061119557611195612916565b60200201511580156111a957506020810151155b80156111df57506000805260056020527f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bc548314155b156111ed57600291506111f2565b600191505b505b919050565b6000828260405160200161120e9291906129c2565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe081840301815291905280516020909101209392505050565b60007f000000000000000000000000000000000000000000000000000000000000000046146112815761127c611be5565b905090565b507f000000000000000000000000000000000000000000000000000000000000000090565b600560205281600052604060002081600281106112c257600080fd5b01549150829050565b60006112d561124b565b8484846040516020016112ea939291906129f1565b604051602081830303815290604052805190602001206040516020016113429291907f190100000000000000000000000000000000000000000000000000000000000081526002810192909252602282015260420190565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe08184030181529190528051602090910120949350505050565b60008061138b6115e9565b8060200190518101906109e6919061297d565b6113a733610c57565b806113c5575033730576a174d229e3cfa37253523e645a78a0c91b57145b611451576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152603e60248201527f4f6e6c792063616c6c61626c6520627920746865206d656368206f706572617460448201527f6f72206f722074686520656e74727920706f696e7420636f6e747261637400006064820152608401610b4e565b60008281526005602052604080822081518083019283905284939290919060029082845b8154815260200190600101908083116114755750505050509050806000600281106114a2576114a2612916565b60200201511580156114b657506020810151155b80156114ec57506000805260056020527f05b8ccbb9d4d8fb16ea74ce3c29a41f1b461fbdaff4714a0d9a8eb05499746bc548414155b15611526576040517ffe23980400000000000000000000000000000000000000000000000000000000815260048101859052602401610b4e565b6020818101805183516000908152600590935260408084206001908101929092558451925184528084209290925586835290822082815501819055600280549161156f83612a30565b91905055503373ffffffffffffffffffffffffffffffffffffffff167f0cd979445339c62199996f208428d987b1cea24d18e62b79ec24d94b636e8b7086846040516115bc9291906127e6565b60405180910390a25050505050565b60008060006115dc87878787611ce4565b9150915061111581611dd3565b606061127c6116b56040517fd60000000000000000000000000000000000000000000000000000000000000060208201527f940000000000000000000000000000000000000000000000000000000000000060218201527fffffffffffffffffffffffffffffffffffffffff0000000000000000000000003060601b1660228201527f010000000000000000000000000000000000000000000000000000000000000060368201526000906037016040516020818303038152906040528051906020012060001c905090565b611f86565b33730576a174d229e3cfa37253523e645a78a0c91b5714611737576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601c60248201527f6163636f756e743a206e6f742066726f6d20456e747279506f696e74000000006044820152606401610b4e565b565b7f19457468657265756d205369676e6564204d6573736167653a0a3332000000006000908152601c829052603c81207f1626ba7e000000000000000000000000000000000000000000000000000000006117d58261179b61014088018861286f565b8080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525061084392505050565b7fffffffff0000000000000000000000000000000000000000000000000000000016146118065760019150506109e6565b5060009392505050565b600080546020830135918061182483612945565b9190505514610e94576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600d60248201527f496e76616c6964206e6f6e6365000000000000000000000000000000000000006044820152606401610b4e565b8015610e945760405160009033907fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff90849084818181858888f193505050503d80600081146118fa576040519150601f19603f3d011682016040523d82523d6000602084013e6118ff565b606091505b5050505050565b600061191182611fdc565b905060008151602083016000f090506119e76040517fd60000000000000000000000000000000000000000000000000000000000000060208201527f940000000000000000000000000000000000000000000000000000000000000060218201527fffffffffffffffffffffffffffffffffffffffff0000000000000000000000003060601b1660228201527f010000000000000000000000000000000000000000000000000000000000000060368201526000906037016040516020818303038152906040528051906020012060001c905090565b73ffffffffffffffffffffffffffffffffffffffff168173ffffffffffffffffffffffffffffffffffffffff1614611a7b576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152600c60248201527f5772697465206661696c656400000000000000000000000000000000000000006044820152606401610b4e565b505050565b82158015611a9f57503360009081526008602052604090205460015411155b15611ad0576001543360009081526008602052604081208054909190611ac6908490612a65565b9091555050505050565b611a7b838383612014565b600060606001846001811115611af357611af3612617565b03611b6a578673ffffffffffffffffffffffffffffffffffffffff168386604051611b1e9190612a78565b6000604051808303818686f4925050503d8060008114611b5a576040519150601f19603f3d011682016040523d82523d6000602084013e611b5f565b606091505b509092509050611bdb565b8673ffffffffffffffffffffffffffffffffffffffff16838787604051611b919190612a78565b600060405180830381858888f193505050503d8060008114611bcf576040519150601f19603f3d011682016040523d82523d6000602084013e611bd4565b606091505b5090925090505b9550959350505050565b60007f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f7f493aeac1d921aa02a044029e7fe4be43b1a4e80b40706fa5819e8fbb0d0935256040518060400160405280600581526020017f312e302e30000000000000000000000000000000000000000000000000000000815250604051602001611c6f9190612604565b604080517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe081840301815282825280516020918201209083019490945281019190915260608101919091524660808201523060a082015260c00160405160208183030381529060405280519060200120905090565b6000807f7fffffffffffffffffffffffffffffff5d576e7357a4501ddfe92f46681b20a0831115611d1b5750600090506003611dca565b6040805160008082526020820180845289905260ff881692820192909252606081018690526080810185905260019060a0016020604051602081039080840390855afa158015611d6f573d6000803e3d6000fd5b50506040517fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0015191505073ffffffffffffffffffffffffffffffffffffffff8116611dc357600060019250925050611dca565b9150600090505b94509492505050565b6000816004811115611de757611de7612617565b03611def5750565b6001816004811115611e0357611e03612617565b03611e6a576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601860248201527f45434453413a20696e76616c6964207369676e617475726500000000000000006044820152606401610b4e565b6002816004811115611e7e57611e7e612617565b03611ee5576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152601f60248201527f45434453413a20696e76616c6964207369676e6174757265206c656e677468006044820152606401610b4e565b6003816004811115611ef957611ef9612617565b03610e94576040517f08c379a000000000000000000000000000000000000000000000000000000000815260206004820152602260248201527f45434453413a20696e76616c6964207369676e6174757265202773272076616c60448201527f75650000000000000000000000000000000000000000000000000000000000006064820152608401610b4e565b6060813b60018111611fa8575050604080516020810190915260008152919050565b80611fb281612a30565b9150506040519150601f19601f602083010116820160405280825280600160208401853c50919050565b606081516001611fec9190612903565b82604051602001611ffe929190612a94565b6040516020818303038152906040529050919050565b600154831015611a7b576001546040517fb4897828000000000000000000000000000000000000000000000000000000008152610b4e918591600401918252602082015260400190565b73ffffffffffffffffffffffffffffffffffffffff81168114610e9457600080fd5b60008083601f84011261209257600080fd5b50813567ffffffffffffffff8111156120aa57600080fd5b6020830191508360208285010111156120c257600080fd5b9250929050565b60008060008060008060008060c0898b0312156120e557600080fd5b88356120f08161205e565b975060208901356121008161205e565b965060408901356121108161205e565b955060608901359450608089013567ffffffffffffffff8082111561213457600080fd5b6121408c838d01612080565b909650945060a08b013591508082111561215957600080fd5b506121668b828c01612080565b999c989b5096995094979396929594505050565b60008060008060006080868803121561219257600080fd5b853561219d8161205e565b945060208601356121ad8161205e565b935060408601359250606086013567ffffffffffffffff8111156121d057600080fd5b6121dc88828901612080565b969995985093965092949392505050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b600082601f83011261222d57600080fd5b813567ffffffffffffffff80821115612248576122486121ed565b604051601f83017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0908116603f0116810190828211818310171561228e5761228e6121ed565b816040528381528660208588010111156122a757600080fd5b836020870160208301376000602085830101528094505050505092915050565b600080604083850312156122da57600080fd5b82359150602083013567ffffffffffffffff8111156122f857600080fd5b6123048582860161221c565b9150509250929050565b60008060006060848603121561232357600080fd5b833567ffffffffffffffff81111561233a57600080fd5b8401610160818703121561234d57600080fd5b95602085013595506040909401359392505050565b60006020828403121561237457600080fd5b8135610a0a8161205e565b6000806040838503121561239257600080fd5b50508035926020909101359150565b6020808252825182820181905260009190848201906040850190845b818110156123d9578351835292840192918401916001016123bd565b50909695505050505050565b6000602082840312156123f757600080fd5b5035919050565b60006020828403121561241057600080fd5b813567ffffffffffffffff81111561242757600080fd5b6124338482850161221c565b949350505050565b60008083601f84011261244d57600080fd5b50813567ffffffffffffffff81111561246557600080fd5b6020830191508360208260051b85010111156120c257600080fd5b60008060008060008060008060a0898b03121561249c57600080fd5b88356124a78161205e565b975060208901356124b78161205e565b9650604089013567ffffffffffffffff808211156124d457600080fd5b6124e08c838d0161243b565b909850965060608b01359150808211156124f957600080fd5b6125058c838d0161243b565b909650945060808b013591508082111561215957600080fd5b600080600080600060a0868803121561253657600080fd5b85356125418161205e565b945060208601359350604086013567ffffffffffffffff81111561256457600080fd5b6125708882890161221c565b93505060608601356002811061258557600080fd5b949793965091946080013592915050565b60005b838110156125b1578181015183820152602001612599565b50506000910152565b600081518084526125d2816020860160208601612596565b601f017fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe0169290920160200192915050565b602081526000610a0a60208301846125ba565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b6020810160038310612681577f4e487b7100000000000000000000000000000000000000000000000000000000600052602160045260246000fd5b91905290565b6000806040838503121561269a57600080fd5b82356126a58161205e565b9150602083013567ffffffffffffffff8111156122f857600080fd5b60008060008060008060a087890312156126da57600080fd5b86356126e58161205e565b955060208701356126f58161205e565b94506040870135935060608701359250608087013567ffffffffffffffff81111561271f57600080fd5b61272b89828a01612080565b979a9699509497509295939492505050565b60008060006060848603121561275257600080fd5b833561275d8161205e565b9250602084013567ffffffffffffffff81111561277957600080fd5b6127858682870161221c565b925050604084013590509250925092565b6000806000606084860312156127ab57600080fd5b8335925060208401359150604084013567ffffffffffffffff8111156127d057600080fd5b6127dc8682870161221c565b9150509250925092565b82815260406020820152600061243360408301846125ba565b60006020828403121561281157600080fd5b81517fffffffff0000000000000000000000000000000000000000000000000000000081168114610a0a57600080fd5b6000806040838503121561285457600080fd5b825161285f8161205e565b6020939093015192949293505050565b60008083357fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe18436030181126128a457600080fd5b83018035915067ffffffffffffffff8211156128bf57600080fd5b6020019150368190038213156120c257600080fd5b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b808201808211156109e6576109e66128d4565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b60007fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff8203612976576129766128d4565b5060010190565b60006020828403121561298f57600080fd5b8151610a0a8161205e565b8381528260208201526060604082015260006129b960608301846125ba565b95945050505050565b73ffffffffffffffffffffffffffffffffffffffff8316815260406020820152600061243360408301846125ba565b73ffffffffffffffffffffffffffffffffffffffff84168152606060208201526000612a2060608301856125ba565b9050826040830152949350505050565b600081612a3f57612a3f6128d4565b507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0190565b818103818111156109e6576109e66128d4565b60008251612a8a818460208701612596565b9190910192915050565b7f630000000000000000000000000000000000000000000000000000000000000081527fffffffff000000000000000000000000000000000000000000000000000000008360e01b1660018201527f80600e6000396000f3000000000000000000000000000000000000000000000060058201526000600e82015260008251612b2481600f850160208701612596565b91909101600f01939250505056fea26469706673582212209a0ab5e2ee30980a5f0e6bb806a575bc80cefff6d9d9a6dba6545ff1c3ef9df864736f6c63430008150033", + "linkReferences": {}, + "deployedLinkReferences": {} +} \ No newline at end of file diff --git a/packages/valory/contracts/mech_marketplace/contract.py b/packages/valory/contracts/mech_marketplace/contract.py new file mode 100644 index 00000000..9b952c65 --- /dev/null +++ b/packages/valory/contracts/mech_marketplace/contract.py @@ -0,0 +1,336 @@ +# -*- coding: utf-8 -*- +# ------------------------------------------------------------------------------ +# +# Copyright 2023-2024 Valory AG +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +# ------------------------------------------------------------------------------ + +"""This module contains the dynamic_contribution contract definition.""" +import logging +from enum import Enum +from typing import Any, Dict, List, Optional, cast + +from aea.common import JSONLike +from aea.configurations.base import PublicId +from aea.contracts.base import Contract +from aea.crypto.base import LedgerApi +from aea_ledger_ethereum import EthereumApi +from web3 import Web3 +from web3.types import BlockIdentifier, TxReceipt + + +PUBLIC_ID = PublicId.from_str("valory/agent_mech:0.1.0") + +_logger = logging.getLogger( + f"aea.packages.{PUBLIC_ID.author}.contracts.{PUBLIC_ID.name}.contract" +) + + +BATCH_PRIORITY_PASSED_DATA = { + "abi": [ + { + "inputs": [ + { + "internalType": "contract IMechMarketplace", + "name": "_marketplace", + "type": "address" + }, + { + "internalType": "uint256[]", + "name": "_requestIds", + "type": "uint256[]" + } + ], + "stateMutability": "nonpayable", + "type": "constructor" + } + ], + "bytecode": "0x608060405234801561001057600080fd5b5060405161078c38038061078c8339818101604052810190610032919061046d565b60008151905060008167ffffffffffffffff811115610054576100536102f4565b5b6040519080825280602002602001820160405280156100825781602001602082028036833780820191505090505b5090506000805b8381101561018d5760008673ffffffffffffffffffffffffffffffffffffffff1663cb261bec8784815181106100c2576100c16104c9565b5b60200260200101516040518263ffffffff1660e01b81526004016100e69190610507565b608060405180830381865afa158015610103573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906101279190610607565b9050806060015163ffffffff1642106101815785828151811061014d5761014c6104c9565b5b6020026020010151848481518110610168576101676104c9565b5b6020026020010181815250508261017e90610663565b92505b81600101915050610089565b5060008167ffffffffffffffff8111156101aa576101a96102f4565b5b6040519080825280602002602001820160405280156101d85781602001602082028036833780820191505090505b50905060005b8281101561022b578381815181106101f9576101f86104c9565b5b6020026020010151828281518110610214576102136104c9565b5b6020026020010181815250508060010190506101de565b5060008160405160200161023f9190610769565b60405160208183030381529060405290506020810180590381f35b6000604051905090565b600080fd5b600080fd5b600073ffffffffffffffffffffffffffffffffffffffff82169050919050565b60006102998261026e565b9050919050565b60006102ab8261028e565b9050919050565b6102bb816102a0565b81146102c657600080fd5b50565b6000815190506102d8816102b2565b92915050565b600080fd5b6000601f19601f8301169050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052604160045260246000fd5b61032c826102e3565b810181811067ffffffffffffffff8211171561034b5761034a6102f4565b5b80604052505050565b600061035e61025a565b905061036a8282610323565b919050565b600067ffffffffffffffff82111561038a576103896102f4565b5b602082029050602081019050919050565b600080fd5b6000819050919050565b6103b3816103a0565b81146103be57600080fd5b50565b6000815190506103d0816103aa565b92915050565b60006103e96103e48461036f565b610354565b9050808382526020820190506020840283018581111561040c5761040b61039b565b5b835b81811015610435578061042188826103c1565b84526020840193505060208101905061040e565b5050509392505050565b600082601f830112610454576104536102de565b5b81516104648482602086016103d6565b91505092915050565b6000806040838503121561048457610483610264565b5b6000610492858286016102c9565b925050602083015167ffffffffffffffff8111156104b3576104b2610269565b5b6104bf8582860161043f565b9150509250929050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052603260045260246000fd5b610501816103a0565b82525050565b600060208201905061051c60008301846104f8565b92915050565b600080fd5b6105308161028e565b811461053b57600080fd5b50565b60008151905061054d81610527565b92915050565b600063ffffffff82169050919050565b61056c81610553565b811461057757600080fd5b50565b60008151905061058981610563565b92915050565b6000608082840312156105a5576105a4610522565b5b6105af6080610354565b905060006105bf8482850161053e565b60008301525060206105d38482850161053e565b60208301525060406105e78482850161053e565b60408301525060606105fb8482850161057a565b60608301525092915050565b60006080828403121561061d5761061c610264565b5b600061062b8482850161058f565b91505092915050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fd5b600061066e826103a0565b91507fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff82036106a05761069f610634565b5b600182019050919050565b600081519050919050565b600082825260208201905092915050565b6000819050602082019050919050565b6106e0816103a0565b82525050565b60006106f283836106d7565b60208301905092915050565b6000602082019050919050565b6000610716826106ab565b61072081856106b6565b935061072b836106c7565b8060005b8381101561075c57815161074388826106e6565b975061074e836106fe565b92505060018101905061072f565b5085935050505092915050565b60006020820190508181036000830152610783818461070b565b90509291505056fe", +} + + +class MechOperation(Enum): + """Operation types.""" + + CALL = 0 + DELEGATE_CALL = 1 + + +class MechMarketplaceContract(Contract): + """The scaffold contract class for a smart contract.""" + + contract_id = PublicId.from_str("valory/mech_marketplace:0.1.0") + + @classmethod + def get_raw_transaction( + cls, ledger_api: LedgerApi, contract_address: str, **kwargs: Any + ) -> JSONLike: + """ + Handler method for the 'GET_RAW_TRANSACTION' requests. + + Implement this method in the sub class if you want + to handle the contract requests manually. + + :param ledger_api: the ledger apis. + :param contract_address: the contract address. + :param kwargs: the keyword arguments. + :return: the tx # noqa: DAR202 + """ + raise NotImplementedError + + @classmethod + def get_raw_message( + cls, ledger_api: LedgerApi, contract_address: str, **kwargs: Any + ) -> bytes: + """ + Handler method for the 'GET_RAW_MESSAGE' requests. + + Implement this method in the sub class if you want + to handle the contract requests manually. + + :param ledger_api: the ledger apis. + :param contract_address: the contract address. + :param kwargs: the keyword arguments. + :return: the tx # noqa: DAR202 + """ + raise NotImplementedError + + @classmethod + def get_state( + cls, ledger_api: LedgerApi, contract_address: str, **kwargs: Any + ) -> JSONLike: + """ + Handler method for the 'GET_STATE' requests. + + Implement this method in the sub class if you want + to handle the contract requests manually. + + :param ledger_api: the ledger apis. + :param contract_address: the contract address. + :param kwargs: the keyword arguments. + :return: the tx # noqa: DAR202 + """ + raise NotImplementedError + + @classmethod + def get_deliver_data( + cls, + ledger_api: LedgerApi, + contract_address: str, + sender_address: str, + request_id: int, + data: str, + delivery_mech_staking_instance: str, + delivery_mech_service_id: int, + ) -> JSONLike: + """ + Deliver a response to a request. + + :param ledger_api: LedgerApi object + :param contract_address: the address of the token to be used + :param sender_address: the address of the sender + :param request_id: the id of the target request + :param data: the response data + :param delivery_mech_staking_instance: the staking instance + :param delivery_mech_service_id: the service id + :return: the deliver data + """ + ledger_api = cast(EthereumApi, ledger_api) + contract_instance = cls.get_instance(ledger_api, contract_address) + data = contract_instance.encodeABI( + fn_name="deliverMarketplace", + args=[ + request_id, + data, + delivery_mech_staking_instance, + delivery_mech_service_id, + ], + + ) + + simulation_ok = cls.simulate_tx( + ledger_api, contract_address, sender_address, data + ).pop("data") + return {"data": bytes.fromhex(data[2:]), "simulation_ok": simulation_ok} # type: ignore + + @classmethod + def get_request_events( + cls, + ledger_api: LedgerApi, + contract_address: str, + from_block: BlockIdentifier = "earliest", + to_block: BlockIdentifier = "latest", + ) -> JSONLike: + """Get the Request events emitted by the contract.""" + ledger_api = cast(EthereumApi, ledger_api) + contract_instance = cls.get_instance(ledger_api, contract_address) + entries = contract_instance.events.MarketplaceRequest.create_filter( + fromBlock=from_block, + toBlock=to_block, + ).get_all_entries() + + request_events = list( + { + "tx_hash": entry.transactionHash.hex(), + "block_number": entry.blockNumber, + **entry["args"], + "contract_address": contract_address, + } + for entry in entries + ) + return {"data": request_events} + + @classmethod + def get_deliver_events( + cls, + ledger_api: LedgerApi, + contract_address: str, + from_block: BlockIdentifier = "earliest", + to_block: BlockIdentifier = "latest", + ) -> JSONLike: + """Get the Deliver events emitted by the contract.""" + ledger_api = cast(EthereumApi, ledger_api) + contract_instance = cls.get_instance(ledger_api, contract_address) + entries = contract_instance.events.MarketplaceDeliver.create_filter( + fromBlock=from_block, + toBlock=to_block, + ).get_all_entries() + + request_events = list( + { + "tx_hash": entry.transactionHash.hex(), + "block_number": entry.blockNumber, + **entry["args"], + "contract_address": contract_address, + } + for entry in entries + ) + return {"data": request_events} + + @classmethod + def process_tx_receipt( + cls, + ledger_api: LedgerApi, + contract_address: str, + tx_receipt: TxReceipt, + ) -> JSONLike: + """Process transaction receipt to filter contract events.""" + + ledger_api = cast(EthereumApi, ledger_api) + contract_instance = cls.get_instance(ledger_api, contract_address) + event, *_ = contract_instance.events.Request().processReceipt(tx_receipt) + return dict(event["args"]) + + + @classmethod + def has_priority_passed( + cls, + ledger_api: LedgerApi, + contract_address: str, + request_ids: List[int], + ) -> Dict[str, Any]: + """Check the priority of the requests.""" + # BatchPriorityData contract is a special contract used specifically for checking if the requests have passed + # the priority timeout. It is not deployed anywhere, nor it needs to be deployed + batch_workable_contract = ledger_api.api.eth.contract( + abi=BATCH_PRIORITY_PASSED_DATA["abi"], bytecode=BATCH_PRIORITY_PASSED_DATA["bytecode"] + ) + + # Encode the input data (constructor params) + encoded_input_data = ledger_api.api.codec.encode_abi( + ["address", "address[]"], [contract_address, request_ids] + ) + + # Concatenate the bytecode with the encoded input data to create the contract creation code + contract_creation_code = batch_workable_contract.bytecode + encoded_input_data + + # Call the function with the contract creation code + # Note that we are not sending any transaction, we are just calling the function + # This is a special contract creation code that will return some result + encoded_strategies = ledger_api.api.eth.call({"data": contract_creation_code}) + + # Decode the raw response + # the decoding returns a Tuple with a single element so we need to access the first element of the tuple, + request_ids = ledger_api.api.codec.decode_abi( + ["uint256[]"], encoded_strategies + )[0] + return dict(request_ids=request_ids) + + + @classmethod + def get_undelivered_reqs( + cls, + ledger_api: LedgerApi, + contract_address: str, + from_block: BlockIdentifier = "earliest", + to_block: BlockIdentifier = "latest", + max_block_window: int = 1000, + **kwargs: Any, + ) -> JSONLike: + """Get the requests that are not delivered.""" + if from_block == "earliest": + from_block = 0 + + current_block = ledger_api.api.eth.block_number + requests, delivers = [], [] + for from_block_batch in range(int(from_block), current_block, max_block_window): + to_block_batch = (from_block_batch + max_block_window) - 1 + if to_block_batch >= current_block: + to_block_batch = "latest" + requests_batch: List[Dict[str, Any]] = cls.get_request_events( + ledger_api, contract_address, from_block_batch, to_block_batch + )["data"] + delivers_batch: List[Dict[str, Any]] = cls.get_deliver_events( + ledger_api, contract_address, from_block_batch, to_block_batch + )["data"] + requests.extend(requests_batch) + delivers.extend(delivers_batch) + pending_tasks: List[Dict[str, Any]] = [] + for request in requests: + if request["requestId"] not in [ + deliver["requestId"] for deliver in delivers + ]: + # store each requests in the pending_tasks list, make sure each req is stored once + pending_tasks.append(request) + + request_ids = [req["requestId"] for req in pending_tasks] + eligible_request_ids = cls.has_priority_passed(ledger_api, contract_address, request_ids).pop("request_ids") + pending_tasks = [req for req in pending_tasks if req["requestId"] in eligible_request_ids] + return {"data": pending_tasks} + + + @classmethod + def simulate_tx( + cls, + ledger_api: EthereumApi, + contract_address: str, + sender_address: str, + data: str, + ) -> JSONLike: + """Simulate the transaction.""" + try: + ledger_api.api.eth.call( + { + "from": ledger_api.api.to_checksum_address(sender_address), + "to": ledger_api.api.to_checksum_address(contract_address), + "data": data, + } + ) + simulation_ok = True + except Exception as e: + _logger.info(f"Simulation failed: {str(e)}") + simulation_ok = False + + return dict(data=simulation_ok) diff --git a/packages/valory/contracts/mech_marketplace/contract.yaml b/packages/valory/contracts/mech_marketplace/contract.yaml new file mode 100644 index 00000000..8c7895dc --- /dev/null +++ b/packages/valory/contracts/mech_marketplace/contract.yaml @@ -0,0 +1,22 @@ +name: mech_marketplace +author: valory +version: 0.1.0 +type: contract +description: Mech Marketplace contract for the AgentMech project. +license: Apache-2.0 +aea_version: '>=1.0.0, <2.0.0' +fingerprint: + BatchPriorityPassedCheck.sol: bafybeie3hfpyss43sggqh5rjzwsqe7o37td4v4k6f3hlweiosnayyseo4i + __init__.py: bafybeigqedpnruwcvjarngql7yfnpqwozvvgzcei2xcrp7mjf4ccspa62y + build/MechMarketplace.json: bafybeiavaelxgltfzquszveskzn732c47tbkyoqd6gwbk3by6ky2n73rcm + contract.py: bafybeibuyclvqogginsusuf5h77iuhwsyustys2thptwcdilu6lk5oo7iq +fingerprint_ignore_patterns: [] +class_name: MechMarketplaceContract +contract_interface_paths: + ethereum: build/MechMarketplace.json +dependencies: + open-aea-ledger-ethereum: + version: ==1.50.0 + web3: + version: <7,>=6.0.0 +contracts: [] diff --git a/packages/valory/services/mech/service.yaml b/packages/valory/services/mech/service.yaml index fef7ca63..fa4bbf2f 100644 --- a/packages/valory/services/mech/service.yaml +++ b/packages/valory/services/mech/service.yaml @@ -7,7 +7,7 @@ license: Apache-2.0 fingerprint: README.md: bafybeif7ia4jdlazy6745ke2k2x5yoqlwsgwr6sbztbgqtwvs3ndm2p7ba fingerprint_ignore_patterns: [] -agent: valory/mech:0.1.0:bafybeicbjm4qzztawekdr55gpbtntc6lu2sig6cfttss4zcu4tdnbypyhq +agent: valory/mech:0.1.0:bafybeib4ptljwzt34isrcmbkloexgp2wdmbrinl5a57xxvgjqub2ikhzvm number_of_agents: 4 deployment: agent: @@ -54,6 +54,7 @@ type: skill use_slashing: ${USE_SLASHING:bool:false} termination_from_block: ${TERMINATION_FROM_BLOCK:int:0} slash_cooldown_hours: ${SLASH_COOLDOWN_HOURS:int:3} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} slash_threshold_amount: ${SLASH_THRESHOLD_AMOUNT:int:10000000000000000} light_slash_unit_amount: ${LIGHT_SLASH_UNIT_AMOUNT:int:5000000000000000} serious_slash_unit_amount: ${SERIOUS_SLASH_UNIT_AMOUNT:int:8000000000000000} @@ -100,6 +101,7 @@ type: skill service_endpoint_base: ${SERVICE_ENDPOINT_BASE:str:https://dummy_service.autonolas.tech/} mech_to_subscription: ${MECH_TO_SUBSCRIPTION:list:[["0x77af31De935740567Cf4fF1986D04B2c964A786a",["0x0000000000000000000000000000000000000000","1"]]]} agent_funding_amount: ${AGENT_FUNDING_AMOUNT:int:200000000000000000} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} minimum_agent_balance: ${MINIMUM_AGENT_BALANCE:int:100000000000000000} 2: models: @@ -126,6 +128,7 @@ type: skill use_slashing: ${USE_SLASHING:bool:false} slash_cooldown_hours: ${SLASH_COOLDOWN_HOURS:int:3} slash_threshold_amount: ${SLASH_THRESHOLD_AMOUNT:int:10000000000000000} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} light_slash_unit_amount: ${LIGHT_SLASH_UNIT_AMOUNT:int:5000000000000000} serious_slash_unit_amount: ${SERIOUS_SLASH_UNIT_AMOUNT:int:8000000000000000} service_endpoint_base: ${SERVICE_ENDPOINT_BASE:str:https://dummy_service.autonolas.tech/} @@ -166,6 +169,7 @@ type: skill serious_slash_unit_amount: ${SERIOUS_SLASH_UNIT_AMOUNT:int:8000000000000000} agent_registry_address: ${AGENT_REGISTRY_ADDRESS:str:0xE49CB081e8d96920C38aA7AB90cb0294ab4Bc8EA} agent_id: ${AGENT_ID:int:3} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} metadata_hash: ${METADATA_HASH:str:f01701220caa53607238e340da63b296acab232c18a48e954f0af6ff2b835b2d93f1962f0} profit_split_freq: ${PROFIT_SPLIT_FREQ:int:100} hash_checkpoint_address: ${CHECKPOINT_ADDRESS:str:0x0000000000000000000000000000000000000000} @@ -187,8 +191,9 @@ type: skill polling_interval: ${POLLING_INTERVAL:float:30.0} agent_index: ${AGENT_INDEX_0:int:0} num_agents: ${NUM_AGENTS:int:4} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} timeout_limit: ${TIMEOUT_LIMIT:int:3} - mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"]]]} + mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]]]} max_block_window: ${MAX_BLOCK_WINDOW:int:500} 1: models: @@ -199,9 +204,10 @@ type: skill file_hash_to_tools_json: ${FILE_HASH_TO_TOOLS:list:[]} api_keys_json: ${API_KEYS:list:[]} polling_interval: ${POLLING_INTERVAL:float:30.0} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} agent_index: ${AGENT_INDEX_1:int:1} num_agents: ${NUM_AGENTS:int:4} - mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"]]]} + mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]]]} timeout_limit: ${TIMEOUT_LIMIT:int:3} max_block_window: ${MAX_BLOCK_WINDOW:int:500} 2: @@ -213,9 +219,10 @@ type: skill file_hash_to_tools_json: ${FILE_HASH_TO_TOOLS:list:[]} api_keys_json: ${API_KEYS:list:[]} polling_interval: ${POLLING_INTERVAL:float:30.0} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} agent_index: ${AGENT_INDEX_2:int:2} num_agents: ${NUM_AGENTS:int:4} - mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"]]]} + mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]]]} timeout_limit: ${TIMEOUT_LIMIT:int:3} max_block_window: ${MAX_BLOCK_WINDOW:int:500} 3: @@ -226,11 +233,12 @@ type: skill task_deadline: ${TASK_DEADLINE:float:240.0} file_hash_to_tools_json: ${FILE_HASH_TO_TOOLS:list:[]} api_keys_json: ${API_KEYS:list:[]} + mech_marketplace_address: ${MECH_MARKETPLACE_ADDRESS:str:0x0000000000000000000000000000000000000000} polling_interval: ${POLLING_INTERVAL:float:30.0} agent_index: ${AGENT_INDEX_3:int:3} num_agents: ${NUM_AGENTS:int:4} timeout_limit: ${TIMEOUT_LIMIT:int:3} - mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"]]]} + mech_to_config: ${MECH_TO_CONFIG:list:[["0xFf82123dFB52ab75C417195c5fDB87630145ae81",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]],["0x77af31De935740567Cf4fF1986D04B2c964A786a",["use_dynamic_pricing","false"],["is_mech_marketplace","false"]]]} max_block_window: ${MAX_BLOCK_WINDOW:int:500} --- public_id: valory/ledger:0.19.0 diff --git a/packages/valory/skills/mech_abci/skill.yaml b/packages/valory/skills/mech_abci/skill.yaml index 2ba6f0d9..3928a52c 100644 --- a/packages/valory/skills/mech_abci/skill.yaml +++ b/packages/valory/skills/mech_abci/skill.yaml @@ -23,7 +23,7 @@ skills: - valory/abstract_round_abci:0.1.0:bafybeih3enhagoql7kzpeyzzu2scpkif6y3ubakpralfnwxcvxexdyvy5i - valory/registration_abci:0.1.0:bafybeiek7zcsxbucjwzgqfftafhfrocvc7q4yxllh2q44jeemsjxg3rcfm - valory/reset_pause_abci:0.1.0:bafybeidw4mbx3os3hmv7ley7b3g3gja7ydpitr7mxbjpwzxin2mzyt5yam -- valory/task_submission_abci:0.1.0:bafybeihvvp6ovstb7po7kx6o7dno6kvjmffnmlerfw6qxhhzyrxmktd67e +- valory/task_submission_abci:0.1.0:bafybeifkd76popxwociq2ryojbcjyesmxoagqyjrbs73qoyd5o4szz6cgu - valory/termination_abci:0.1.0:bafybeihq6qtbwt6i53ayqym63vhjexkcppy26gguzhhjqywfmiuqghvv44 - valory/transaction_settlement_abci:0.1.0:bafybeigtzlk4uakmd54rxnznorcrstsr52kta474lgrnvx5ovr546vj7sq - valory/subscription_abci:0.1.0:bafybeihtortmv4fqua5wrnshpnvqsbpaf52frwynrmpuv2uw5j7wkauhze @@ -159,6 +159,8 @@ models: task_wait_timeout: 15.0 use_slashing: false manual_gas_limit: 1000000 + mech_staking_instance_address: '0x0000000000000000000000000000000000000000' + mech_marketplace_address: '0x0000000000000000000000000000000000000000' agent_registry_address: '0x0000000000000000000000000000000000000000' agent_id: 3 metadata_hash: '00000000000000000000000000000000000000000000000000' diff --git a/packages/valory/skills/task_execution/behaviours.py b/packages/valory/skills/task_execution/behaviours.py index edd3317a..a76524fe 100644 --- a/packages/valory/skills/task_execution/behaviours.py +++ b/packages/valory/skills/task_execution/behaviours.py @@ -42,6 +42,7 @@ PUBLIC_ID as P2P_CLIENT_PUBLIC_ID, ) from packages.valory.contracts.agent_mech.contract import AgentMechContract +from packages.valory.contracts.mech_marketplace.contract import MechMarketplaceContract from packages.valory.protocols.acn_data_share import AcnDataShareMessage from packages.valory.protocols.acn_data_share.dialogues import AcnDataShareDialogues from packages.valory.protocols.contract_api import ContractApiMessage @@ -223,6 +224,18 @@ def _check_for_new_reqs(self) -> None: # set the initial from block self._populate_from_block() return + self._check_undelivered_reqs() + self._check_undelivered_reqs_marketplace() + self.params.in_flight_req = True + self._last_polling = time.time() + + def _check_undelivered_reqs(self) -> None: + """Check for undelivered mech reqs.""" + target_mechs = [ + mech + for mech, config in self.params.mech_to_config.items() + if not config.is_marketplace_mech + ] contract_api_msg, _ = self.context.contract_dialogues.create( performative=ContractApiMessage.Performative.GET_STATE, contract_address=self.params.agent_mech_contract_addresses[0], @@ -232,7 +245,29 @@ def _check_for_new_reqs(self) -> None: dict( from_block=self.params.from_block, chain_id=GNOSIS_CHAIN, - contract_addresses=self.params.agent_mech_contract_addresses, + contract_addresses=target_mechs, + max_block_window=self.params.max_block_window, + ) + ), + counterparty=LEDGER_API_ADDRESS, + ledger_id=self.context.default_ledger_id, + ) + self.context.outbox.put_message(message=contract_api_msg) + + def _check_undelivered_reqs_marketplace(self) -> None: + """Check for undelivered mech reqs.""" + if not self.params.use_mech_marketplace: + return + contract_api_msg, _ = self.context.contract_dialogues.create( + performative=ContractApiMessage.Performative.GET_STATE, + contract_address=self.params.mech_marketplace_address, + contract_id=str(MechMarketplaceContract.contract_id), + callable="get_undelivered_reqs", + kwargs=ContractApiMessage.Kwargs( + dict( + from_block=self.params.from_block, + my_mech=self._get_designated_marketplace_mech_address(), + chain_id=GNOSIS_CHAIN, max_block_window=self.params.max_block_window, ) ), @@ -240,8 +275,6 @@ def _check_for_new_reqs(self) -> None: ledger_id=self.context.default_ledger_id, ) self.context.outbox.put_message(message=contract_api_msg) - self.params.in_flight_req = True - self._last_polling = time.time() def _execute_task(self) -> None: """Execute tasks.""" @@ -281,12 +314,23 @@ def send_message( self.params.req_to_callback[nonce] = callback self.params.in_flight_req = True + def _get_designated_marketplace_mech_address(self) -> str: + """Get the designated mech address.""" + for mech, config in self.params.mech_to_config.items(): + if config.is_marketplace_mech: + return mech + + raise ValueError("No marketplace mech address found") + def _handle_done_task(self, task_result: Any) -> None: """Handle done tasks""" executing_task = cast(Dict[str, Any], self._executing_task) req_id = executing_task.get("requestId", None) request_id_nonce = executing_task.get("requestIdWithNonce", None) - mech_address = executing_task.get("contract_address", None) + mech_address = ( + executing_task.get("contract_address", None) + or self._get_designated_marketplace_mech_address() + ) tool = executing_task.get("tool", None) model = executing_task.get("model", None) tool_params = executing_task.get("params", None) @@ -504,6 +548,7 @@ def _handle_store_response(self, message: IpfsMessage, dialogue: Dialogue) -> No ["uint256", "bytes"], [cost, bytes.fromhex(task_result)] ).hex() + done_task["is_marketplace_mech"] = mech_config.is_marketplace_mech done_task["task_result"] = task_result # add to done tasks, in thread safe way with self.done_tasks_lock: diff --git a/packages/valory/skills/task_execution/models.py b/packages/valory/skills/task_execution/models.py index d2bf7a3d..7083f550 100644 --- a/packages/valory/skills/task_execution/models.py +++ b/packages/valory/skills/task_execution/models.py @@ -26,17 +26,22 @@ from aea.skills.base import Model +ZERO_ADDRESS = "0x0000000000000000000000000000000000000000" + + @dataclasses.dataclass class MechConfig: """Mech config dataclass.""" use_dynamic_pricing: bool + is_marketplace_mech: bool @staticmethod def from_dict(raw_dict: Dict[str, Any]) -> "MechConfig": """From dict.""" return MechConfig( - use_dynamic_pricing=raw_dict["use_dynamic_pricing"].lower() == "true" + use_dynamic_pricing=raw_dict["use_dynamic_pricing"].lower() == "true", + is_marketplace_mech=raw_dict["is_marketplace_mech"].lower() == "true", ) @@ -82,6 +87,13 @@ def __init__(self, *args: Any, **kwargs: Any) -> None: # maps the request id to the number of times it has timed out self.request_id_to_num_timeouts: Dict[int, int] = defaultdict(lambda: 0) self.mech_to_config: Dict[str, MechConfig] = self._parse_mech_configs(kwargs) + self.mech_marketplace_address: Optional[str] = kwargs.get( + "mech_marketplace_address", None + ) + self.use_mech_marketplace = ( + self.mech_marketplace_address is not None + and self.mech_marketplace_address != ZERO_ADDRESS + ) super().__init__(*args, **kwargs) def _nested_list_todict_workaround( @@ -97,11 +109,12 @@ def _nested_list_todict_workaround( def _parse_mech_configs(self, kwargs: Dict) -> Dict[str, MechConfig]: """Parse the mech configs.""" - mech_configs_json = self._nested_list_todict_workaround( - kwargs, "mech_to_config" - ) + key = "mech_to_config" + values = cast(List, kwargs.get(key)) + mech_configs_json = {value[0]: value[1:] for value in values} mech_configs_json = { - key: {value[0]: value[1]} for key, value in mech_configs_json.items() + key: {value[0]: value[1] for value in values} + for key, values in mech_configs_json.items() } mech_configs = { diff --git a/packages/valory/skills/task_execution/skill.yaml b/packages/valory/skills/task_execution/skill.yaml index 712f969f..8e9412be 100644 --- a/packages/valory/skills/task_execution/skill.yaml +++ b/packages/valory/skills/task_execution/skill.yaml @@ -7,10 +7,10 @@ license: Apache-2.0 aea_version: '>=1.0.0, <2.0.0' fingerprint: __init__.py: bafybeidqhvvlnthkbnmrdkdeyjyx2f2ab6z4xdgmagh7welqnh2v6wczx4 - behaviours.py: bafybeic6srotpryrn3s2kzxzvq6vrstpw6bh3qbqcvgv5dryihsffcio4u + behaviours.py: bafybeieqfperjuyytzuqeur4tsurkhk6z44kd3ncn53rljtgfffttpjkim dialogues.py: bafybeid4zxalqdlo5mw4yfbuf34hx4jp5ay5z6chm4zviwu4cj7fudtwca handlers.py: bafybeidbt5ezj74cgfogk3w4uw4si2grlnk5g54veyumw7g5yh6gdscywu - models.py: bafybeid6befxrrbiaw7nduz4zgbm5nfc246fn2eb6rfmja6v5hmq4wtcwe + models.py: bafybeihnwrb6l7fe5ewt3zokxl7rn6ijtzu3z7lgpam2cz4v5cwj4ewvyu utils/__init__.py: bafybeiccdijaigu6e5p2iruwo5mkk224o7ywedc7nr6xeu5fpmhjqgk24e utils/apis.py: bafybeigu73lfz3g3mc6iupisrvlsp3fyl4du3oqlyajgdpfvtqypddh3w4 utils/benchmarks.py: bafybeiafnee7iay6dyjnatyqyzjov5c4ibl3ojamjmgfjri7cyghl7qayq @@ -24,6 +24,7 @@ connections: - valory/p2p_libp2p_client:0.1.0:bafybeid3xg5k2ol5adflqloy75ibgljmol6xsvzvezebsg7oudxeeolz7e contracts: - valory/agent_mech:0.1.0:bafybeiah6b5epo2hlvzg5rr2cydgpp2waausoyrpnoarf7oa7bw33rex34 +- valory/mech_marketplace:0.1.0:bafybeich3a3oh5w4u533w6y7ideojudqp2m5gxta7pqmsfiaohdhuw7yz4 protocols: - valory/acn_data_share:0.1.0:bafybeih5ydonnvrwvy2ygfqgfabkr47s4yw3uqxztmwyfprulwfsoe7ipq - valory/contract_api:1.0.0:bafybeidgu7o5llh26xp3u3ebq3yluull5lupiyeu6iooi2xyymdrgnzq5i @@ -92,6 +93,8 @@ models: - - '0x9A676e781A523b5d0C0e43731313A708CB607508' - - - use_dynamic_pricing - 'false' + - - is_marketplace_mech + - 'false' polling_interval: 30.0 task_deadline: 240.0 max_block_window: 500 @@ -101,6 +104,7 @@ models: slash_threshold_amount: 10000000000000000 light_slash_unit_amount: 5000000000000000 serious_slash_unit_amount: 8000000000000000 + mech_marketplace_address: '0x0000000000000000000000000000000000000000' class_name: Params dependencies: beautifulsoup4: diff --git a/packages/valory/skills/task_submission_abci/behaviours.py b/packages/valory/skills/task_submission_abci/behaviours.py index 31447c99..cace258f 100644 --- a/packages/valory/skills/task_submission_abci/behaviours.py +++ b/packages/valory/skills/task_submission_abci/behaviours.py @@ -40,6 +40,7 @@ SafeOperation, ) from packages.valory.contracts.hash_checkpoint.contract import HashCheckpointContract +from packages.valory.contracts.mech_marketplace.contract import MechMarketplaceContract from packages.valory.contracts.multisend.contract import ( MultiSendContract, MultiSendOperation, @@ -889,10 +890,11 @@ def _get_safe_tx_hash(self, data: bytes) -> Generator[None, None, Optional[str]] tx_hash = cast(str, response.state.body["tx_hash"])[2:] return tx_hash - def _get_deliver_tx( - self, task_data: Dict[str, Any] + def _get_agent_mech_deliver_tx( + self, + task_data: Dict[str, Any], ) -> Generator[None, None, Optional[Dict]]: - """Get the deliver tx.""" + """Get the deliver tx for the mech delivery.""" contract_api_msg = yield from self.get_contract_api_response( performative=ContractApiMessage.Performative.GET_STATE, # type: ignore contract_address=task_data["mech_address"], @@ -920,6 +922,74 @@ def _get_deliver_tx( "simulation_ok": simulation_ok, } + def _get_deliver_marketplace_tx( + self, + task_data: Dict[str, Any], + ) -> Generator[None, None, Optional[Dict]]: + """Get the deliver tx for the marketplace delivery.""" + contract_api_msg = yield from self.get_contract_api_response( + performative=ContractApiMessage.Performative.GET_STATE, # type: ignore + contract_address=self.params.mech_marketplace_address, + contract_id=str(MechMarketplaceContract.contract_id), + contract_callable="get_deliver_data", + sender_address=task_data["mech_address"], + request_id=task_data["request_id"], + data=task_data["task_result"], + delivery_mech_staking_instance=self.params.mech_staking_instance_address, + delivery_mech_service_id=self.params.on_chain_service_id, + ) + if ( + contract_api_msg.performative != ContractApiMessage.Performative.STATE + ): # pragma: nocover + self.context.logger.warning( + f"get_deliver_data unsuccessful!: {contract_api_msg}" + ) + return None + + data = cast(bytes, contract_api_msg.state.body["data"]) + simulation_ok = cast(bool, contract_api_msg.state.body["simulation_ok"]) + + contract_api_msg = yield from self.get_contract_api_response( + performative=ContractApiMessage.Performative.GET_STATE, # type: ignore + contract_address=task_data["mech_address"], + contract_id=str(AgentMechContract.contract_id), + contract_callable="get_exec_tx_data", + to=self.params.mech_marketplace_address, + value=ZERO_ETHER_VALUE, + data=data, + tx_gas=AUTO_GAS, + operation=MechOperation.CALL.value, + ) + if ( + contract_api_msg.performative != ContractApiMessage.Performative.STATE + ): # pragma: nocover + self.context.logger.warning( + f"get_deliver_data unsuccessful!: {contract_api_msg}" + ) + return None + + data = cast(bytes, contract_api_msg.state.body["data"]) + return { + "to": task_data["mech_address"], + "value": ZERO_ETHER_VALUE, + "data": data, + "simulation_ok": simulation_ok, + } + + def _get_deliver_tx( + self, task_data: Dict[str, Any] + ) -> Generator[None, None, Optional[Dict]]: + """Get the deliver tx.""" + is_marketplace_mech = task_data.get("is_marketplace_mech", False) + request_id = task_data["request_id"] + if is_marketplace_mech: + self.context.logger.info( + f"Delivering reqId {request_id} to marketplace mech contract." + ) + return self._get_deliver_marketplace_tx(task_data) + + return self._get_agent_mech_deliver_tx(task_data) + class TaskSubmissionRoundBehaviour(AbstractRoundBehaviour): """TaskSubmissionRoundBehaviour""" diff --git a/packages/valory/skills/task_submission_abci/models.py b/packages/valory/skills/task_submission_abci/models.py index 3c0d1ef8..7958ffee 100644 --- a/packages/valory/skills/task_submission_abci/models.py +++ b/packages/valory/skills/task_submission_abci/models.py @@ -74,6 +74,16 @@ def __init__(self, *args: Any, **kwargs: Any) -> None: self.hash_checkpoint_address = self._ensure( "hash_checkpoint_address", kwargs, str ) + self.mech_marketplace_address = self._ensure( + "mech_marketplace_address", + kwargs, + str, + ) + self.mech_staking_instance_address = self._ensure( + "mech_staking_instance_address", + kwargs, + str, + ) self.minimum_agent_balance = self._ensure("minimum_agent_balance", kwargs, int) self.agent_funding_amount = self._ensure("agent_funding_amount", kwargs, int) super().__init__(*args, **kwargs) diff --git a/packages/valory/skills/task_submission_abci/skill.yaml b/packages/valory/skills/task_submission_abci/skill.yaml index f0cf59a0..15965371 100644 --- a/packages/valory/skills/task_submission_abci/skill.yaml +++ b/packages/valory/skills/task_submission_abci/skill.yaml @@ -8,11 +8,11 @@ license: Apache-2.0 aea_version: '>=1.0.0, <2.0.0' fingerprint: __init__.py: bafybeiholqak7ltw6bbmn2c5tn3j7xgzkdlfzp3kcskiqsvmxoih6m4muq - behaviours.py: bafybeibzrspy5pkv2sxeqob4fdakf4olahsgp33afwp65svshmli6d5bbq + behaviours.py: bafybeifgon5yuonrcpbwslwxbpd3cttqyj42llgpcwioyfmtx3uoxh7dnm dialogues.py: bafybeibmac3m5u5h6ucoyjr4dazay72dyga656wvjl6z6saapluvjo54ne fsm_specification.yaml: bafybeidtmsmpunr3t77pshd3k2s6dd6hlvhze6inu3gj7xyvlg4wi3tnuu handlers.py: bafybeibe5n7my2vd2wlwo73sbma65epjqc7kxgtittewlylcmvnmoxtxzq - models.py: bafybeigmraodqqx33mlflscp27tkngjkmtk6j7askmwe4ynhinimtcomuq + models.py: bafybeifkca4krpykazv4tar4nfgaefwplpcia34zrdlvkiijf5anrxzcmu payloads.py: bafybeia2yorri2u5rwh6vukb6iwdrbn53ygsuuhthns2txptvjipyb6f4e rounds.py: bafybeiazzauhh5ddr6fkqckv7tiu7nek6k7deoaihwyspeywlrq46uemou tasks.py: bafybeicu5t5cvfhbndgpxbbtmp4vbmtyb6fba6vsnlewftvuderxp5lwcy @@ -25,6 +25,7 @@ contracts: - valory/multisend:0.1.0:bafybeig5byt5urg2d2bsecufxe5ql7f4mezg3mekfleeh32nmuusx66p4y - valory/service_registry:0.1.0:bafybeicbxmbzt757lbmyh6762lrkcrp3oeum6dk3z7pvosixasifsk6xlm - valory/hash_checkpoint:0.1.0:bafybeicbycr6rxods7sg3f2qlhgkjqrbh7kymmy2yw7bewxdwjyp7ibtg4 +- valory/mech_marketplace:0.1.0:bafybeich3a3oh5w4u533w6y7ideojudqp2m5gxta7pqmsfiaohdhuw7yz4 protocols: - valory/acn_data_share:0.1.0:bafybeih5ydonnvrwvy2ygfqgfabkr47s4yw3uqxztmwyfprulwfsoe7ipq - valory/contract_api:1.0.0:bafybeidgu7o5llh26xp3u3ebq3yluull5lupiyeu6iooi2xyymdrgnzq5i @@ -139,6 +140,8 @@ models: tendermint_max_retries: 5 tendermint_p2p_url: localhost:26656 tendermint_url: http://localhost:26657 + mech_staking_instance_address: '0x0000000000000000000000000000000000000000' + mech_marketplace_address: '0x0000000000000000000000000000000000000000' tx_timeout: 10.0 use_termination: false validate_timeout: 1205