예제 #1
0
    def balanceTotalSupply():
        request = app.current_request
        data = request.json_body
        token = Database.find_one("Token", {"address": data["token"]})
        if not token:
            raise NotFoundError('token not found with address {}'.format(
                data["token"]))
        print(data)
        Database.update("Token", {"id": token["id"]},
                        {"totalSupply": data["newTotalSupply"]})

        user = Database.find_one("User", {'address': data["owner"]})
        if not user:
            raise NotFoundError('user not found with address {}'.format(
                data["owner"]))
        userBalance = Database.find_one("TokenBalance", {
            'userId': user['id'],
            "tokenId": token["id"]
        },
                                        insert=True)
        if 'balance' not in userBalance: userBalance['balance'] = '0'
        if not userBalance['balance']: userBalance['balance'] = '0'
        newBalance = int(float(userBalance['balance'])) + int(
            float(data["newTotalSupply"])) - int(float(data["oldTotalSupply"]))
        userBalance = Database.update("TokenBalance",
                                      {"id": userBalance["id"]},
                                      {"balance": newBalance},
                                      return_updated=True)[0]
        return toObject(userBalance)
예제 #2
0
    def test_update(self):
        with patch.dict('os.environ', env):
            Database.insert("User", {'name': 'tom'})
            Database.update("User", [[('name','=','tom')]], {'name': 'tom2'})

            user = Database.find_one("User", {'name': 'tom'})
            self.assertEqual(user, None)

            user = Database.find_one("User", {'name': 'tom2'})
            self.assertEqual(user['name'], 'tom2')
예제 #3
0
 def truelayer():
     request = app.current_request
     if 'id' not in request.query_params: raise NotFoundError('id')
     user_id = request.query_params['id']
     user = Database.find_one('User', {'id': user_id})
     nonce = ''.join(
         random.choice("qwertyuioplkjhgfdsazxvbnm") for _ in range(10))
     Database.update('User', {"id": int(user["id"])}, {"nonce": nonce})
     url = TL.get_auth_url(nonce)
     return Response(body=None, status_code=302, headers={"Location": url})
예제 #4
0
    def balanceTransfer():
        request = app.current_request
        data = request.json_body
        print("\n\nbalanceTransfer\n\n")
        print(data)
        print("\n\nbalanceTransfer\n\n")
        token = Database.find_one("Token", {"address": data["token"]})
        fromUser = Database.find_one("User", {'address': data["from"]})
        if not fromUser:
            raise NotFoundError('user not found with address {}'.format(
                data["from"]))
        toUser = Database.find_one("User", {'address': data["to"]})
        if not toUser:
            raise NotFoundError('user not found with address {}'.format(
                data["to"]))
        value = data['value']

        fromBalance = Database.find_one("TokenBalance", {
            'userId': fromUser['id'],
            "tokenId": token["id"]
        },
                                        for_update=True)
        # If there is no from balance this transfer cannot be valid
        if not fromBalance:
            raise NotFoundError('token balance not found for user {}'.format(
                fromUser['id']))
        # Check does the user have enough balance
        print("fromBalanceYo: ", fromBalance)
        if ('balance' not in fromBalance or not fromBalance['balance']
                or int(fromBalance['balance']) < int(value)):
            raise NotFoundError('token balance not enough for user {}'.format(
                fromUser['id']))

        newFromBalance = int(float(fromBalance['balance'])) - int(float(value))
        fromBalance = Database.update("TokenBalance",
                                      {"id": fromBalance["id"]},
                                      {"balance": newFromBalance},
                                      return_updated=True)[0]

        toBalance = Database.find_one("TokenBalance", {
            'userId': toUser['id'],
            "tokenId": token["id"]
        },
                                      insert=True,
                                      for_update=True)
        if 'balance' not in toBalance: toBalance['balance'] = '0'
        if not toBalance['balance']: toBalance['balance'] = '0'
        newToBalance = int(float(toBalance['balance'])) + int(float(value))
        toBalance = Database.update("TokenBalance", {"id": toBalance["id"]},
                                    {"balance": newToBalance},
                                    return_updated=True)[0]

        return {"message": "Funds transferred"}
