Пример #1
0
def get_pool(pool_id: UInt256) -> list:
    creator = get(POOL_OWNER_KEY + pool_id)

    if len(creator) == 0:
        raise Exception("Pool doesn't exist.")

    description = get(POOL_DESCRIPTION_KEY + pool_id).to_str()
    options: List[str] = deserialize(get(POOL_OPTIONS_KEY + pool_id))

    result = None
    serialized_result = get(POOL_RESULT_KEY + pool_id)
    if len(serialized_result) > 0:
        result = deserialize(serialized_result)

    pool_bets: Dict[bytes, str] = {}
    bet_prefix = POOL_BET_KEY + pool_id
    bets = find(bet_prefix)
    while bets.next():
        result_pair = bets.value
        storage_key = cast(bytes, result_pair[0])
        player_bet = cast(str, result_pair[1])
        player_id = storage_key[len(bet_prefix):].to_str().to_bytes()

        pool_bets[player_id] = player_bet

    return [pool_id, creator, description, options, result, pool_bets]
Пример #2
0
def main(operation: int) -> Any:

    # create an array
    stuff = ['a', 3, ['j', 3, 5], 'jk', 'lmnopqr']

    # serialize it
    to_save = StdLib.serialize(stuff)
    put('serialized', to_save)

    if operation == 1:
        return to_save

    elif operation == 2:
        to_retrieve = get('serialized')
        return to_retrieve

    elif operation == 3:

        to_retrieve = get('serialized')
        deserialized = StdLib.deserialize(to_retrieve)
        return deserialized

    elif operation == 4:

        to_retrieve = get('serialized')
        deserialized = StdLib.deserialize(to_retrieve)
        return cast(list, deserialized)[2]

    return False
Пример #3
0
def main(operation: int) -> Any:

    # create an array
    stuff = ['a', 3, ['j', 3, 5], 'jk', 'lmnopqr']

    # serialize it
    to_save = serialize(stuff)
    put('serialized', to_save)

    if operation == 1:
        return to_save

    elif operation == 2:
        to_retrieve = get('serialized')
        return to_retrieve

    elif operation == 3:

        to_retrieve = get('serialized')
        deserialized = deserialize(to_retrieve)
        return deserialized

    elif operation == 4:

        to_retrieve = get('serialized')
        deserialized = deserialize(to_retrieve)
        if isinstance(deserialized, list):
            return deserialized[2]

    return False
Пример #4
0
def cancel_pool(pool_id: UInt256):
    creator_on_storage = get(POOL_OWNER_KEY + pool_id)

    if len(creator_on_storage) == 0:
        raise Exception("Pool doesn't exist.")

    creator = UInt160(creator_on_storage)
    if not check_witness(creator):
        raise Exception('No authorization.')
    if len(get(POOL_RESULT_KEY + pool_id)) > 0:
        raise Exception('Pool is finished already')

    executing_contract = executing_script_hash

    # refund players
    bets_key_prefix = POOL_BET_KEY + pool_id
    bet = find(bets_key_prefix)
    while bet.next():
        result_pair: List[bytes] = bet.value
        storage_key = result_pair[0]

        account = UInt160(storage_key[len(bets_key_prefix):])
        transfer_gas(executing_contract, account, PRICE_IN_GAS)

    # set result
    put(POOL_RESULT_KEY + pool_id, serialize('Cancelled by owner'))
Пример #5
0
def get_reserves() -> List[int]:
    """
    Returns how many token_a and token_b tokens are in the pool.

    :return: a list of 2 ints, the value in the first index is reserve of token_a and the second value is the reserve of token_b
    """
    return [get(SUPPLY_KEY + TOKEN_A).to_int(), get(SUPPLY_KEY + TOKEN_B).to_int()]
