def test_conflict(self): input1 = os.urandom(32) payment1 = PaymentTransaction() payment1.input = input1 payment1.number = 0 payment1.outputs = [os.urandom(32), os.urandom(32)] payment1.amounts = [123, 999] payment1_hash = payment1.get_hash() # trying to spend the same input payment2 = PaymentTransaction() payment2.input = input1 payment2.number = 0 payment2.outputs = [os.urandom(32), os.urandom(32)] payment2.amounts = [1, 1] spent, unspent = Resolver.resolve( [[payment1, payment2]] ) #TODO is it okay that conflicting transactions are in the same block #zero input of random transaction should be marked as spent self.assertEqual(len(spent), 1) self.assertEqual(spent[0].tx, input1) self.assertEqual(spent[0].number, 0) #transaction spending the same output is rejected self.assertEqual(len(unspent), 2) self.assertIn(Entry(payment1_hash, 0), unspent) self.assertIn(Entry(payment1_hash, 1), unspent)
def test_simple(self): input1 = os.urandom(32) payment1 = PaymentTransaction() payment1.input = input1 payment1.number = 0 payment1.outputs = [os.urandom(32), os.urandom(32)] payment1.amounts = [123, 999] payment1_hash = payment1.get_hash() output3 = os.urandom(32) output4 = os.urandom(32) payment2 = PaymentTransaction() payment2.input = payment1_hash payment2.number = 0 payment2.outputs = [output3, output4] payment2.amounts = [555, 234] payment2_hash = payment2.get_hash() spent, unspent = Resolver.resolve([[payment1], [payment2]]) #zero input of random transaction should be marked as spent self.assertEqual(len(spent), 1) self.assertEqual(spent[0].tx, input1) self.assertEqual(spent[0].number, 0) #zero output of payment1 tx is spent by payment2, so only 3 unspent outputs left here self.assertEqual(len(unspent), 3) self.assertIn(Entry(payment1_hash, 1), unspent) self.assertIn(Entry(payment2_hash, 0), unspent) self.assertIn(Entry(payment2_hash, 1), unspent)
def create_payment(input, number, outputs, amounts): tx = PaymentTransaction() tx.input = input tx.number = number tx.outputs = outputs tx.amounts = amounts return tx
def test_payment_pack_unpack(self): original = PaymentTransaction() original.input = os.urandom(32) original.number = 1 original.outputs = [os.urandom(32), os.urandom(32)] original.amounts = [123, 999] raw = original.pack() restored = PaymentTransaction() restored.parse(raw) self.assertEqual(original.get_hash(), restored.get_hash())
def test_add_outputs(self): output1 = os.urandom(32) output2 = os.urandom(32) payment = PaymentTransaction() payment.input = COINBASE_IDENTIFIER payment.number = 1 payment.outputs = [output1, output2] payment.amounts = [123, 999] payment_hash = payment.get_hash() utxo = Utxo() utxo.add(payment) self.assertIn(payment_hash, utxo.utxo) self.assertEqual(len(utxo.utxo[payment_hash]), 2) self.assertEqual(utxo.utxo[payment_hash][0], 123) self.assertEqual(utxo.utxo[payment_hash][1], 999)
def test_ignore_coinbase(self): block_reward = TransactionFactory.create_block_reward( os.urandom(32), 0) payment = PaymentTransaction() payment.input = block_reward.get_hash() payment.number = 0 payment.outputs = [os.urandom(32), os.urandom(32)] payment.amounts = [129, 23423] spent, unspent = Resolver.resolve([[block_reward, payment]]) #nothing spent since block reward just creates outputs self.assertEqual(len(spent), 0) #block reward was split in two ouputs by payment transaction self.assertEqual(len(unspent), 2) self.assertIn(Entry(payment.get_hash(), 0), unspent) self.assertIn(Entry(payment.get_hash(), 1), unspent)
def test_spend_input(self): prev_tx = os.urandom(32) utxo = Utxo() utxo.utxo[prev_tx] = { 0 : 300 } # predefine utxo payment = PaymentTransaction() payment.input = prev_tx payment.number = 0 payment.outputs = [os.urandom(32), os.urandom(32)] payment.amounts = [149, 151] utxo.add(payment) # spend it payment_hash = payment.get_hash() self.assertNotIn(prev_tx, utxo.utxo) self.assertIn(payment_hash, utxo.utxo) self.assertEqual(utxo.utxo[payment_hash][0], 149) self.assertEqual(utxo.utxo[payment_hash][1], 151)