Example #1
0
def get_handler(**args):
    address = args.get('user_did').lstrip(forge_did.PREFIX)
    event_address = args.get('request').args.get('event_address')

    pk = forge_utils.multibase_b58decode(args.get('user_pk'))

    acquire_asset_tx, _ = forge.rpc.build_acquire_asset_tx(
        to=event_address,
        spec_datas=[{
            "id": str(uuid.uuid4())
        }],
        type_url='ec:s:general_ticket',
        proto_lib=protos)

    tx = forge_utils.build_unsigned_tx(itx=forge_utils.encode_to_any(
        'fg:t:acquire_asset', acquire_asset_tx),
                                       chain_id=forge.config.chain_id,
                                       address=address,
                                       pk=pk)

    return {
        'request_type': 'signature',
        'workflow': 'buy-ticket',
        'tx': tx,
        'description': 'Confirm Purchase of Ticket',
    }
Example #2
0
 def to_state(self):
     event_info = protos.EventInfo(
         title=self.event_info.title,
         description=self.event_info.description,
         total=self.event_info.total,
         start_time=self.event_info.start_time,
         end_time=self.event_info.end_time,
         ticket_price=int(self.event_info.ticket_price),
         remaining=self.remaining,
         tickets=self.tickets,
         participants=self.participants,
         location=self.event_info.location,
         consume_tx=self.event_info.consume_tx,
         img_url=self.event_info.img_url,
     )
     state = protos.AssetState(
         address=self.address,
         owner=self.owner,
         moniker=self.moniker,
         readonly=self.readonly,
         transferrable=self.transferrable,
         ttl=self.ttl,
         consumed_time=self.consumed_time,
         stake=self.stake,
         context=self.context,
         data=forge_utils.encode_to_any(
             'ec:s:event_info',
             event_info,
         ),
     )
     return state
Example #3
0
def post_handler(**args):
    wallet_res = args.get('wallet_res')
    asset_address = wallet_res.get_asset_address()
    ticket = controllers.get_ticket_state(asset_address)
    new_tx = controllers.update_tx_multisig(tx=forge_utils.parse_to_proto(
        forge_utils.multibase_b58decode(ticket.consume_tx),
        forge_protos.Transaction),
                                            signer=wallet_res.get_address(),
                                            pk=wallet_res.get_user_pk(),
                                            data=forge_utils.encode_to_any(
                                                'fg:x:address',
                                                asset_address,
                                            ))
    token = args.get('token')
    utils.mark_token_status(token, 'succeed')
    params = {
        'tx':
        new_tx,
        'url':
        utils.server_url(
            f'/api/did/consume_ticket/consume?_t_={token}&ticket_address={ticket.address}'
        ),
        'description':
        'Confirm to use the ticket.',
        'workflow':
        'use-ticket',
        'user_did':
        wallet_res.get_address()
    }
    res = utils.send_did_request(request_type='signature',
                                 **params,
                                 **args.get('app_params'))
    logger.debug(f"POST Response: {res}")

    return json.loads(res)
Example #4
0
def gen_consume_tx(wallet, token=None):
    consume_itx = forge_protos.ConsumeAssetTx(issuer=wallet.address)
    logger.debug(str(forge.rpc))
    tx = forge.rpc.build_signed_tx(itx=forge_utils.encode_to_any(
        'fg:t:consume_asset', consume_itx),
                                   wallet=wallet,
                                   token=token)
    return tx.SerializeToString()