Пример #6
0
def refund() -> bool:
    """
    If the atomic swap didn't occur in time, refunds the cryptocurrency that was deposited in this smart contract

    :return: whether enough time has passed and the cryptocurrencies were refunded
    :rtype: bool
    """
    if get_time > get(START_TIME).to_int() + LOCK_TIME:
        # Checking if PERSON_A transferred to this smart contract
        funded_crypto = get(FUNDED_PREFIX + PERSON_A).to_int()
        if funded_crypto != 0:
            call_contract(UInt160(get(TOKEN_PREFIX + PERSON_A)), 'transfer', [
                executing_script_hash,
                UInt160(get(ADDRESS_PREFIX + PERSON_A)),
                get(AMOUNT_PREFIX + PERSON_A).to_int(), None
            ])

        # Checking if PERSON_B transferred to this smart contract
        funded_crypto = get(FUNDED_PREFIX + PERSON_B).to_int()
        if funded_crypto != 0:
            call_contract(UInt160(get(TOKEN_PREFIX + PERSON_B)), 'transfer', [
                executing_script_hash,
                get(ADDRESS_PREFIX + PERSON_B),
                get(AMOUNT_PREFIX + PERSON_B).to_int(), None
            ])
        put(FUNDED_PREFIX + PERSON_A, 0)
        put(FUNDED_PREFIX + PERSON_B, 0)
        put(NOT_INITIALIZED, True)
        put(START_TIME, 0)
        return True
    return False
Пример #7
0
def withdraw(secret: str) -> bool:
    """
    Deposits the contract's cryptocurrency into the owner and other_person addresses as long as they both transferred
    to this contract and there is some time remaining

    :param secret: the private key that unlocks the transaction
    :type secret: str

    :return: whether the transfers were successful
    :rtype: bool
    """
    # Checking if OWNER and OTHER_PERSON transferred to this smart contract
    funded_owner = get(FUNDED_PREFIX + OWNER).to_int()
    funded_other_person = get(FUNDED_PREFIX + OTHER_PERSON).to_int()
    if verify() and not refund() and hash160(secret) == get(SECRET_HASH) and funded_owner != 0 and funded_other_person != 0:
        put(FUNDED_PREFIX + OWNER, 0)
        put(FUNDED_PREFIX + OTHER_PERSON, 0)
        put(NOT_INITIALIZED, True)
        put(START_TIME, 0)
        call_contract(UInt160(get(TOKEN_PREFIX + OTHER_PERSON)), 'transfer',
                      [executing_script_hash, get(ADDRESS_PREFIX + OWNER), get(AMOUNT_PREFIX + OTHER_PERSON), ''])
        call_contract(UInt160(get(TOKEN_PREFIX + OWNER)), 'transfer',
                      [executing_script_hash, get(ADDRESS_PREFIX + OTHER_PERSON), get(AMOUNT_PREFIX + OWNER), ''])
        return True

    return False
Пример #8
0
def withdraw(secret: str) -> bool:
    """
    Deposits the contract's cryptocurrency into the person_a and person_b addresses as long as they both transferred
    to this contract and there is some time remaining

    :param secret: the private key that unlocks the transaction
    :type secret: str

    :return: whether the transfers were successful
    :rtype: bool
    """
    # Checking if PERSON_A and PERSON_B transferred to this smart contract
    funded_person_a = storage.get(FUNDED_PREFIX + PERSON_A).to_int()
    funded_person_b = storage.get(FUNDED_PREFIX + PERSON_B).to_int()
    if verify() and not refund() and hash160(secret) == storage.get(
            SECRET_HASH) and funded_person_a != 0 and funded_person_b != 0:
        storage.put(FUNDED_PREFIX + PERSON_A, 0)
        storage.put(FUNDED_PREFIX + PERSON_B, 0)
        storage.put(NOT_INITIALIZED, True)
        storage.put(START_TIME, 0)
        call_contract(UInt160(storage.get(TOKEN_PREFIX + PERSON_B)),
                      'transfer', [
                          runtime.executing_script_hash,
                          storage.get(ADDRESS_PREFIX + PERSON_A),
                          storage.get(AMOUNT_PREFIX + PERSON_B), None
                      ])
        call_contract(UInt160(storage.get(TOKEN_PREFIX + PERSON_A)),
                      'transfer', [
                          runtime.executing_script_hash,
                          storage.get(ADDRESS_PREFIX + PERSON_B),
                          storage.get(AMOUNT_PREFIX + PERSON_A), None
                      ])
        return True

    return False
