Esempio n. 1
0
    async def post(self):
        config = self.config
        mongo = self.config.mongo
        body = json.loads(self.request.body.decode('utf-8'))
        try:
            fg = FastGraph.from_dict(0, body.get('txn'), raw=True)
            fg.verify()
        except:
            raise
            return 'invalid transaction', 400
        res = mongo.db.signed_transactions.find_one({'hash': body.get('hash')})
        if res:
            return 'no', 400
        try:
            rid = TU.generate_rid(config, body.get('bulletin_secret'))
            my_entry_for_relationship = GU().get_transaction_by_rid(
                rid,
                config.wif,
                rid=True,
                my=True,
                public_key=config.public_key)
            their_entry_for_relationship = GU().get_transaction_by_rid(
                rid,
                rid=True,
                raw=True,
                theirs=True,
                public_key=config.public_key)
            verified = verify_signature(
                base64.b64decode(body.get('bulletin_secret')),
                my_entry_for_relationship['relationship']
                ['their_username'].encode(),
                bytes.fromhex(their_entry_for_relationship['public_key']))
            if not verified:
                return 'no', 400
            verified = verify_signature(
                base64.b64decode(body.get('id')),
                body.get('hash').encode('utf-8'),
                bytes.fromhex(their_entry_for_relationship['public_key']))
            address = str(
                P2PKHBitcoinAddress.from_pubkey(
                    bytes.fromhex(their_entry_for_relationship['public_key'])))
            found = False
            for x in BU().get_wallet_unspent_transactions(
                    address, [body.get('input')]):
                if body.get('input') == x['id']:
                    found = True

            if not found:
                for x in BU().get_wallet_unspent_fastgraph_transactions(
                        address):
                    if body.get('input') == x['id']:
                        found = True

            if found:
                signature = mongo.db.signed_transactions.find_one({
                    'input':
                    body.get('input'),
                    'txn.public_key':
                    body['txn']['public_key']
                })
                if signature:
                    already_spent = mongo.db.fastgraph_transactions.find_one({
                        'txn.inputs.id':
                        body['input'],
                        'txn.public_key':
                        body['txn']['public_key']
                    })
                    if already_spent:
                        self.set_status(400)
                        self.write('already spent!')
                        self.finish()
                        return True
                    else:
                        signature['txn']['signatures'] = [
                            signature['signature']
                        ]
                        fastgraph = FastGraph.from_dict(0, signature['txn'])
                        try:
                            fastgraph.verify()
                        except Exception as e:
                            raise
                            return 'did not verify', 400
                        result = mongo.db.fastgraph_transactions.find_one(
                            {'txn.hash': fastgraph.hash})
                        if result:
                            return 'duplicate transaction found', 400
                        spent_check = mongo.db.fastgraph_transactions.find_one(
                            {
                                'txn.inputs.id': {
                                    '$in': [x.id for x in fastgraph.inputs]
                                }
                            })
                        if spent_check:
                            return 'already spent input', 400
                        fastgraph.save()
            else:
                return 'no transactions with this input found', 400
            if verified:
                transaction_signature = TU.generate_signature_with_private_key(
                    config.private_key, body.get('hash'))
                signature = {
                    'signature': transaction_signature,
                    'hash': body.get('hash'),
                    'bulletin_secret': body.get('bulletin_secret'),
                    'input': body.get('input'),
                    'id': body.get('id'),
                    'txn': body.get('txn')
                }
                mongo.db.signed_transactions.insert(signature)
                if '_id' in signature:
                    del signature['_id']
                self.render_as_json(signature, indent=4)
            else:
                return 'no', 400
        except Exception as e:
            raise
            self.render_as_json({'status': 'error', 'msg': e})
