Pomelo has concluded its journey. Together with the web3 community, we raised over $3 million to fund public goods and facilitated approximately 30,000 donations to 652 projects. We are grateful to have served the builders who created grants and brought their visions to life. Through quadratic funding, your support made a meaningful difference, helping matching partners meet the needs of their communities.
Next Steps: Build with Pinax
Pomelo users can start building with a FREE Pinax Pro Plan. Pinax provides comprehensive blockchain data services for dozens of chains, including EOS, WAX, and Telos. We encourage you to continue your journey by leveraging Pinax's advanced tools and services at https://pinax.network.
id | chain |
---|---|
eos |
EOS Native |
eos.evm |
EOS EVM |
- N/A
# create bounty
cleos push action work.pomelo create '[author.eosn, bounty1, "USDT", null]' -p author.eosn
# fund bounty
cleos transfer myaccount work.pomelo "100.0000 USDT" "bounty1,funder.eosn" --contract tethertether
# author select hunter for bounty
cleos push action work.pomelo approve '[bounty1, hunter.eosn]' -p author.eosn
# author closes unsuccessful open/pending bounty putting it into "closed" state
cleos push action work.pomelo close '[bounty1]' -p author.eosn
# OPTION 1. Author releases funds to hunter when bounty is completed
# > Bounty state must be "completed"
cleos push action work.pomelo release '[bounty1]' -p author.eosn
# OPTION 2. Author denies completed bounty
# > Bounty state is reverted back to "progress"
cleos push action work.pomelo deny '[bounty1]' -p author.eosn
# OPTION 3. funds auto-released to hunter after 72 hours
# /* no action */
# before applying, hunter must link their EOS account with EOSN login
cleos push action login.eosn link '["hunter.eosn", "myaccount", "SIG_K1_KjnbJ2m22HtuRW7u7ZLdoCx76aNMiADHJpATGh32uYeJLdSjhdpHA7tmd4pj1Ni3mSr5DPRHHaydpaggrb5RcBg2HDDn7G"]' -p myaccount
# hunter apply to bounty
cleos push action work.pomelo apply '[bounty1, hunter.eosn]' -p hunter.eosn
# hunter forfeits bounty
cleos push action work.pomelo forfeit '[bounty1]' -p hunter.eosn
# hunter signals work is completed (funds are auto-released after 72 hours if no explicit approval from author)
cleos push action work.pomelo complete '[bounty1]' -p hunter.eosn
# hunter claims bounty funds (EOS account linked with EOSN Login)
cleos push action work.pomelo claim '[bounty1]' -p myaccount
# configure app
cleos push action work.pomelo setconfig '[ok, 1000, login.eosn, fee.pomelo, [url]]' -p work.pomelo
cleos push action work.pomelo token '["4,USDT", tethertether, 10000, 0]' -p work.pomelo
# disable contract
cleos push action work.pomelo setconfig '[disabled, null, null, null, []]' -p work.pomelo
# make bounty public
cleos push action work.pomelo publish '[bounty1]' -p work.pomelo
# set bounty state
cleos push action work.pomelo setstate '[bounty1, pending]' -p work.pomelo
# sync bounty details
cleos push action work.pomelo syncbounty '[bounty1, started, [applicant1.eosn, applicant2.eosn], applicant2.eosn, 2021-01-01T00:00:00, null, null]' -p work.pomelo
# close bounty
cleos push action work.pomelo close '[bounty1]' -p work.pomelo
# set bounty metadata
cleos push action work.pomelo setmetadata '[bounty1, url, "https://github.com/pomelo-io/"]' -p author.eosn
# author withdraws funds bounty in "pending" state (EOS account `myaccount` should be linked to `author.eosn` EOSN Login)
cleos push action work.pomelo withdraw '[bounty1]' -p myaccount
# build contract
$ ./scripts/build.sh
# restart node, create EOSIO users, deploy contracts, issue tokens
$ ./scripts/restart
# run tests
$ ./test.sh
role |
description |
---|---|
Admin | Pomelo Admin |
Author | Bounty Author |
Hunter | Bounty Hunter |
Funder | Bounty Funder |
SC | Smart Contract |
- ACTION
setconfig
- ACTION
token
- ACTION
deltoken
- ACTION
create
- ACTION
setmetadata
- ACTION
setstate
- ACTION
syncbounty
- ACTION
publish
- ACTION
withdraw
- ACTION
apply
- ACTION
approve
- ACTION
release
- ACTION
deny
- ACTION
complete
- ACTION
forfeit
- ACTION
claim
- ACTION
close
scope: {name} bount_id
{uint64_t} id
- (primary key) deposit ID{name} from
- sender account (EOSN Login ID or EOS account){asset} quantity
- token quantity{time_point_sec} timestamp
- timestamp{checksum256} trx_id
- transaction ID
{
"id": 1,
"from": "1111234.eosn",
"quantity": "5.0000 USDT",
"timestamp": "2023-12-01T00:00:00",
"trx_id": "33916e02c5fdc40c7c7d08598a606e51bcd93fc0003316fd85a335eedf58d26b"
}
{name} status
- contract status ("ok", "testing", "maintenance"){uint64_t} fee
- platform fee (bips - 1/100 1%){name} login_contract
- EOSN Login contract{name} fee_account
- fee{set<name>} metadata_keys
- list of keys allowed to include in bounty Metadata
{
"status": "ok",
"fee": 500,
"login_contract": "login.eosn",
"fee_account": "fee.pomelo",
"metadata_keys": ["url"]
}
{symbol} sym
- (primary key) symbol{name} contract
- token contract{uint64_t} min_amount
- min amount required per bounty{uint64_t} max_amount
- max amount required per bounty
{
"sym": "4,USDT",
"contract": "tethertether",
"min_amount": 50000,
"max_amount": 5000000
}
scope: {name} get_self()
{name} bount_id
- (primary key) bounty ID (ex: "bounty1"){name} author_user_id
- author (EOSN Login ID){map<name, asset>} funders
- funders contributions map (EOSN Login id => amount){extended_asset} amount
- amount of tokens to be released once bounty is completed{set<name>} applicant_user_ids
- list of applicants that have applied to bounty{set<name>} approved_user_id
- approved account for bounty{name} status="pending"
- status (pending/open/started/submitted/done
){name} type="traditional"
- bounty type (traditional
= "1 worker at a time, 1 is paid out"){name} permissions="approval"
- bounty permissions (approval
= "Funder must approve hunter to start work"){map<name, string>} metadata={}
- bounty metadata{time_point_sec} created_at
- created at time{time_point_sec} updated_at
- updated at time{time_point_sec} submitted_at
- submitted at time{time_point_sec} completed_at
- completed at time
{
"bount_id": "bounty1",
"author_user_id": "author.eosn",
"funders": {"funder1.eosn": "5.0000 USDT", "funder2.eosn": "5.0000 USDT"},
"amount": {"quantity": "10.0000 USDT", "contract": "tethertether"},
"claimed": "10.0000 USDT",
"applicant_user_ids": ["hunter.eosn"],
"approved_user_id": "hunter.eosn",
"status": "pending",
"type": "traditional",
"permissions": "approval",
"metadata": [{"key": "url", "value": "https://github.com/pomelo-io/pomelo-bounties-contract/issues/1"}],
"created_at": "2020-12-06T00:00:00",
"updated_at": "2020-12-06T00:00:00",
"submitted_at": "1970-01-01T00:00:00",
"completed_at": "1970-01-01T00:00:00"
}
- scope:
{name} get_self()
{uint64_t} transfer_id
- (primary key) token transfer ID{name} bounty_id
- bounty ID{name} from
- EOS account sender{name} to
- EOS account receiver{extended_asset} ext_quantity
- amount of tokens transfered{asset} fee
- fee charged and sent toglobal.fee_account
{string} memo
- transfer memo{double} value
- valuation at time of received{checksum256} trx_id
- transaction ID{time_point_sec} created_at
- created at time
{
"transfer_id": 10001,
"bounty_id": 123,
"funder_user_id": "funder.eosn",
"from": "myaccount",
"to": "work.pomelo",
"ext_quantity": {"contract": "tethertether", "quantity": "15.0000 USDT"},
"fee": "1.0000 USDT",
"memo": "grant:grant1",
"value": 100.0,
"trx_id": "3bf31f6c32a8663bf3fdb0993a2bf3784d181dc879545603dca2046f05e0c9e1",
"created_at": "2020-12-06T00:00:00"
}
- authority:
get_self()
{name} [status]
- contract status: ok/testing/disabled{uint64_t} [fee]
- platform fee (bips - 1/100 1%){name} [login_contract]
- EOSN Login contract{name} [fee_account]
- fee account{set<name>} metadata_keys
- allowed metadata keys
$ cleos push action work.pomelo setconfig '[ok, 1000, "login.eosn", "fee.pomelo", [url]]' -p work.pomelo
- authority:
get_self()
Set token as supported asset
{symbol} sym
- (primary key) symbol{name} contract
- token contract{uint64_t} min_amount
- min amount required per bounty{uint64_t} max_amount
- max amount required per bounty
$ cleos push action work.pomelo token '["4,USDT", "tethertether", 50000, 5000000]' -p work.pomelo
- authority:
get_self()
Delete token from supported assets
{symbol_code} symcode
- symbol code
$ cleos push action work.pomelo deltoken '["USDT"]' -p work.pomelo
- authority:
author_user_id
Create bounty
{name} author_user_id
- author (EOSN Login ID){name} bount_id
- bounty ID{symbol_code} accepted_token
- accepted deposit token (ex:"USDT"
){string} url
- bounty URL (ex: GitHub issue URL){optional<name>} bounty_type
- bounty type (default = traditional)
$ cleos push action work.pomelo create '[author.eosn, bounty1, "USDT", "https://github.com/pomelo-io/pomelo-rest-api/issues/735", null]' -p author.eosn
- authority:
author_user_id
Add/remove metadata. If key == "" - remove.
{name} bounty_id
- bounty ID{name} metadata_key
- one of the allowed metadata keys{string} metadata_value
- metadata value
$ cleos push action work.pomelo setmetadata '[bounty1, url, "https://github.com/pomelo-io/pomelo-rest-api/issues/735"]' -p author.eosn
- authority:
get_self()
Set bounty state. Shouldn't be used for normal flows. Only to override by admin.
{name} bounty_id
- bounty ID{name} state
- new state `pending/closed/open/started/submitted/released/done'
$ cleos push action work.pomelo setstate '[bounty1, published]' -p work.pomelo
- authority:
get_self()
Sync bounty details from backend. Called by /admin/sync
on backend if there are inconsistencies between backend and blockchain.
{name} bounty_id
- bounty ID{name} status
- status `pending/published/banned/retired/denied'{vector<name>} applicant_user_ids
- list of applicants{optional<name>} approved_user_id
- approved applicant{time_point_sec} updated_at
- last update time{optional<time_point_sec>} submitted_at
- submitted time{optional<time_point_sec>} completed_at
- completed time
$ cleos push action work.pomelo syncbounty '[bounty1, started, [applicant1.eosn, applicant2.eosn], applicant2.eosn, 2021-01-01T00:00:00, null, null]' -p work.pomelo
- authority:
hunter_user_id
Hunter forfeits the bounty, puts the bounty into open
state and removes himself from the list of applicants
Bounty state must be "started"
{name} bounty_id
- bounty ID
$ cleos push action work.pomelo forfeit '[bounty1]' -p hunter.eosn
- authority:
author_user_id
Author closes the bounty and puts it into closed
state
Bounty state must be "open" or "pending"
{name} bounty_id
- bounty ID
$ cleos push action work.pomelo close '[bounty1]' -p author.eosn
- authority:
get_self()
Admin publishes the bounty making it open for applications
Bounty state must be "pending"
{name} bounty_id
- bounty ID
$ cleos push action work.pomelo publish '[bounty1]' -p work.pomelo
- authority:
author_user_id
Author releases funds to hunter when bounty is completed
Bounty state must be "submitted"
{name} bounty_id
- bounty ID
$ cleos push action work.pomelo release '[bounty1]' -p author.eosn
- authority:
author_user_id
Author denies completed bounty
Bounty state is reverted back to "started"
{name} bounty_id
- bounty ID
$ cleos push action work.pomelo deny '[bounty1]' -p author.eosn
- authority:
author_user_id
(EOSN Login)
Author withdraws funds from bounty in "pending" state
{name} bounty_id
- bounty ID{name} chain
- chain name{name} receiver
- receiver (Antelope account or EVM address){string} [memo=""]
- (optional) memo (only available when using Antelope receiver)
// withdraw to EOS Native
$ cleos push action work.pomelo withdraw '[bounty1, eos, "myaccount", null]' -p author.eosn
// withdraw to Exchange
$ cleos push action work.pomelo withdraw '[bounty1, eos, "eosbndeposit", "100245696"]' -p author.eosn
// withdraw to EOS EVM
$ cleos push action work.pomelo withdraw '[bounty1, eos.evm, "0xaa2F34E41B397aD905e2f48059338522D05CA534", null]' -p author.eosn
- authority:
user_id
Hunter apply to bounty
{name} bounty_id
- bounty ID{name} user_id
- user ID (EOS account linked to EOSN Login)
$ cleos push action work.pomelo apply '[bounty1, hunter.eosn]' -p hunter.eosn
- authority:
author_id
Author approves one of the hunters who applied for bounty
{name} bounty_id
- bounty ID{name} applicant_user_id
- hunter user ID
$ cleos push action work.pomelo approve '[bounty1, hunter.eosn]' -p hunter.eosn
- authority:
user_id
Hunter signals the work is completed
Funds are auto-released after 72 hours if no explicit approval from author
{name} bounty_id
- bounty ID
$ cleos push action work.pomelo complete '[bounty1]' -p hunter.eosn
- authority:
approved_user_id
(EOSN Login)
Hunter claims bounty funds
{name} bounty_id
- bounty ID{name} chain
- chain name{name} receiver
- receiver (Antelope account or EVM address){string} [memo=""]
- (optional) memo (only available when using Antelope receiver)
// claim to EOS Native
$ cleos push action work.pomelo claim '[bounty1, eos, "myaccount", null]' -p claimer.eosn
// claim to Exchange
$ cleos push action work.pomelo claim '[bounty1, eos, "eosbndeposit", "100245696"]' -p claimer.eosn
// claim to EOS EVM
$ cleos push action work.pomelo claim '[bounty1, eos.evm, "0xaa2F34E41B397aD905e2f48059338522D05CA534", null]' -p claimer.eosn
Process incoming transfer
{name} from
- from EOS account (donation sender){name} to
- to EOS account (process only incoming){asset} quantity
- quantity received{string} memo
- transfer memo, i.e. "bounty1,author.eosn"
$ cleos transfer author work.pomelo "5.0000 USDT" "bounty1,author.eosn" --contract tethertether -p author.eosn