Пример #9
0
def totalSupply() -> int:
    """
    Gets the total token supply deployed in the system.

    This number must not be in its user representation. E.g. if the total supply is 10,000,000 tokens, this method
    must return 10,000,000 * 10 ^ decimals.

    :return: the total token supply deployed in the system.
    """
    debug(['totalSupply: ', get(SUPPLY_PREFIX).to_int()])
    return get(SUPPLY_PREFIX).to_int()
Пример #10
0
def isPaused() -> bool:
    """
    Get the contract pause status.

    If the contract is paused, some operations are restricted.

    :return: whether the contract is paused
    """
    debug(['isPaused: ', get(PAUSED).to_bool()])
    if get(PAUSED).to_bool():
        return True
    return False
Пример #11
0
def transfer(from_address: UInt160, to_address: UInt160, amount: int,
             data: Any) -> bool:
    """
    Transfers a specified amount of NEP17 tokens from one account to another

    If the method succeeds, it must fire the `transfer` event and must return true, even if the amount is 0,
    or from and to are the same address.

    :param from_address: the address to transfer from
    :type from_address: UInt160
    :param to_address: the address to transfer to
    :type to_address: UInt160
    :param amount: the amount of NEP17 tokens to transfer
    :type amount: int
    :param data: whatever data is pertinent to the onPayment method
    :type data: Any

    :return: whether the transfer was successful
    :raise AssertionError: raised if `from_address` or `to_address` length is not 20 or if `amount` if less than zero.
    """
    # the parameters from and to should be 20-byte addresses. If not, this method should throw an exception.
    assert len(from_address) == 20 and len(to_address) == 20
    # the parameter amount must be greater than or equal to 0. If not, this method should throw an exception.
    assert amount >= 0

    # The function MUST return false if the from account balance does not have enough tokens to spend.
    from_balance = storage.get(from_address).to_int()
    if from_balance < amount:
        return False

    # The function should check whether the from address equals the caller contract hash.
    # If so, the transfer should be processed;
    # If not, the function should use the check_witness to verify the transfer.
    if from_address != runtime.calling_script_hash:
        if not runtime.check_witness(from_address):
            return False

    # skip balance changes if transferring to yourself or transferring 0 cryptocurrency
    if from_address != to_address and amount != 0:
        if from_balance == amount:
            storage.delete(from_address)
        else:
            storage.put(from_address, from_balance - amount)

        to_balance = storage.get(to_address).to_int()
        storage.put(to_address, to_balance + amount)

    # if the method succeeds, it must fire the transfer event
    on_transfer(from_address, to_address, amount)
    # if the to_address is a smart contract, it must call the contracts onPayment
    post_transfer(from_address, to_address, amount, data)
    # and then it must return true
    return True
Пример #12
0
def transfer(from_address: bytes, to_address: bytes, amount: int) -> bool:
    """
    Transfers a specified amount of NEP5 tokens from one account to another

    If the method succeeds, it must fire the `transfer` event and must return true, even if the amount is 0,
    or from and to are the same address.

    :param from_address: the address to transfer from
    :type from_address: bytes
    :param to_address: the address to transfer to
    :type to_address: bytes
    :param amount: the amount of NEP5 tokens to transfer
    :type amount: int

    :return: whether the transfer was successful
    :raise AssertionError: raised if `from_address` or `to_address` length is not 20 or if `amount` if less than zero.
    """
    # the parameters from and to should be 20-byte addresses. If not, this method should throw an exception.
    assert len(from_address) == 20 and len(to_address) == 20
    # the parameter amount must be greater than or equal to 0. If not, this method should throw an exception.
    assert amount >= 0

    # The function MUST return false if the from account balance does not have enough tokens to spend.
    from_balance = get(from_address).to_int()
    if from_balance < amount:
        return False

    # The function should check whether the from address equals the caller contract hash.
    # If so, the transfer should be processed;
    # If not, the function should use the check_witness to verify the transfer.
    if from_address != calling_script_hash:
        if not check_witness(from_address):
            return False

    # if the `to_address` is a deployed contract, the function should check the payable flag of this contract
    # TODO: include example when objects are implemented

    if from_address == to_address:
        # transfer to self
        return True

    if from_balance == amount:
        delete(from_address)
    else:
        put(from_address, from_balance - amount)

    to_balance = get(to_address).to_int()
    put(to_address, to_balance + amount)

    # if the method succeeds, it must fire the transfer event, and must return true
    on_transfer(from_address, to_address, amount)
    return True