예제 #5
0
  def trades_claim(tradeId):
    trade = Database.find_one("Trade", {"id": int(tradeId)})
    decrypted = Cryptor.decryptInput(trade['nominalAmount'], trade['sk'])
    price = Cryptor.decryptInput(trade['price'], trade['sk'])

    # Ill need to include the currency here
    amountInvested = int(decrypted.split(':')[1])
    if trade['state'] != 5:
      return {'message': 'Trade is in state {}, requires state 5'.format(trade['state'])}

    # get trade dates nav
    nav = Database.find_one("NAVTimestamp", {"tokenId": trade["tokenId"]}, order_by='-createdAt')
    # get todays nav and totalSupply
    token = Database.find_one('Token', {'id': trade['tokenId']})

    totalTokens = int(amountInvested / nav['price'])

    investorTokens = None
    if amountInvested > 0:
      effectiveNAV = (1.0+float(price)/100)*nav['price']
      investorTokens = amountInvested / effectiveNAV
    else:
      investorTokenBalance = Database.find_one("TokenBalance", {"tokenId": token["id"], "userId": investor["id"]})
      if not investorTokenBalance['balance']: investorTokenBalance['balance'] = '0'
      effectiveNAV = (1-float(price)/100)*nav['price']
      investorTokens =  min(int(amountInvested / effectiveNAV), -1 * int(investorTokenBalance['balance']))

    tokenContract = Web3Helper.getContract("ETT.json", token['address'])
    totalSupply = Web3Helper.call(tokenContract,'dateTotalSupply',arrow.get(trade['executionDate']).format('YYYY-MM-DD'),)

    # find number of tokens user allocated
    numberTokens = 0 if not nav['price'] else math.floor(amountInvested * totalSupply / nav['price'])
    investorTokens = int(investorTokens * math.pow(10, token['decimals']))

    # now ask the contract to distribute the tokens (maybe should be the investor that does this)
    investor = Database.find_one("User", {"id": trade["investorId"]})
    tradeKernelContract = Web3Helper.getContract("TradeKernel.json")
    tx = Web3Helper.transact(
      tradeKernelContract,
      'distributeTokens',
      trade['hash'],
      [
        Web3Helper.toChecksumAddress(token['address']),
        Web3Helper.toChecksumAddress(investor['address']),
      ],
      [
        investorTokens
      ]
    )
    print(tx.hex())
    Database.update("Trade", {"id": trade["id"]}, {"state": 6, "numberTokens": numberTokens})
    return {"message": "Tokens distributed"}
예제 #6
0
  def trades_show(tradeId):
    request = app.current_request
    data = request.json_body
    trade = Database.find_one("Trade", {"id": int(tradeId)})
    if not trade: raise NotFoundError("trade not found with id {}".format(tradeId))

    tradeBroker = Database.find_one("TradeBroker", {
      "tradeId": trade["id"],
      "brokerId": request.user["id"]
    })
    if not tradeBroker: raise NotFoundError("tradeBroker not found with trade id {}".format(tradeId))
    Database.update("TradeBroker", {"id": tradeBroker["id"]}, {"price": data["price"]})
    # Socket, should be pushing to a message queue of some kind
    r = passWithoutError(requests.post)(socket_uri + "trade-update", data=toObject(trade))
    return toObject(trade)
예제 #7
0
  def trades_confirmed():
    request = app.current_request
    data = request.json_body
    tradeHash = data['tradeHash']
    broker = Database.find_one("User", {"address": data["broker"]})
    trade = Database.find_one("Trade", {"hash": tradeHash})
    if not trade: raise NotFoundError("trade not found with hash {}".format(tradeHash))

    Database.update("Trade", {"id": trade["id"]}, {"state": 1})
    Database.update("TradeBroker", {"tradeId": trade["id"], "brokerId": broker["id"]}, {"state": 1})

    trade["state"] = 1
    # Socket, should be pushing to a message queue of some kind
    r = passWithoutError(requests.post)(socket_uri + "trade-update", data=toObject(trade))
    return toObject(trade)
예제 #8
0
    def user_put(userId):
        request = app.current_request
        data = request.json_body

        if 'address' in data:
            # Find if another user
            # requestingUser = request.user
            data['address'] = Web3Helper.toChecksumAddress(data['address'])
            # user = Database.find_one("User", {'address': data['address']})
            # if user and user['id'] != requestingUser['id']:
            #   raise ForbiddenError('user already exists with address {}'.format(data['address']))

        user = Database.find_one("User", {'id': int(userId)})
        if not user:
            raise NotFoundError('user not found with id {}'.format(userId))
        user = Database.update('User', {'id': user['id']},
                               data,
                               return_updated=True)[0]

        if 'address' in data:
            # Set user athorized as investor
            tx = Web3Helper.transact(permissions_contract, 'setAuthorized',
                                     data['address'], 1)

        return toObject(
            user, ['id', 'name', 'address', 'role', 'ik', 'spk', 'signature'])
