# Presentation

This documentation intend to explain our Decentralized Application. It will cover :

* Mid Token informations
* How to use the dapp

The first version of our application aim to allow any project owner or community (dao) to promote their ESDT through a one clic staking solution.

We will complete this documentation over time based on feedback and product evolution.

If you have any question you can reach us on telegram : [FR](https://t.me/MiddleStaking) [EN](https://t.me/MiddleStaking_EN)


# Stake Unstake Rewards

The dapp page "ESDT staking"  References the list of existing staking pairs and their respective rewards that users are able to interact with.

**First**, select the "Staked Token" (default will be MID)

![](https://1032193158-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FFA7NN9vuQfFUZz5ZOvNS%2Fuploads%2Fvyh4sQOi86sain8maEty%2Fimage.png?alt=media\&token=2406714f-8bad-4c14-9aa9-bcea58a63af9)

This menu will load every existing pools related to the staked token

If you want, you can share a direct link to a staked token page with the token of your choice.

![](https://1032193158-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FFA7NN9vuQfFUZz5ZOvNS%2Fuploads%2FBP08pQ5TcjnbKufFxogy%2Fimage.png?alt=media\&token=13d8baba-4163-4a50-aa8c-62d1df9e2dcd)

**Second,** choose the pool to stake. You can split your tokens on multiple pools.

**Pool informations and interactions :**

<img src="https://1032193158-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FFA7NN9vuQfFUZz5ZOvNS%2Fuploads%2FIFdsp2zn9HQZZKtDcXAA%2Fimage.png?alt=media&amp;token=773054f6-f6f2-4556-9e8f-745c13d9fe9b" alt="" data-size="original">

1 : Logo of the token that user have to stake in this pool

2 & 3 Logo & Ticker of the token that user will receive as a staking rewards

4 : Explorer link + Social links and price of the rewarded token if they exist

5 : Amount of rewarded tokens locked in SC that will be distributed over time to users.

6 : Amount of rewarded tokens distributed since the pool creation.

7 : Distribution speed of the pool.&#x20;

8 : Calculated APR based  the (5)(7)(9) This calculation is only based on the number of token and not on the price.

9 : Amount of tokens staked by users in pool

10 : Staking position of the user (if logged)

&#x20;11 : Button stake : Open a modal and choose the amount to stake in the pool

![](https://1032193158-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FFA7NN9vuQfFUZz5ZOvNS%2Fuploads%2FpHDnoWB49jvZBrE53bpC%2Fimage.png?alt=media\&token=b036cd3d-2c0f-4a3e-90e8-0ee1a9fb7077)

Choose the amount you want to stake, clic STAKE and sign the transaction

<figure><img src="https://1032193158-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FFA7NN9vuQfFUZz5ZOvNS%2Fuploads%2FNqNryfPsesYtjucvqihH%2Fimage.png?alt=media&amp;token=c59e4087-9b22-4415-85f2-cac6db63d75b" alt=""><figcaption></figcaption></figure>

11 : Stake : add tokens to the pool&#x20;

&#x20;*Stake will automatically claim the Available rewards (17)*

12 : Amount of the the logged user has in pool

13 : Percentage of token the user have in pool

14 : Unstake -> choose the amount or unstake ALL.

&#x20;*Unstake will automatically claim the Available rewards (17)*

15 : Claim rewards -> will send the Available rewards (17) to your wallet

16 : Reinvest rewards -> will compound Available rewards (17) into user stake

*This action exist only if the staked token and the rewarded token are the same*

17 : Available rewards compute an estimation of the claimable token for the user based on  (5)(7)(9)(12) and time spent by user in pool since the last Stake/Unstake/ClaimRewards. This amount can grow on decrease over time if the user do not claim his share of the pool from time to time.

18 : This button appear only if the rewarded token have one or many pool to be staked. It will navigate to his dedicated staking page.


# Deposit

The deposit modal allow any Project owner, Dao, Community, User to create a staking pool.

Any token sent as a deposit will be "locked" in the contract and will the be available as staking rewards

The Token owner will have to choose :&#x20;

* The staked token.
* The rewarded token.
* Amount of token to deposit in pool

Interface will only propose token existing in user wallet.

<figure><img src="https://1032193158-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FFA7NN9vuQfFUZz5ZOvNS%2Fuploads%2FAowysNKs5osmz5X9A0U6%2Fimage.png?alt=media&amp;token=4674067e-3ba1-4e6a-a3f5-ec651fe8b2bb" alt=""><figcaption></figcaption></figure>

1 : Choose the token that users will have to stake to earn rewards

2 : Choose the token that users will receive as a staking rewards (wallet balance appear in front of ticker)

3 & 4 : Social and logo that the dapp was able to load from api

5 : \*Deprecated\*

6 : Open the modal and select the amount of token you want to lock inside the pool

![](https://1032193158-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FFA7NN9vuQfFUZz5ZOvNS%2Fuploads%2FAxkM3CmyhFp7x2U1P4ud%2Fimage.png?alt=media\&token=32632663-8033-4ed7-b3a4-29ebcf518b64)


# Deposit fees

By default every new pools have a 1% fees for rewards deposit

If 100 tokens are added as reward to a pool, 1 tokens will be sent to our "fees wallet" and 99 will be added as reward to the pool.

Token in our fees wallet will be sold to pay rent or added to a staking pools.


# Distribution

MID are distributed to EGLD delegators

MID tokens are not sold under private or public sale. They are distributed to our EGLD delegators once a year. Each years the number of MID distributed is reduced until we reach 120 000 / year

| Staking EGLD in | MID to share | Distributed in |
| --------------- | ------------ | -------------- |
| 2021            | 1 200 000    | 2022           |
| 2022            | 1 080 000    | 2023           |
| 2023            | 960 000      | 2024           |
| 2024            | 840 000      | 2025           |
| 2025            | 720 000      | 2026           |
| 2026            | 600 000      | 2027           |
| 2027            | 480 000      | 2028           |
| 2028            | 360 000      | 2029           |
| 2029            | 240 000      | 2030           |
| 2030            | 120 000      | 2031           |
| 2031+           | 120 000      | 2032           |

The share each user will received is calculted on the sum of rewards he get in EGLD when he "Claim" or "Redelegate"


# Staking rewards

No mid are issued for MID:MID staking.&#x20;

We have EGLD staked and rewards from staking will be used to buy back MID on the secondary market.&#x20;

The buyed MID will be then used to increase the liquidity and/or added to the staking contract for MID holders.

Anyone can track our EGLD collateral on Multiversx [explorer](https://explorer.multiversx.com/accounts/erd1c3nfhvj5jgulw62yndr6fgh0fcmut34fful733tl998zpt9s2k5qrxumhs/staking).

All MID tokens in this account balance will be added to the staking contract over time.

Other source of income can help increase the MID:MID like :&#x20;

* Fees deposit payment
* Count Down Game
* Fees from swap


# Buy & Sell

MID tokens has been listed on [Jexchange](https://app.jexchange.io/?paymentToken=EGLD\&buyToken=MID-ecb7bf) they will found the best change rate available&#x20;

We also have our own [liquidity pool](https://explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgqw0tp0z2evzvdgmreavvszfwkncnxnsejtxfql7w9tu/tokens) and listed on [xExchange](https://explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgq9aj0amrue5s6d2q5vqvrrq0vve259vp92jpsgut3vl/tokens).

We may have very small liquidity amount. Proceed with care and with small amounts to limit the impact on price. You should always have a looks on [price chart](https://e-compass.io/charts/XEXCHANGE/MID/USDC) or [liquidity](https://xexchange.com/analytics/pools/erd1qqqqqqqqqqqqqpgq9aj0amrue5s6d2q5vqvrrq0vve259vp92jpsgut3vl) before executing an order


# Use cases

Here are few things you can do with MID token at this stage if you have some :

* Hold them (yes you can)
* Sell them. It's listed on DEX so if the price match your expectation you are free to sell it.
* Send them to friends and family.
* Stake them on our app to earn more MID or others tokens listed on our staking contract by other users
* Deposit them as a staking rewards for the token of your choice.
* Distribute them with pulsar money


# Staking Contract

Source : <https://github.com/MiddleStaking/sc-esdt-staking>

Devnet : [erd1qqqqqqqqqqqqqpgq4dvqaez22usynmp7e3w957q24m6740nkch9s5lvlc7](https://devnet-explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgq4dvqaez22usynmp7e3w957q24m6740nkch9s5lvlc7)

Devnet 2 : [erd1qqqqqqqqqqqqqpgqnhdcg9ugyall5xyxa8xayz80hp5d3d6gch9s2kragz](https://devnet2-explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgqnhdcg9ugyall5xyxa8xayz80hp5d3d6gch9s2kragz)

Mainnet : [erd1qqqqqqqqqqqqqpgqgdf6vk43c2jxk4a6nw2adv8vmnpqagegtxfqmf8et2](https://explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgqgdf6vk43c2jxk4a6nw2adv8vmnpqagegtxfqmf8et2)


# Details

Few more details about staking contract

staked\_tokens : This represent the token that will be staked by users in pools

rewarded\_tokens : This represent the token that will be rewarded to users who stake in a pool

fee\_wallet : is owned by us. Fees that goes to this wallet will be used at our discretion. (Create new pool, refill existing pool, wages, infrastructures)&#x20;

burn\_wallet : will not really "burn" tokens. Tokens that will end to this wallet will be considered "out of the system" and eventually sent back to the token creator. $MID tokens ending in this wallet will be burned from time to time.


# Functions

Here is a summary of views and functions

**User functions**

```rust
fund@staked_token
```

:warning:Once funded, the rewarded\_token cannot be removed from a pool.

Must be called under ESDTTransfer function.

Transferred token will be set as reward (rewarded\_token).

The staked\_token define what token users will have to stake to harvest rewards

This function have a 10% default deposit fee for new pools. Fees can be cut forever on a pool with a $MID payment with removePoolFees function

```
stake@rewarded_token
```

Must be called under ESDTTransfer function.

Transferred token will be set as a staked\_token.

User will have to choose the rewarded\_token he want as reward

```
unstake@staked_token@rewarded_token@opt_unstake_amount
```

Allow to remove staked\_token from a pool.

Time spent in pool will be reseted and calculated rewards harvested.

If opt\_unstake\_amount is not set the unstaked amount will be set to user max user position.

```
claimRewards@staked_token@rewarded_token
```

Will calculate rewards from the pool for user and send them to his wallet.

Time spent in pool will be reseted

```
stakeRewards@staked_token
```

:grey\_question:Only for pools where staked\_token = rewarded\_token

Will calculate rewards from the pool. But instead to send rewards to user's wallet his position will be compounded.

Time spent in pool will be reseted

```
removePoolFees@staked_token@rewarded_token
```

Must be called under ESDTTransfer function.

This function will set to 0% the fees deposit of tokens in a pool. It can be called before the first deposit. The payment will be added to MID:MID pool as a staking rewards minus the fees set in MID:MID pool.

**Owner functions**

```
setFees@staked_token@rewarded_token@fees@burn@opt_blocks_to_max
```

Edit the configuration of a pool :

fees : Percentage of deposited token redirected to the "fee\_wallet"

burn : Percentage of deposited token redirected to the "burn\_wallet"

blocks\_to\_max : Configure the pool speed. Allowing to slow down or speed up rewards distribution of the pool.

```
setConfig@def_staked_token@fee_wallet@burn_wallet@remove_fees_price
```

Edit configuration&#x20;

def\_staked\_token : Set the main token that will be used as payement&#x20;

fee\_wallet : set the wallet that will receive fees tokens

burn\_wallet : set the wallet that will receive burn tokens

remove\_fees\_price : define price in main token to remove fees from a pool

```
pause
unPause
```

Pause functions of contract : fund, stake, stakeRewards, removePoolFees

Users can still unstake and claimRewards from all pools

```
pausePool@staked_token@rewarded_token
unpausePool@staked_token@rewarded_token
```

Pause main functions of a specific pool : fund, stake, stakeRewards, removePoolFees

Users can still unstake and claimRewards from the pool

```rust
close_pool@staked_token@rewarded_token
```

If a pool did not received any new fund after one year and is paused. This function allow to remove the pool from the contract and send all staked tokens to respective users. if some rewards are still in the pool, they will first be distributed to removed users based on their share and time spent in pool. The very last remaining tokens will then be sent to the burn wallet.

**View functions**

```
getDefTokenIdentifier -> Token identifier for payment
```

```
getRemoveFeesPrice -> Price to remove deposit fees
```

```
getBurnWallet -> Wallet address
```

```
getFeeWallet -> Wallet address
```

```
getStakedTokens -> unoredered array of token identifier
```

This array represent the list of tokens that can be staked in contract to get rewards

<pre><code><strong>getRewardedTokens [staked_token] -> unoredered array of token identifier
</strong></code></pre>

This array represent the list of tokens that can be harvested for a specific staked token creating a staking pool from a pair staked\_token:rewarded\_token

```
getStakedAddresses [staked_token, rewarded_token]
-> unordered array of address
```

This array return the address list of participants in a specific pool

```
getTokenPosition [staked_token, rewarded_token]
```

Return pool information :&#x20;

balance : Tokens availaibles as reward

total\_stake : Tokens staked by users

total\_rewarded : All time rewarded since the first fund

fee\_percentage : Fund percentage (default 10%)

burn\_percentage : "Burn" percentage (default 0%)

last\_fund\_block : Block of the last fund deposit

paused : Is the pool fund/stake/stakeRewards paused ?

blocks\_to\_max : Number of blocks a user has to stay in pool to claim 100% of his pool share. (default 5 256 000 \~one year)

```
getStakingPosition [ user_address, staked_token, rewarded_token]
```

Return user participation information in pool :&#x20;

stake\_amout : The amount of token staked by user

last\_action\_block : Last block since the user has called one of the stake/unstake/claimRewards/stakeRewards function

```rust
calculateRewardsForUser [ user_address, staked_token, rewarded_token]
```

Compute the current theoretical available rewards for user in pool.

{stake\_amout} \* {%} / {total\_stake} \* {balance} / {%} \* {last\_action\_block} / {blocks\_to\_max} = theoretical rewards


# Swap contract

Source :&#x20;

Not published at this time

Devnet2 :&#x20;

[erd1qqqqqqqqqqqqqpgq0dr0a8ag4y59q4nd66leux69vaeg6j9nch9swrxd82](https://devnet2-explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgq0dr0a8ag4y59q4nd66leux69vaeg6j9nch9swrxd82)

Mainnet :&#x20;

​​[erd1qqqqqqqqqqqqqpgqw0tp0z2evzvdgmreavvszfwkncnxnsejtxfql7w9tu](https://explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgqw0tp0z2evzvdgmreavvszfwkncnxnsejtxfql7w9tu)


# Details

swaped\_tokens : list all tokens that have liquidity with MID token&#x20;

All pools are created with $MID as first token.

The swap function will allow to swap in both way&#x20;

MID <-> MEX or MEX <-> MID

first\_fee from a pool is applied on tokens sent by the user and used to increase liquidity.

second\_fee is applied on amount of tokens that the user receive and added as $MID staking rewards.

MID to MEX : MID are added to liquidity and MEX added as staking rewards

Dualswap function can use 2 pools position in one time . eg wegld to mex will be done in one time doing WEGLD <-> MID <-> MEX takin the fees only one time instead of two.

WEGLD to MEX : WEGLD are added to liquidity and MEX added as staking rewards.


# Liquidity

To be able to swap 2 tokens at any time we need liquidity and to add liquidity we need to send a "proof of deposit" to users (Liquidity Pool token)

```rust
    #[only_owner]
    #[payable("EGLD")]
    #[endpoint(issueLpToken)]
    
    issueLpToken@first_token(mid)@second_token(mex)@LPname@LpTicker
```

At this stage only the owner of the contract (us) can call the function to create a new liquidity pool. If you want to    enable swap on our application please contact us.&#x20;

Must send 0,05 EGLD to pay ESDT creation

The resulting esdt ticker will be saved in pool information&#x20;

```
#[endpoint(setLocalRoles)]

setLocalRoles@first_token(mid)@second_token(mex)
```

We need to call this function once to allow the SC to mint and burn the LP token&#x20;

```rust
   #[payable("*")]
   #[endpoint(addLp)]
   fn add_lp(&self)
   
   MultiESDTNFTTransfer
   @erd1qqqqqqqqqqqqqpgqgdf6vk43c2jxk4a6nw2adv8vmnpqagegtxfqmf8et2(SC)
   @2(2 tokens)
   @MID-ecb7bf(first ticker)
   @0(nonce)
   @4000000000000000000000 (first token qty)
   @MEX-455c57 (second token)
   @0(nonce)
   @12000000000000000000000000 (second token qty)
   @addLp

```

Exemple: <https://explorer.multiversx.com/transactions/3b58877b00280ee5ff5c7d02423dfc0f0d42a726c1682aaac38f94163a6e5589>

If this is the very first deposit, the SC will consider the two amounts as the exchange ratio to be applied

If it is an addition of liquidity, the contract will calculate the maximum possible ratio and return the surplus to the user.&#x20;

In both cases, the user will receive an amount of LP tokens corresponding to his participation rate in the liquidity provision

```rust
    #[payable("*")]
    #[endpoint(removeLp)]
    fn remove_lp(&self, first_token: TokenIdentifier, second_token: TokenIdentifier)
```

The user can send his LP tokens to the SC by specifying the pairs concerned, he will receive in exchange his shares of the liquidity in place.


# Swap

Swap functions use the liquidity available to trade one token with another

```rust
    #[payable("*")]
    #[endpoint(swap)]
    fn swap(
        &self, 
        first_token: TokenIdentifier,  
        second_token: TokenIdentifier, 
        opt_min_out: OptionalValue<BigUint>,
    )
```

first\_token will always be MID token and second\_token indicate what liquidity to use.

Payment token can be first or second token.

opt\_min\_out (slippage) : is an optionnal value where user can indicate the minimum amount of token he want to receive. We will use this to set the slippage tolerance

```rust
    #[payable("*")]
    #[endpoint(dualSwap)]
    fn dual_swap(
        &self, 
        first_token: TokenIdentifier,  
        second_token: TokenIdentifier, 
        opt_min_out: OptionalValue<BigUint>,
    )
```

first token and second token must be in the "swaped\_tokens" list


# NFT/SFT Staking Contract

This contract allow any user to giveaway/rewards tokens to any SFT/NFT  collection running on the MultiversX blockchain through staking system.

Please read the documentation and feel free to contact us on [telegram](https://t.me/MiddleStaking) at any time if you want more insight on the mechanism of the contract.

Source : Not published yet

Devnet 2 : [erd1qqqqqqqqqqqqqpgqq9va3mwdgzx5qzc7qnxu8k6ay0twry5jch9sz0ymrt](https://devnet2-explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgqq9va3mwdgzx5qzc7qnxu8k6ay0twry5jch9sz0ymrt)

Mainnet : [erd1qqqqqqqqqqqqqpgq5re66vt0dlee8v83dtyh6k54qqpjs3ketxfq9tcd29](https://explorer.multiversx.com/accounts/erd1qqqqqqqqqqqqqpgq5re66vt0dlee8v83dtyh6k54qqpjs3ketxfq9tcd29)


# Details

The NFT/SFT staking contract is quite close to the staking contract as it allow anyone to deposit staking rewards. But this time, final users will have to stake NFT or SFT to harvest them.

NFT staking can be configured with few more options to improve use cases :&#x20;

* NFT/SFT collection to stake&#x20;
* ESDT token to be rewarded to participant
* Amount of esdt to distribute over time
* Speed of distribution (in days)
* Nonce restriction (all nonce or only one nonce)&#x20;
* Vesting (in days) min 0, max 40
* Unbonding (in days) min 0, max 10

If one reward pool already exist and all 6 params are strictly identical, rewards will be add to existing pool

Speed param define how fast tokens will be distributed to users participating in nft staking.

Lets say that one user has **2/5** of the staked NFT in one pool with **1000** tokens left to distribute at a speed of **10 days** and no other user will claim tokens in this scenario.

If our user wait 3 days to claim tokens after entering pool he will receive :&#x20;

tokens / share of the pool / speed \* time\_spent

1000 / 5\*2 / 10 \* 3 = 120 tokens

for 5 days :&#x20;

1000 / 5\*2 / 10 \* 5 = 200 tokens

for 10 days :&#x20;

1000 / 5\*2 / 10 \* 10 = 400 tokens