Пример #13
0
def updatePause(status: bool) -> bool:
    """
    Set contract pause status.

    :param status: the status of the contract pause
    :type status: bool
    :return: the contract pause status
    :raise AssertionError: raised if witness is not verified.
    """
    assert verify(), '`acccount` is not allowed for updatePause'
    put(PAUSED, status)
    debug(['updatePause: ', get(PAUSED).to_bool()])
    return get(PAUSED).to_bool()
Пример #14
0
def balanceOf(owner: UInt160) -> int:
    """
    Get the current balance of an address

    The parameter owner must be a 20-byte address represented by a UInt160.

    :param owner: the owner address to retrieve the balance for
    :type owner: UInt160
    :return: the total amount of tokens owned by the specified address.
    :raise AssertionError: raised if `owner` length is not 20.
    """
    assert len(owner) == 20, "Incorrect `owner` length"
    debug(['balanceOf: ', get(mk_balance_key(owner)).to_int()])
    return get(mk_balance_key(owner)).to_int()
Пример #15
0
def getFeesMap() -> Iterator:
    """
    How many fees of each kind of token can be collected
    :return: collateral_token: amount_of_fees.to_bytes()
    """
    administrator = get(ADMINISTRATOR_KEY)
    if not (check_witness(administrator)
            or calling_script_hash == administrator):
        fee_receiver = get(
            FEE_RECEIVER_KEY
        )  # if not admin, get fee_receiver. This saves GAS for executing this API
        assert check_witness(
            fee_receiver) or calling_script_hash == fee_receiver
    return find(b'feesMap')
Пример #16
0
def cancel_player_bet(player: UInt160, bet_id: UInt256):
    if len(get(POOL_OWNER_KEY + bet_id)) == 0:
        raise Exception("Pool doesn't exist.")
    if not check_witness(player):
        raise Exception('No authorization.')
    if len(get(POOL_RESULT_KEY + bet_id)) > 0:
        raise Exception('Pool is finished already')
    if len(get(POOL_BET_KEY + bet_id + player)) == 0:
        raise Exception("Player didn't bet on this pool")

    # 5% fee of the bet for cancelling
    refund_value = PRICE_IN_GAS - PRICE_IN_GAS * 5 // 100
    transfer_gas(executing_script_hash, player, refund_value)

    delete(POOL_BET_KEY + bet_id + player)