예제 #9
0
    def test_update_multiple_with_or(self):
        with patch.dict('os.environ', env):
            Database.insert("User", {'name': 'tom'})
            Database.insert("User", {'name': 'tom2'})

            Database.update("User", [[('name','=','tom')],[('name','=','tom2')]], {'name': 'tom3'})

            user = Database.find_one("User", {'name': 'tom'})
            self.assertEqual(user, None)
            user = Database.find_one("User", {'name': 'tom2'})
            self.assertEqual(user, None)

            users = Database.find("User", {'name': 'tom3'})
            self.assertEqual(len(users), 2)
            self.assertEqual(users[0]['name'], 'tom3')
            self.assertEqual(users[1]['name'], 'tom3')
예제 #10
0
    def feeTaken():
        request = app.current_request
        data = request.json_body
        print(data)

        token = Database.find_one("Token", {"address": data["token"]})
        ownerUser = Database.find_one("User", {'address': data["owner"]})
        if not ownerUser:
            raise NotFoundError('user not found with address {}'.format(
                data["owner"]))

        value = data['value']

        ownerBalance = Database.find_one("TokenBalance", {
            'userId': ownerUser['id'],
            "tokenId": token["id"]
        },
                                         insert=True)
        if 'balance' not in ownerBalance: ownerBalance['balance'] = '0'
        if not ownerBalance['balance']: ownerBalance['balance'] = '0'
        newOwnerBalance = int(float(ownerBalance['balance'])) + int(
            float(value))
        ownerBalance = Database.update("TokenBalance",
                                       {"id": ownerBalance["id"]},
                                       {"balance": newOwnerBalance},
                                       return_updated=True)[0]

        return {"message": "Fee taken"}
예제 #11
0
  def trades_delete(tradeId):
    request = app.current_request
    data = request.json_body
    trade = Database.find_one("Trade", {"id": int(tradeId)})
    if not trade: raise NotFoundError("trade not found with id {}".format(tradeId))

    trade = Database.update("Trade", {"id": int(tradeId)}, {'state': 3}, return_updated=True)[0]
    # Socket, should be pushing to a message queue of some kind
    r = passWithoutError(requests.post)(socket_uri + "trade-update", data=toObject(trade))
    return toObject(trade)
예제 #12
0
  def orders_complete():
    request = app.current_request
    data = request.json_body
    order = Database.find_one("Order", {"hash": data["orderHash"]})

    # set order state to complete
    Database.update("Order", {"id": order["id"]}, {"state": 1})

    # set state to all trade as verified
    orderTrades = Database.find("OrderTrade", {"orderId": order["id"]})
    tradeIds = [o['tradeId'] for o in orderTrades]
    tradeQuery = [[('id','=',tradeId)] for tradeId in tradeIds]
    Database.update("Trade", tradeQuery, {'state': 2})

    # Here I need to check if all orders are complete for the day
    executionDate = order["executionDate"]
    incompleteOrders = Database.find("Order", {"state": 0, "executionDate": executionDate, "tokenId": order["tokenId"]})
    if len(incompleteOrders):
      # There are still orders waiting to complete
      print("There are still orders waiting to complete")
      return {"message": "Order completed"}

    # Here I need to calculate the AUM
    # find the token
    token = Database.find_one("Token", {"id": order["tokenId"]})
    print(token['address'])
    tokenContract = Web3Helper.getContract("ETT.json", token['address'])

    tokenHoldingsObject = Database.find_one("TokenHoldings", {"tokenId": token["id"]})
    tokenHoldings = Database.find("TokenHolding", {"tokenHoldingsId": tokenHoldingsObject["id"]})

    newAUM = 0
    for tokenHolding in tokenHoldings:
      securityTimestamp = Database.find_one('SecurityTimestamp', {'securityId': tokenHolding["securityId"]}, order_by='-createdAt')
      newAUM += securityTimestamp['price'] * tokenHolding['securityAmount']

    executionDateString = arrow.get(executionDate).format('YYYY-MM-DD')

    tx = Web3Helper.transact(tokenContract, 'endOfDay', executionDateString)
    # tx = b''
    print({"message": "AUM updated", "AUM": newAUM, "hash": tx.hex()})
    return {"message": "AUM updated", "AUM": newAUM, "hash": tx.hex()}