Example #5
0
    def gen_ticket_holder(self, ticket_id):
        create_asset_ticket = create_asset_ticket_info(
            ticket_id,
            self.address,
        )

        ticket__address = did.get_asset_address(
            did_address=self.wallet.address,
            itx=create_asset_ticket,
        )
        ticket_create_tx = forge_rpc.create_tx(
            itx=forge_utils.encode_to_any(
                type_url='fg:t:create_asset',
                data=create_asset_ticket,
            ),
            from_address=self.wallet.address,
            token=self.token,
        )

        exchange_tx = gen_exchange_tx(
            self.ticket_price,
            ticket__address,
            self.address,
        )
        ticket_exchange_tx = forge_rpc.create_tx(
            itx=forge_utils.encode_to_any('fg:t:exchange', exchange_tx),
            from_address=self.wallet.address,
            wallet=self.wallet,
            token=self.token,
        )

        ticket_holder = protos.TicketHolder(
            ticket_create=ticket_create_tx.tx,
            ticket_exchange=ticket_exchange_tx.tx,
            id=ticket_id,
            address=ticket__address,
        )
        return ticket_holder
Example #6
0
def create_asset_ticket_info(id, event_address):
    ticket_info = protos.TicketInfo(
        id=id,
        event_address=event_address,
        is_used=False,
    )
    ticket_itx = protos.CreateAssetTx(
        data=forge_utils.encode_to_any(
            'ec:s:ticket_info',
            ticket_info,
        ),
        readonly=True,
    )
    return ticket_itx
Example #7
0
    def consume_mobile(self, consume_tx, address, signature, user_pk):
        multisig_data = forge_utils.encode_to_any(
            'fg:x:address',
            self.address,
        )

        tx = utils.update_tx_multisig(
            tx=consume_tx,
            signer=address,
            signature=signature,
            pk=user_pk,
            data=multisig_data,
        )
        return forge_rpc.send_tx(tx)
Example #8
0
def gen_poke_tx(address, pk):
    poke_itx = forge_protos.PokeTx(
            date=str(
                    datetime.now().date()),
            address='zzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzz',
    )
    itx = forge_utils.encode_to_any('fg:t:poke', poke_itx)
    params = {
        'from': address,
        'chain_id': config.chain_id,
        'nonce': 0,
        'pk': pk,
        'itx': itx
    }
    return forge_protos.Transaction(**params)
Example #9
0
def require_asset(event_address):
    try:
        event = models.get_event_factory(event_address)

        if request.method == 'GET':
            lib.parse_request_get(request, 'require-asset')
            params = {
                'url':
                url_for('api_mobile.require_asset',
                        event_address=event_address),
                'target':
                event.title,
            }
            response = controllers.require_asset_consume(**params)
            return response

        if request.method == 'POST':
            wallet_res = lib.parse_request_post(request, 'require-asset')

            if not wallet_res:
                return lib.error("Error in parsing wallet data.")

            asset_address = wallet_res.get_asset_address()
            if not asset_address:
                return lib.error("Please provide an asset address.")

            new_tx = utils.update_tx_multisig(tx=event.consume_tx,
                                              signer=wallet_res.get_address(),
                                              pk=wallet_res.get_user_pk(),
                                              data=forge_utils.encode_to_any(
                                                  'fg:x:address',
                                                  asset_address,
                                              ))

            params = {
                'did': wallet_res.get_address(),
                'tx': new_tx,
                'url': url_for('api_mobile.consume',
                               ticket_address=asset_address),
            }
            return controllers.require_sig_consume(**params)

    except Exception as e:
        logger.error(e, exc_info=True)
        return lib.error("Exception in requesting asset.")
Example #10
0
 def gen_consume_tx(self):
     consume_itx = protos.ConsumeAssetTx(issuer=self.wallet.address)
     res = forge_rpc.create_tx(
         itx=forge_utils.encode_to_any(
             'fg:t:consume_asset',
             consume_itx,
         ),
         from_address=self.wallet.address,
         wallet=self.wallet,
         token=self.token,
     )
     if res.code != 0 or res.tx is None:
         logger.error(u'Fail to generate consume tx for event.')
         return None
     else:
         logger.debug(
             u"Consume tx generated for event {}".format(self.title), )
         return res.tx