Пример #17
0
def onNEP17Payment(from_address: UInt160, amount: int, data: Any):
    """
    Since this is a deployed contract, transfer will be calling this onPayment method with the data parameter from
    transfer. If someone is doing a not required transfer, then ABORT will be called.

    :param from_address: the address of the one who is trying to transfer cryptocurrency to this smart contract
    :type from_address: UInt160
    :param amount: the amount of cryptocurrency that is being sent to this smart contract
    :type amount: int
    :param data: any pertinent data that may validate the transaction
    :type data: Any

    :raise AssertionError: raised if `from_address` length is not 20
    """
    # the parameters from and to should be 20-byte addresses. If not, this method should throw an exception.
    aux_var = from_address is not None  # TODO: using identity operators or isinstance as a condition of an if is bugged
    if aux_var:
        assert len(from_address) == 20

    # this validation will verify if Neo is trying to mint GAS to this smart contract
    aux_var = from_address is None  # TODO: using identity operators or isinstance as a condition of an if is bugged
    if aux_var and runtime.calling_script_hash == GAS_SCRIPT:
        return

    if not storage.get(NOT_INITIALIZED).to_bool():
        # Used to check if the one who's transferring to this contract is the PERSON_A
        address = storage.get(ADDRESS_PREFIX + PERSON_A)
        # Used to check if PERSON_A already transfer to this smart contract
        funded_crypto = storage.get(FUNDED_PREFIX + PERSON_A).to_int()
        # Used to check if PERSON_A is transferring the correct amount
        amount_crypto = storage.get(AMOUNT_PREFIX + PERSON_A).to_int()
        # Used to check if PERSON_A is transferring the correct token
        token_crypto = storage.get(TOKEN_PREFIX + PERSON_A)
        if (from_address == address and funded_crypto == 0
                and amount == amount_crypto
                and runtime.calling_script_hash == token_crypto):
            storage.put(FUNDED_PREFIX + PERSON_A, amount)
            return
        else:
            # Used to check if the one who's transferring to this contract is the OTHER_PERSON
            address = storage.get(ADDRESS_PREFIX + PERSON_B)
            # Used to check if PERSON_B already transfer to this smart contract
            funded_crypto = storage.get(FUNDED_PREFIX + PERSON_B).to_int()
            # Used to check if PERSON_B is transferring the correct amount
            amount_crypto = storage.get(AMOUNT_PREFIX + PERSON_B).to_int()
            # Used to check if PERSON_B is transferring the correct token
            token_crypto = storage.get(TOKEN_PREFIX + PERSON_B)
            if (from_address == address and funded_crypto == 0
                    and amount == amount_crypto
                    and runtime.calling_script_hash == token_crypto):
                storage.put(FUNDED_PREFIX + PERSON_B, amount)
                return
    abort()
Пример #18
0
def transfer(to: UInt160, token_id: bytes, data: Any):
    assert len(to) == 20

    token = cast(Dict['str'], deserialize(get(TOKEN_PREFIX + token_id)))

    from_address: UInt160 = token['owner']
    if from_address != calling_script_hash and not check_witness(from_address):
        return False

    # if it's not transferring to your own account
    if from_address != to:
        owner = cast(List[int],
                     deserialize(get(ACCOUNT_PREFIX + from_address)))

    post_transfer()
    return True
Пример #19
0
def is_valid_address(address: UInt160) -> bool:
    """
    Validates if the address passed through the kyc.

    :return: whether the given address is validated by kyc
    """
    return storage.get(KYC_WHITELIST_PREFIX + address).to_int() > 0
Пример #20
0
def get_unclaimed(index: str, material: str) -> int:
    land = land_get(index)
    rate = cast(int, land[material])

    last_claim = cast(
        int, get(CLAIM_TIMESTAMP + index.to_bytes() + material.to_bytes()))
    return (get_time - max(cast(int, land["genesis"]), last_claim)) * rate + 1
Пример #21
0
def totalSupply() -> int:
    """
    Gets the total token supply deployed in the system.

    :return: the total token supply in the system.
    """
    return get(TOTAL_SUPPLY).to_int()
Пример #22
0
def method(account: UInt160):
    """
    This method is not working as intended and ends up giving tokens to a user whenever he wants.
    """
    # some omitted code
    storage.put(account, storage.get(account).to_int() + 2 * 10 ** 8)
    on_transfer(None, account, 2 * 10 ** 8)
Пример #23
0
def deploy(administrator: UInt160) -> bool:
    """
    administrating access is mostly related to flashLoan
    """
    assert check_witness(administrator) or calling_script_hash == administrator
    if get(DEPLOYED_KEY) == b'':  # not deployed
        assert get(ADMINISTRATOR_KEY) == b''
        put(ADMINISTRATOR_KEY, administrator)
        put(FEE_RECEIVER_KEY, administrator)
        put(DEPLOYED_KEY, 1)
    else:
        original_administrator = get(ADMINISTRATOR_KEY)
        assert check_witness(original_administrator
                             ) or calling_script_hash == original_administrator
        put(ADMINISTRATOR_KEY, administrator)
    return True