예제 #13
0
    def tokens_nav_update():
        print('\n\n\n\n')
        request = app.current_request
        data = request.json_body
        token = Database.find_one("Token", {"address": data["token"]})
        time = data["time"]
        executionDate = arrow.get(time).format('YYYY-MM-DD')
        nav = Database.insert("NAVTimestamp", {
            "tokenId": token['id'],
            "price": data['value'],
            "executionDate": executionDate
        },
                              return_inserted=True)

        # First need to collect the trades
        print(token['id'])
        trades = Database.find("Trade", {"state": 1, "tokenId": token["id"]})
        print(trades)
        # Need to go through each trade and get the NAV+price
        supplyUpdate = 0
        for trade in trades:
            decryptedNominalAmount = Cryptor.decryptInput(
                trade['nominalAmount'], trade['sk'])
            amountInvested = int(decryptedNominalAmount.split(':')[1])
            price = Cryptor.decryptInput(trade['price'], trade['sk'])
            price = float(price)
            print("amountInvested: ", amountInvested)
            print("price: ", price)
            effectiveNAV = (1.0 + float(price) / 100) * nav['price']
            print("supplyUpdate", int(amountInvested * 1.0 / effectiveNAV))
            # supplyUpdate += int(amountInvested * math.pow(10, token['decimals']) / nav['price'])
            supplyUpdate += int(amountInvested *
                                math.pow(10, token['decimals']) / effectiveNAV)

        tokenContract = Web3Helper.getContract("ETT.json", token['address'])

        # Update trades to be ready for claiming
        tradeQuery = [[('id', '=', t['id'])] for t in trades]
        trades = Database.update("Trade",
                                 tradeQuery, {'state': 4},
                                 return_updated=True)
        for trade in trades:
            # Take funds
            takeFunds(trade)
        tx = Web3Helper.transact(
            tokenContract,
            'updateTotalSupply',
            supplyUpdate,
            '',  # we are ignoring this for now
            executionDate)
        # tx = b''
        print(tx.hex())

        return toObject(nav)
예제 #14
0
 def tokens_contract_update():
     request = app.current_request
     data = request.json_body
     Database.update(
         "Token", {"symbol": data["symbol"]}, {
             "address": Web3Helper.toChecksumAddress(data["tokenAddress"]),
         })
     token = Database.find_one("Token", {"symbol": data["symbol"]})
     owner = Database.find_one(
         "User", {"address": Web3Helper.toChecksumAddress(data["owner"])})
     tokenBalance = Database.find_one("TokenBalance", {
         "tokenId": token['id'],
         "userId": owner["id"]
     })
     if not tokenBalance:
         tokenBalance = Database.find_one("TokenBalance", {
             "tokenId": token['id'],
             "userId": owner["id"],
             "balance": data['initialAmount']
         },
                                          insert=True)
     return toObject(token)
예제 #15
0
  def orders_post():
    request = app.current_request
    data = request.json_body
    trades = data['trades']
    order = {
      "brokerId": request.user["id"],
      "signature": data["signature"],
      "tokenId": data["token"],
      "salt": data["salt"],
      "amount": data["amount"],
      "executionDate": data["executionDate"],
      "hash": data["hash"],
      "state": 0
    }

    order = Database.insert("Order", order)
    for orderHolding in data['orderHoldings']:
      security = Database.find_one("Security", {"id": orderHolding["securityId"]}, insert=True)
      amount = 1 if orderHolding["direction"] == "Buy" else -1
      amount *= int(orderHolding["amount"])
      orderHolding = {
        "securityId": security["id"],
        "orderId": order["id"],
        "amount": amount,
        "cost": int(orderHolding["cost"]) if "cost" in orderHolding else 0
      }
      orderHolding = Database.insert("OrderHolding", orderHolding, return_inserted=True)

    for trade in trades:
      Database.update("Trade", {"id": trade["id"]},{"sk": trade["sk"]})
      orderTrade = {
        "orderId": order["id"],
        "tradeId": trade["id"]
      }
      orderTrade = Database.insert("OrderTrade", orderTrade, return_inserted=True)

    return toObject(order)
