Skip to content

Commit

Permalink
feat: Getter functions of SDK (#833)
Browse files Browse the repository at this point in the history
* add data model for statistics data

* add getter function for escrow and statistics

* update gql queries for typescript and python sdk

* fix storage client related issues
  • Loading branch information
leric7 authored Aug 30, 2023
1 parent d90724c commit 8e27a4b
Show file tree
Hide file tree
Showing 32 changed files with 1,948 additions and 285 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -66,8 +66,8 @@ export class WebhookService {
this.bucket = this.configService.get<string>(ConfigNames.S3_BUCKET)!;

this.storageClient = new StorageClient(
storageCredentials,
this.storageParams,
storageCredentials,
);
}

Expand Down
3 changes: 3 additions & 0 deletions packages/sdk/python/human-protocol-sdk/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -38,3 +38,6 @@ build-package:
publish-package:
make build-package
twine upload dist/* --skip-existing

run-example:
pipenv run python3 example.py
64 changes: 64 additions & 0 deletions packages/sdk/python/human-protocol-sdk/example.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
import datetime
from web3 import Web3

from human_protocol_sdk.escrow import EscrowClient, EscrowFilter, Status
from human_protocol_sdk.statistics import StatisticsClient, StatisticsParam

if __name__ == "__main__":
alchemy_url = (
"https://polygon-mumbai.g.alchemy.com/v2/lnog1fIT7pvL4_o3lkcosQ7PL08ed3nX"
)
w3 = Web3(Web3.HTTPProvider(alchemy_url))

escrow_client = EscrowClient(w3)

print(
escrow_client.get_escrows(
EscrowFilter(
status=Status.Pending,
date_from=datetime.datetime(2023, 5, 8),
date_to=datetime.datetime(2023, 6, 8),
)
)
)

statistics_client = StatisticsClient(w3)

print(statistics_client.get_escrow_statistics())
print(
statistics_client.get_escrow_statistics(
StatisticsParam(
date_from=datetime.datetime(2023, 5, 8),
date_to=datetime.datetime(2023, 6, 8),
)
)
)

print(statistics_client.get_worker_statistics())
print(
statistics_client.get_worker_statistics(
StatisticsParam(
date_from=datetime.datetime(2023, 5, 8),
date_to=datetime.datetime(2023, 6, 8),
)
)
)

print(statistics_client.get_payment_statistics())
print(
statistics_client.get_payment_statistics(
StatisticsParam(
date_from=datetime.datetime(2023, 5, 8),
date_to=datetime.datetime(2023, 6, 8),
)
)
)
print(statistics_client.get_hmt_statistics())
print(
statistics_client.get_hmt_statistics(
StatisticsParam(
date_from=datetime.datetime(2023, 5, 8),
date_to=datetime.datetime(2023, 6, 8),
)
)
)
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ class ChainId(Enum):
ChainId.MAINNET: {
"title": "Ethereum",
"scan_url": "https://etherscan.io",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/mainnet-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/mainnet-v2",
"hmt_address": "0xd1ba9BAC957322D6e8c07a160a3A8dA11A0d2867",
"factory_address": "0xD9c75a1Aa4237BB72a41E5E26bd8384f10c1f55a",
"staking_address": "0x05398211bA2046E296fBc9a9D3EB49e3F15C3123",
Expand All @@ -36,7 +36,7 @@ class ChainId(Enum):
ChainId.GOERLI: {
"title": "Ethereum Goerli",
"scan_url": "https://goerli.etherscan.io",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/goerli-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/goerli-v2",
"hmt_address": "0xd3A31D57FDD790725d0F6B78095F62E8CD4ab317",
"factory_address": "0x87469B4f2Fcf37cBd34E54244c0BD4Fa0603664c",
"staking_address": "0xf46B45Df3d956369726d8Bd93Ba33963Ab692920",
Expand All @@ -48,7 +48,7 @@ class ChainId(Enum):
ChainId.BSC_MAINNET: {
"title": "Binance Smart Chain",
"scan_url": "https://bscscan.com",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/bsc-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/bsc-v2",
"hmt_address": "0x711Fd6ab6d65A98904522d4e3586F492B989c527",
"factory_address": "0x92FD968AcBd521c232f5fB8c33b342923cC72714",
"staking_address": "0xdFbB79dC35a3A53741be54a2C9b587d6BafAbd1C",
Expand All @@ -60,7 +60,7 @@ class ChainId(Enum):
ChainId.BSC_TESTNET: {
"title": "Binance Smart Chain (Testnet)",
"scan_url": "https://testnet.bscscan.com",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/bsctest-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/bsctest-v2",
"hmt_address": "0xE3D74BBFa45B4bCa69FF28891fBE392f4B4d4e4d",
"factory_address": "0x2bfA592DBDaF434DDcbb893B1916120d181DAD18",
"staking_address": "0x5517fE916Fe9F8dB15B0DDc76ebDf0BdDCd4ed18",
Expand All @@ -72,7 +72,7 @@ class ChainId(Enum):
ChainId.POLYGON: {
"title": "Polygon",
"scan_url": "https://polygonscan.com",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/polygon-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/polygon-v2",
"hmt_address": "0xc748B2A084F8eFc47E086ccdDD9b7e67aEb571BF",
"factory_address": "0xBDBfD2cC708199C5640C6ECdf3B0F4A4C67AdfcB",
"staking_address": "0xcbAd56bE3f504E98bd70875823d3CC0242B7bB29",
Expand All @@ -84,7 +84,7 @@ class ChainId(Enum):
ChainId.POLYGON_MUMBAI: {
"title": "Polygon Mumbai",
"scan_url": "https://mumbai.polygonscan.com",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/mumbai-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/mumbai-v2",
"hmt_address": "0x0376D26246Eb35FF4F9924cF13E6C05fd0bD7Fb4",
"factory_address": "0xA8D927C4DA17A6b71675d2D49dFda4E9eBE58f2d",
"staking_address": "0x7Fd3dF914E7b6Bd96B4c744Df32183b51368Bfac",
Expand All @@ -96,7 +96,7 @@ class ChainId(Enum):
ChainId.MOONBEAM: {
"title": "Moonbeam",
"scan_url": "https://moonbeam.moonscan.io",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/moonbeam-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/moonbeam-v2",
"hmt_address": "0x3b25BC1dC591D24d60560d0135D6750A561D4764",
"factory_address": "0xD9c75a1Aa4237BB72a41E5E26bd8384f10c1f55a",
"staking_address": "0x05398211bA2046E296fBc9a9D3EB49e3F15C3123",
Expand All @@ -108,7 +108,7 @@ class ChainId(Enum):
ChainId.MOONBASE_ALPHA: {
"title": "Moonbase Alpha",
"scan_url": "https://moonbase.moonscan.io/",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/moonbase-alpha-v1",
"subgraph_url": "https://api.thegraph.com/subgraphs/name/humanprotocol/moonbase-alpha-v2",
"hmt_address": "0x2dd72db2bBA65cE663e476bA8b84A1aAF802A8e3",
"factory_address": "0x5e622FF522D81aa426f082bDD95210BC25fCA7Ed",
"staking_address": "0xBFC7009F3371F93F3B54DdC8caCd02914a37495c",
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,6 @@
from typing import Optional, List
from pgpy import PGPKey, PGPMessage, PGPUID
from pgpy.constants import (
SymmetricKeyAlgorithm,
HashAlgorithm,
KeyFlags,
PubKeyAlgorithm,
)
from pgpy import PGPKey, PGPMessage
from pgpy.constants import SymmetricKeyAlgorithm
from pgpy.errors import PGPError


Expand Down
76 changes: 36 additions & 40 deletions packages/sdk/python/human-protocol-sdk/human_protocol_sdk/escrow.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,6 @@
from typing import List, Optional

from human_protocol_sdk.constants import NETWORKS, ChainId, Role, Status
from human_protocol_sdk.gql.escrow import (
get_escrows_by_launcher_query,
get_filtered_escrows_query,
)
from human_protocol_sdk.utils import (
get_data_from_subgraph,
get_escrow_interface,
Expand Down Expand Up @@ -96,7 +92,9 @@ class EscrowFilter:

def __init__(
self,
launcher_address: Optional[str] = None,
launcher: Optional[str] = None,
reputation_oracle: Optional[str] = None,
recording_oracle: Optional[str] = None,
status: Optional[Status] = None,
date_from: Optional[datetime.datetime] = None,
date_to: Optional[datetime.datetime] = None,
Expand All @@ -105,23 +103,30 @@ def __init__(
Initializes a EscrowFilter instance.
Args:
launcher_address (Optional[str]): Launcher ddress
launcher (Optional[str]): Launcher address
reputation_oracle (Optional[str]): Reputation oracle address
recording_oracle (Optional[str]): Recording oracle address
status (Optional[Status]): Escrow status
date_from (Optional[date]): Created from date
date_to (Optional[date]): Created to date
date_from (Optional[datetime.datetime]): Created from date
date_to (Optional[datetime.datetime]): Created to date
"""
if not launcher_address and not status and not date_from and not date_to:
raise EscrowClientError(
"EscrowFilter class must have at least one parameter"
)
if launcher_address and not Web3.is_address(launcher_address):
raise EscrowClientError(f"Invalid address: {launcher_address}")
if launcher and not Web3.is_address(launcher):
raise EscrowClientError(f"Invalid address: {launcher}")

if reputation_oracle and not Web3.is_address(reputation_oracle):
raise EscrowClientError(f"Invalid address: {reputation_oracle}")

if recording_oracle and not Web3.is_address(recording_oracle):
raise EscrowClientError(f"Invalid address: {recording_oracle}")

if date_from and date_to and date_from > date_to:
raise EscrowClientError(
f"Invalid dates: {date_from} must be earlier than {date_to}"
)

self.launcher_address = launcher_address
self.launcher = launcher
self.reputation_oracle = reputation_oracle
self.recording_oracle = recording_oracle
self.status = status
self.date_from = date_from
self.date_to = date_to
Expand All @@ -145,12 +150,16 @@ def __init__(self, web3: Web3):
if not self.w3.middleware_onion.get("geth_poa"):
self.w3.middleware_onion.inject(geth_poa_middleware, "geth_poa", layer=0)

chain_id = None
# Load network configuration based on chainId
try:
chain_id = self.w3.eth.chain_id
self.network = NETWORKS[ChainId(chain_id)]
except:
raise EscrowClientError(f"Invalid ChainId: {chain_id}")
if chain_id is not None:
raise EscrowClientError(f"Invalid ChainId: {chain_id}")
else:
raise EscrowClientError(f"Invalid Web3 Instance")

# Initialize contract instances
factory_interface = get_factory_interface()
Expand Down Expand Up @@ -589,26 +598,7 @@ def get_status(self, escrow_address: str) -> Status:
self._get_escrow_contract(escrow_address).functions.status().call()
)

def get_launched_escrows(self, launcher_address: str) -> List[dict]:
"""Get escrows addresses created by a job launcher.
Args:
launcher_address (str): Address of the launcher
Returns:
List[dict]: List of escrows
"""

escrows_data = get_data_from_subgraph(
self.network["subgraph_url"],
query=get_escrows_by_launcher_query,
params={"launcherAddress": launcher_address},
)
escrows = escrows_data["data"]["escrows"]

return escrows

def get_escrows_filtered(self, filter: EscrowFilter) -> List[dict]:
def get_escrows(self, filter: EscrowFilter = EscrowFilter()) -> List[dict]:
"""Get an array of escrow addresses based on the specified filter parameters.
Args:
Expand All @@ -617,19 +607,25 @@ def get_escrows_filtered(self, filter: EscrowFilter) -> List[dict]:
Returns:
List[dict]: List of escrows
"""
from human_protocol_sdk.gql.escrow import (
get_escrows_query,
)

escrows_data = get_data_from_subgraph(
self.network["subgraph_url"],
query=get_filtered_escrows_query,
query=get_escrows_query(filter),
params={
"launcherAddress": filter.launcher_address,
"launcher": filter.launcher,
"reputationOracle": filter.reputation_oracle,
"recordingOracle": filter.recording_oracle,
"status": filter.status.name if filter.status else None,
"from": int(filter.date_from.timestamp()) if filter.date_from else None,
"to": int(filter.date_to.timestamp()) if filter.date_to else None,
},
)
launched_escrows = escrows_data["data"]["escrows"]
escrows = escrows_data["data"]["escrows"]

return launched_escrows
return escrows

def get_recording_oracle_address(self, escrow_address: str) -> str:
"""Gets the recording oracle address of the escrow.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
from human_protocol_sdk.escrow import EscrowFilter

escrow_fragment = """
fragment EscrowFields on Escrow {{
fragment EscrowFields on Escrow {
address
amountPaid
balance
Expand All @@ -18,39 +20,45 @@
status
token
totalFundedAmount
}}
createdAt
}
"""

get_escrows_by_launcher_query = """
query GetEscrowByLauncher($launcherAddress: String!) {{
escrows(where: {{ launcher: $launcherAddress }}) {{
...EscrowFields
}}
}}
{escrow_fragment}
""".format(
escrow_fragment=escrow_fragment
)

get_filtered_escrows_query = """
query GetFilteredEscrows(
$launcherAddress: String
$status: EscrowStatus
def get_escrows_query(filter: EscrowFilter):
return """
query GetEscrows(
$launcher: String
$reputationOracle: String
$recordingOracle: String
$status: String
$from: Int
$to: Int
) {{
escrows(
where: {{
launcher: $launcherAddress
status: $status
createdAt_gte: $from
createdAt_lte: $to
}}
where: {{
{launcher_clause}
{reputation_oracle_clause}
{recording_oracle_clause}
{status_clause}
{from_clause}
{to_clause}
}}
) {{
...EscrowFields
...EscrowFields
}}
}}
{escrow_fragment}
""".format(
escrow_fragment=escrow_fragment
)
escrow_fragment=escrow_fragment,
launcher_clause="launcher: $launcher" if filter.launcher else "",
reputation_oracle_clause="reputationOracle: $reputationOracle"
if filter.reputation_oracle
else "",
recording_oracle_clause="recordingOracle: $recordingOracle"
if filter.recording_oracle
else "",
status_clause="status: $status" if filter.status else "",
from_clause="createdAt_gte: $from" if filter.date_from else "",
to_clause="createdAt_lte: $to" if filter.date_from else "",
)
Loading

1 comment on commit 8e27a4b

@vercel
Copy link

@vercel vercel bot commented on 8e27a4b Aug 30, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Successfully deployed to the following URLs:

job-launcher-server – ./packages/apps/job-launcher/server

job-launcher-server-nine.vercel.app
job-launcher-server-humanprotocol.vercel.app
job-launcher-server-git-develop-humanprotocol.vercel.app

Please sign in to comment.