Пример #24
0
def setWhitelistedAddress(address: UInt160, authorized: bool):
    """
    Configure whitelisted addresses.

    When this contract address is included in the transaction signature,
    this method will be triggered as a VerificationTrigger to verify that the signature is correct.
    For example, this method needs to be called when using the no fee mint method.

    :param address: the address of the account that is being authorized
    :type address: UInt160
    :param authorized: authorization status of this address
    :type authorized: bool
    :return: whether the transaction signature is correct
    :raise AssertionError: raised if witness is not verified.
    """
    assert verify(), '`acccount` is not allowed for setWhitelistedAddress'
    serialized = get(WL_ADDRESSES)
    auth = cast(list[UInt160], deserialize(serialized))

    if authorized:
        found = False
        for i in auth:
            if i == address:
                found = True

        if not found:
            auth.append(address)

        put(WL_ADDRESSES, serialize(auth))
        on_auth(address, 1, True)
    else:
        auth.remove(address)
        put(WL_ADDRESSES, serialize(auth))
        on_auth(address, 1, False)
Пример #25
0
def _insert_pair(active: bool, feeRate: int, mintRatio: int, expiry: int,
                 collateralToken: UInt160, pairedToken: UInt160,
                 rcToken: UInt160, rrToken: UInt160, colTotal: int) -> int:
    """
    Create a new pair, writing its attributes.
    This method does not consider whether the pair already exists. Check existence before you call `_insert_pair`
    pairs[_col][_paired][_expiry][_mintRatio] = pair.
    :param active: Whether the pair is active for new deposits.
        If False, `deposit` and `mmDeposit` cannot be called for this pair
    :param feeRate: How much fee will be accrued.
        The fee for collateral is charged when collateral is collected (e.g. `collect` with defaulted loans, `redeem`).
        The fee for paired token is charged when the paired token is given to ruler (`repay` and `mmDeposit`).
    :param mintRatio: pair attribute: mint ratio: 1 collateral token for how many rTokens. DECIMAL_BASE applied.
    :param expiry: pair attribute: expiry timestamp in milliseconds
    :param collateralToken: the collateral token address for this pair
    :param pairedToken: the paired token address for this pair
    :param rcToken: the rcToken address for this pair
    :param rrToken: the rrToken address for this pair
    :param colTotal: the total amount of collateral that has been deposited into this pair.
        Usually set to 0 when created.
    :return: the index of the new pair
    """
    max_index = get(max_pair_index_key).to_int()
    max_index = max_index + 1
    put(max_pair_index_key, max_index)
    pair_map.put(gen_pair_key(max_index, "active"), active)
    pair_map.put(gen_pair_key(max_index, "feeRate"), feeRate)
    pair_map.put(gen_pair_key(max_index, "mintRatio"), mintRatio)
    pair_map.put(gen_pair_key(max_index, "expiry"), expiry)
    pair_map.put(gen_pair_key(max_index, "pairedToken"), pairedToken)
    pair_map.put(gen_pair_key(max_index, "collateralToken"), collateralToken)
    pair_map.put(gen_pair_key(max_index, "rcToken"), rcToken)
    pair_map.put(gen_pair_key(max_index, "rrToken"), rrToken)
    pair_map.put(gen_pair_key(max_index, "colTotal"), colTotal)
    return max_index
Пример #26
0
def _deploy(data: Any, upgrade: bool):
    """
    The contracts initial entry point, on deployment.
    """
    if upgrade:
        return

    if get(DEPLOYED).to_bool():
        abort()

    tx = cast(Transaction, script_container)
    #DEBUG_START
    #custom owner for tests
    if tx.sender is None:
        owner = UInt160(b'\x96Wl\x0e**\x1c!\xc4\xac^\xbd)31\x15%A\x1f@')


#DEBUG_END

    put(DEPLOYED, True)
    put(PAUSED, False)
    put(TOKEN_COUNT, 0)
    put(MINT_FEE, MINT_FEE_ON_DEPLOY)

    auth: List[UInt160] = []
    auth.append(tx.sender)
    serialized = serialize(auth)
    put(AUTH_ADDRESSES, serialized)

    wl: List[UInt160] = []
    wl.append(tx.sender)
    wl_serialized = serialize(auth)
    put(WL_ADDRESSES, wl_serialized)