예제 #16
0
    def truelayer_callback():
        request = app.current_request
        code = request.query_params['code']
        nonce = request.query_params['state']
        user = Database.find_one("User", {'nonce': nonce})
        if not user: raise NotFoundError('user not found')
        user = Database.update('User', {"id": user["id"]},
                               TL.get_access_token(user, code),
                               return_updated=True)[0]
        accounts = TL.get_accounts(user)
        if not len(accounts): raise NotFoundError('No accounts found for user')

        # update the permissions contract
        # Web3Helper.transact(permissions_contract,'setAuthorized',Web3Helper.toChecksumAddress(user['address']),1)

        return Response(
            body=None,
            status_code=302,
            headers={"Location": "{}investor/profile".format(front_end_url)})
예제 #17
0
def createToken(data):
    owner = None
    ownerId = data["ownerId"] if "ownerId" in data else None
    if not ownerId:
        owner = Database.find_one("User", {"address": Web3Helper.account()})
        ownerId = owner["id"]
    else:
        owner = Database.find_one("User", {"id": ownerId})

    if not owner: raise NotFoundError('No user found')

    token_data = {
        "fundId": data["fundId"],
        "decimals": data["decimals"],
        "symbol": data["symbol"],
        "cutoffTime": int(data["cutoffTime"]),
        "fee": int(data["fee"]),
        "ownerId": ownerId,
        "name": data["name"],
        "totalSupply": data["initialAmount"],
        "incomeCategory": data["incomeCategory"],
        "minimumOrder": data["minimumOrder"],
        "currency": data["minimumOrder"],
    }

    if "fundId" in data: token_data["fundId"] = data["fundId"]

    # Check if a token with the same symbol already exists
    symbolToken = Database.find_one("Token", {"symbol": token_data["symbol"]})
    if (symbolToken): raise ForbiddenError("Already a token with this symbol")

    token = Database.find_one("Token", token_data, insert=True)

    tokenHoldings = Database.find_one(
        "TokenHoldings", {
            "tokenId": token['id'],
            "executionDate": str(datetime.today().date())
        },
        insert=True)

    if 'nav' in data:
        # Create a NAV timestamp
        executionDate = arrow.now().format('YYYY-MM-DD')
        Database.insert(
            "NAVTimestamp", {
                "tokenId": token['id'],
                "price": data['nav'],
                "executionDate": executionDate
            })

    holdings = []

    if 'holdings' in data:
        for holding in data['holdings']:
            # get the correct security
            security = Database.find_one("Security",
                                         {"symbol": holding["symbol"]})
            if (security):
                Database.update("Security", {"id": security["id"]}, {
                    "name": holding["name"],
                    "currency": holding["currency"],
                    "country": holding["country"],
                    "sector": holding["sector"],
                    "class": holding["class"]
                })
            else:
                security = Database.find_one("Security", {
                    "symbol": holding["symbol"],
                    "name": holding["name"],
                    "currency": holding["currency"],
                    "country": holding["country"],
                    "sector": holding["sector"],
                    "class": holding["class"]
                },
                                             insert=True)

            price = holding['price'] if 'price' in holding else '0'
            securityTimestamp = Database.find_one('SecurityTimestamp', {
                'securityId': security["id"],
                'price': price
            },
                                                  order_by='-createdAt',
                                                  insert=True)
            tokenHolding = Database.find_one(
                "TokenHolding", {
                    "securityId": security["id"],
                    "securityAmount": holding["amount"],
                    "tokenHoldingsId": tokenHoldings["id"]
                },
                insert=True)
            holdings.append(tokenHolding)

    holdingsString = createHoldingsString(holdings)

    try:
        tx = Web3Helper.transact(
            token_factory_contract,
            'createETT',
            token_data["name"],
            token_data["decimals"],
            token_data["symbol"],
            int(data["initialAmount"]),
            holdingsString,
            token_data["cutoffTime"],
            token_data["fee"],
            Web3Helper.toChecksumAddress(owner['address']),
        )
        print(tx.hex())
    except Exception as e:
        print(e)
        pass
예제 #18
0
def refresh_user_token(user):
    return Database.update('User', {"id": user["id"]},
                           TL.get_refresh_token(user),
                           return_updated=True)[0]
예제 #19
0
 def trades_funds_transfered():
   request = app.current_request
   data = request.json_body
   tradeHash = data['tradeHash']
   trade = Database.update("Trade", {"hash": tradeHash}, {'state': 5})
   return toObject(trade)