Example #11
0
 def create(self):
     logger.debug(u"Creating event...")
     if not self.consume_tx:
         logger.error(u"Consume tx not generated!")
     event_info = protos.EventInfo(
         title=self.title,
         total=self.total,
         start_time=self.start_time,
         end_time=self.end_time,
         ticket_price=self.ticket_price,
         location=self.location,
         tickets=[],
         participants=[],
         remaining=self.total,
         consume_tx=self.consume_tx,
         img_url=self.img_url,
     )
     create_asset_itx = protos.CreateAssetTx(data=forge_utils.encode_to_any(
         self.type_url, event_info), )
     event_address = did.get_asset_address(did_address=self.wallet.address,
                                           itx=create_asset_itx)
     logger.debug(
         u"Event address has been calculated: {}".format(event_address), )
     res = forge_rpc.create_asset(
         self.type_url,
         event_info,
         self.wallet,
         self.token,
     )
     if res.code != 0 or not res.hash:
         logger.error(res)
     else:
         logger.info(
             u"Event '{0}' has been created successfully by tx {"
             "1}!".format(
                 self.title,
                 res.hash,
             ), )
         return event_address
Example #12
0
 def to_state(self):
     ticket_info = protos.TicketInfo(
         id=self.id,
         event_address=self.event_address,
         is_used=self.is_used,
     )
     state = protos.AssetState(
         address=self.address,
         owner=self.owner,
         moniker=self.moniker,
         readonly=self.readonly,
         transferrable=self.transferrable,
         ttl=self.ttl,
         consumed_time=self.consumed_time,
         stake=self.stake,
         context=self.context,
         data=forge_utils.encode_to_any(
             'ec:s:ticket_info',
             ticket_info,
         ),
     )
     logger.debug("ticket state about to update...")
     logger.debug("state: {}".format(state))
     return state
print(f"operator's balance is {rpc.get_account_balance(op.wallet.address)}")
print(
    f"manufacturer's balance is {rpc.get_account_balance(ma.wallet.address)}")
print(f"supplier's balance is {rpc.get_account_balance(su.wallet.address)}")
print(f"location's balance is {rpc.get_account_balance(lo.wallet.address)}")

print("sending a tx...")

# send a tx
itx = AggregateTx(sku=sku,
                  value=value,
                  time=time,
                  operator=op.wallet.address,
                  manufacturer=ma.wallet.address,
                  supplier=su.wallet.address,
                  location=lo.wallet.address)
itx2 = utils.encode_to_any(type_url="fg:t:aggregate", data=itx)
print("itx2 is ", itx2)
res = rpc.send_itx(tx=itx2, wallet=vm.wallet, token=vm.token, nonce=0)
print("res is ", res)

# check tx
sleep(3)
print(f"TX verify: {rpc.is_tx_ok(res.hash)}")

print(f"operator's balance is {rpc.get_account_balance(op.wallet.address)}")
print(
    f"manufacturer's balance is {rpc.get_account_balance(ma.wallet.address)}")