Пример #27
0
def flashLoan(_receiver: UInt160, _token: UInt160, _amount: int,
              _data: Any) -> bool:
    """
    invoker receives an amount of token immediately, utilize the amount of paired token immediately with onFlashLoan,
        and repay all the borrowed paired token and an amount of fee immediately.
    This method may be vulnerable to attacks, because untrusted contracts must be called
    :param _receiver: The wallet address that will receive the flashLoan, use it, and pay back immediately
    :param _token: the token address of the loan
    :param _amount: the amount of the loan
    :param _data: user-defined, anything
    :return: True
    """
    assert call_contract(
        _token, "transfer",
        [executing_script_hash, _receiver, _amount, _data
         ]), "Failed to transfer from Ruler to flashLoan receiver"
    fee = get(FLASH_LOAN_RATE_KEY).to_int() * _amount // DECIMAL_BASE
    assert call_contract(
        _receiver, 'onFlashLoan',
        [calling_script_hash, _token, _amount, fee, _data
         ]), "Failed to execute method 'onFlashLoan' of flashLoan receiver"
    assert call_contract(
        _token, "transfer",
        [_receiver, executing_script_hash, _amount + fee, _data
         ]), "Failed to transfer from flashLoan receiver to Ruler"
    feesMap.put(_token, feesMap.get(_token).to_int() + fee)
    return True
Пример #28
0
def deploy(ruler: UInt160, symbol: str, decimals: int) -> bool:
    """
    Initializes the params when the smart contract is deployed. This method must be executed immediately when deployed
    :param ruler: the address of ruler contract
    :param symbol: the symbol of rToken, f'{RC or RR}_{COLLATERAL_RATE}_{MINT_RATIO}_{PARITY_TOKEN}_{EXPIRY_TIMESTAMP}'
    :return: whether the deploy was successful. This method must return True only during the smart contract's deploy.
    """
    # do not check whether calling_script_hash == ruler, because this contract is deployed just now
    assert get(NOT_DEPLOYED_KEY) == b'' \
           and get(RULER_KEY) == b'' \
           and totalSupply() == 0, \
        'Ruler Core: the token has been deployed'
    put(NOT_DEPLOYED_KEY, 1)
    put(RULER_KEY, ruler)
    put(TOKEN_SYMBOL_KEY, symbol)
    put(TOKEN_DECIMALS_KEY, decimals)
    return True
Пример #29
0
def finish_pool(pool_id: UInt256, winner_options: List[str]):
    creator = get(POOL_OWNER_KEY + pool_id)

    if len(creator) == 0:
        raise Exception("Pool doesn't exist.")
    if not check_witness(creator):
        raise Exception('No authorization.')
    if len(get(POOL_RESULT_KEY + pool_id)) > 0:
        raise Exception('Pool is finished already')
    if len(winner_options) == 0:
        raise Exception('At least one winner is required')

    # validate all winner options are valid options
    winner_options: List[str] = remove_duplicates(winner_options)
    pool_options: List[str] = deserialize(get(POOL_OPTIONS_KEY + pool_id))
    for option in winner_options:
        if option not in pool_options:
            raise Exception('Invalid option for this pool')

    winners: List[UInt160] = []

    # get winner players
    bets_key_prefix = POOL_BET_KEY + pool_id
    bet = find(bets_key_prefix)
    while bet.next():
        result_pair = bet.value
        storage_key = cast(bytes, result_pair[0])
        account_bet = cast(str, result_pair[1])

        if account_bet in winner_options:
            address = storage_key[len(bets_key_prefix):]
            account = UInt160(address)
            winners.append(account)

    # distribute the prizes
    if len(winners) > 0:
        total_stake = get(POOL_TOTAL_STAKE_KEY + pool_id).to_int()
        prize_per_winner = total_stake // len(winners)
        executing_contract = executing_script_hash

        for winner in winners:
            transfer_gas(executing_contract, winner, prize_per_winner)

    # set result
    put(POOL_RESULT_KEY + pool_id, serialize(winner_options))
Пример #30
0
def create_land(owner: UInt160) -> bool:

    total_supply = get(TOTAL_SUPPLY)

    new_land = land_init(total_supply, owner)
    land_save(new_land)

    put(TOTAL_SUPPLY, total_supply.to_int() + 1)
    return True