Esempio n. 2
0
    async def get(self):
        graph = self.get_base_graph()
        config = self.config
        address = self.get_query_argument('address')
        bulletin_secret = self.get_query_argument('bulletin_secret').replace(
            ' ', "+")
        amount_needed = self.get_query_argument('amount_needed', None)
        if amount_needed:
            amount_needed = int(amount_needed)
        rid = TU.generate_rid(config, bulletin_secret)

        unspent_transactions = [
            x for x in BU().get_wallet_unspent_transactions(address)
        ]
        spent_txn_ids = []

        for x in unspent_transactions:
            spent_txn_ids.extend([y['id'] for y in x['inputs']])

        unspent_fastgraph_transactions = [
            x for x in BU().get_wallet_unspent_fastgraph_transactions(address)
            if x['id'] not in spent_txn_ids
        ]
        spent_fastgraph_ids = []
        for x in unspent_fastgraph_transactions:
            spent_fastgraph_ids.extend([y['id'] for y in x['inputs']])
        regular_txns = []
        txns_for_fastgraph = []
        chain_balance = 0
        fastgraph_balance = 0
        for txn in unspent_transactions + unspent_fastgraph_transactions:
            if 'signatures' in txn and txn['signatures']:
                fastgraph = FastGraph.from_dict(0, txn)
                origin_fasttrack = fastgraph.get_origin_relationship(rid)
                if origin_fasttrack or (('rid' in txn and txn['rid'] == rid)
                                        or txn.get('requester_rid') == rid
                                        or txn.get('requested_rid') == rid):
                    txns_for_fastgraph.append(txn)
                    for output in txn['outputs']:
                        if output['to'] == address:
                            fastgraph_balance += int(output['value'])
                else:
                    regular_txns.append(txn)
                    for output in txn['outputs']:
                        if output['to'] == address:
                            chain_balance += int(output['value'])
            elif 'dh_public_key' in txn and txn['dh_public_key'] and (
                ('rid' in txn and txn['rid'] == rid)
                    or txn.get('requester_rid') == rid
                    or txn.get('requested_rid') == rid):
                txns_for_fastgraph.append(txn)
                for output in txn['outputs']:
                    if output['to'] == address:
                        fastgraph_balance += int(output['value'])
            else:
                regular_txns.append(txn)
                for output in txn['outputs']:
                    if output['to'] == address:
                        chain_balance += int(output['value'])

        wallet = {
            'chain_balance': chain_balance,
            'fastgraph_balance': fastgraph_balance,
            'balance': fastgraph_balance + chain_balance,
            'unspent_transactions': regular_txns,
            'txns_for_fastgraph': txns_for_fastgraph
        }
        self.render_as_json(wallet, indent=4)
Esempio n. 3
0
    async def post(self):
        config = self.config
        mongo = self.config.mongo
        kwargs = json.loads(self.request.body.decode('utf-8'))
        bulletin_secret = kwargs.get('bulletin_secret', '')
        username = kwargs.get('username', '')
        to = kwargs.get('to', '')

        if not bulletin_secret:
            return 'error: "bulletin_secret" missing', 400

        if not username:
            return 'error: "username" missing', 400

        if not to:
            return 'error: "to" missing', 400
        rid = TU.generate_rid(config, bulletin_secret)
        dup = mongo.db.blocks.find({'transactions.rid': rid})
        if dup.count():
            found_a = False
            found_b = False
            for txn in dup:
                if txn['public_key'] == config.public_key:
                    found_a = True
                if txn['public_key'] != config.public_key:
                    found_b = True
            if found_a and found_b:
                return json.dumps({
                    "success": False,
                    "status": "Already added"
                })

        miner_transactions = mongo.db.miner_transactions.find()
        mtxn_ids = []
        for mtxn in miner_transactions:
            for mtxninput in mtxn['inputs']:
                mtxn_ids.append(mtxninput['id'])

        checked_out_txn_ids = mongo.db.checked_out_txn_ids.find()
        for mtxn in checked_out_txn_ids:
            mtxn_ids.append(mtxn['id'])

        a = os.urandom(32).decode('latin1')
        dh_public_key = scalarmult_base(a).encode('latin1').hex()
        dh_private_key = a.encode('latin1').hex()

        transaction = TransactionFactory(
            block_height=BU().get_latest_block()['index'],
            bulletin_secret=bulletin_secret,
            username=username,
            fee=0.00,
            public_key=config.public_key,
            dh_public_key=dh_public_key,
            private_key=config.private_key,
            dh_private_key=dh_private_key,
            outputs=[{
                'to': to,
                'value': 0
            }])

        mongo.db.miner_transactions.insert(transaction.transaction.to_dict())
        """
        # TODO: integrate new socket/peer framework for transmitting txns

        job = Process(target=TxnBroadcaster.txn_broadcast_job, args=(transaction.transaction,))
        job.start()
        """

        self.render_as_json({"success": True})