print(f"supplier's balance is {rpc.get_account_balance(su.wallet.address)}")
print(f"location's balance is {rpc.get_account_balance(lo.wallet.address)}")
Example #14
0
def buy_ticket(event_address):
    try:
        if request.method == 'GET':

            wallet = lib.parse_request_get(request, 'buy-ticket')

            acquire_asset_tx, _ = forge_rpc.build_acquire_asset_tx(
                to=event_address,
                spec_datas=[{
                    "id": str(uuid.uuid4())
                }],
                type_url='ec:s:general_ticket',
                proto_lib=protos)

            unsigned_tx = forge_rpc.build_unsigned_tx(
                forge_utils.encode_to_any('fg:t:acquire_asset',
                                          acquire_asset_tx), wallet, 2)

            did_request_params = {
                'did':
                wallet.did,
                'tx':
                unsigned_tx,
                'url':
                url_for('api_mobile.buy_ticket', event_address=event_address),
            }
            response = controllers.require_sig_buy_ticket(**did_request_params)

            logger.debug(f'did auth response: {response}')
            return response

        elif request.method == 'POST':
            wallet_res = lib.parse_request_post(request, 'mobile-buy-ticket')
            if not wallet_res:
                return lib.error("Error in parsing wallet data.")

            participant_state = models.get_participant_state(
                wallet_res.get_address())
            if not participant_state:
                return lib.error(
                    f"user {wallet_res.get_address()} doesn't exist.")

            ticket_address, tx_hash = controllers.buy_ticket_mobile(
                wallet_res.get_origin_tx(),
                wallet_res.get_signature(),
            )
            tx = wallet_res.get_origin_tx().__deepcopy__()
            tx.signature = wallet_res.get_signature()

            if ticket_address and tx_hash:
                logger.info(f"Ticket {ticket_address} is bought successfully.")

                return lib.ok({
                    'ticket': ticket_address,
                    'hash': tx_hash,
                    'tx': utils.base58_encode_tx(tx)
                })
            else:
                return lib.error('Whoops. Something is wrong :(')
    except Exception as e:
        logger.error(e, exc_info=True)
        return lib.error('Exception in buying ticket.')
async def send(context):
    '''
    Get a ramdon element from each category, and current time to generate a bill for simulation.
    Send this bill on the chain through AggregateTx
    ------
    Args:
        context(dict): all necessary info (items, vending_machines, batch)

    Output:
        send aggregate tx on the chain
    '''

    # put random info together to generate a random bill

    item_unit = choice(context['items'])
    vm_unit = choice(context['vms'])

    op = vm_unit['operator']
    ma = vm_unit['manufacturer']
    su = item_unit['supplier']
    lo = vm_unit['location']

    # get current time
    curr_time = Timestamp()
    curr_time.GetCurrentTime()

    # get item's value
    value = utils.int_to_biguint(utils.to_unit(item_unit['value']))

    logger.debug("before tx...")
    logger.debug(
        f"{op['moniker']}'s balance is {rpc.get_account_balance(op['address'])}"
    )
    logger.debug(
        f"{ma['moniker']}'s balance is {rpc.get_account_balance(ma['address'])}"
    )
    logger.debug(
        f"{su['moniker']}'s balance is {rpc.get_account_balance(su['address'])}"
    )
    logger.debug(
        f"{lo['moniker']}'s balance is {rpc.get_account_balance(lo['address'])}"
    )

    # group a wallet object for vending_machine
    vm_wallet = protos.WalletInfo(pk=utils.multibase_b64decode(vm_unit['pk']),
                                  sk=utils.multibase_b64decode(vm_unit['sk']),
                                  address=vm_unit['address'])

    # creat tx
    itx = AggregateTx(sku=item_unit['sku'],
                      value=value,
                      time=curr_time,
                      operator=op['address'],
                      manufacturer=ma['address'],
                      supplier=su['address'],
                      location=lo['address'])
    itx2 = utils.encode_to_any(type_url="fg:t:aggregate", data=itx)

    logger.info(
        f"batch {context['batch']} is sending tx... ---> value: {item_unit['value']}, from: {vm_unit['address']}, operator: {op['address']}, manufacturer: {ma['address']}, supplier: {su['address']}, location: {lo['address']}"
    )
    res = rpc.send_itx(tx=itx2, wallet=vm_wallet, nonce=0)

    await asyncio.sleep(5)
    logger.info(f"verify tx: {rpc.is_tx_ok(res.hash)}")

    logger.debug(
        f"{op['moniker']}'s balance is {rpc.get_account_balance(op['address'])}"
    )
    logger.debug(
        f"{ma['moniker']}'s balance is {rpc.get_account_balance(ma['address'])}"
    )
    logger.debug(
        f"{su['moniker']}'s balance is {rpc.get_account_balance(su['address'])}"
    )
    logger.debug(
        f"{lo['moniker']}'s balance is {rpc.get_account_balance(lo['address'])}"
    )