Учебники

Python Blockchain — класс транзакций

В этой главе давайте создадим класс Transaction, чтобы клиент мог кому-то отправлять деньги. Обратите внимание, что клиент может быть как отправителем, так и получателем денег. Когда вы хотите получить деньги, другой отправитель создаст транзакцию и укажет в ней ваш публичный адрес. Мы определяем инициализацию класса транзакции следующим образом:

def __init__(self, sender, recipient, value):
   self.sender = sender
   self.recipient = recipient
   self.value = value
   self.time = datetime.datetime.now()

Метод init принимает три параметра — открытый ключ отправителя, открытый ключ получателя и отправляемую сумму. Они хранятся в переменных экземпляра для использования другими методами. Кроме того, мы создаем еще одну переменную для хранения времени транзакции.

Затем мы напишем служебный метод to_dict, который объединяет все четыре вышеупомянутые переменные экземпляра в объекте словаря. Это просто для того, чтобы вся информация о транзакции была доступна через одну переменную.

Как вы знаете из предыдущего урока, первый блок в блокчейне — это блок Genesis . Блок Genesis содержит первую транзакцию, инициированную создателем блокчейна. Личность этого человека может храниться в секрете, как в случае с биткойнами. Поэтому, когда создается эта первая транзакция, создатель может просто отправить свою личность как Genesis . Таким образом, при создании словаря мы проверяем, является ли отправитель Genesis, и если это так, мы просто присваиваем некоторое строковое значение переменной-идентификатору; иначе мы присваиваем идентификатор отправителя переменной идентификатора .

if self.sender == "Genesis":
   identity = "Genesis"
else:
   identity = self.sender.identity

Мы строим словарь, используя следующую строку кода

return collections.OrderedDict({
   'sender': identity,
   'recipient': self.recipient,
   'value': self.value,
   'time' : self.time})

Весь код для метода to_dict показан ниже —

def to_dict(self):
   if self.sender == "Genesis":
      identity = "Genesis"
   else:
      identity = self.sender.identity

   return collections.OrderedDict({
      'sender': identity,
      'recipient': self.recipient,
      'value': self.value,
      'time' : self.time})

Наконец, мы подпишем этот объект словаря, используя закрытый ключ отправителя. Как и прежде, мы используем встроенную PKI с алгоритмом SHA. Сгенерированная подпись декодируется, чтобы получить представление ASCII для печати и сохранения ее в нашей цепочке блоков. Код метода sign_transaction показан здесь —

def sign_transaction(self):
   private_key = self.sender._private_key
   signer = PKCS1_v1_5.new(private_key)
   h = SHA.new(str(self.to_dict()).encode('utf8'))
   return binascii.hexlify(signer.sign(h)).decode('ascii')

Теперь мы проверим этот класс транзакций .

Класс тестовой транзакции

Для этого мы создадим двух пользователей, называемых Динеш и Рамеш . Динеш отправит 5 TPCoins Рамешу. Для этого сначала мы создаем клиентов с именами Dinesh и Ramesh.

Dinesh = Client()
Ramesh = Client()

Помните, что при создании экземпляра класса Client будут созданы открытый и закрытый ключи, уникальные для клиента. Поскольку Динеш отправляет платеж Рамешу, ему понадобится открытый ключ Рамеша, полученный с помощью свойства идентификатора клиента.

Таким образом, мы создадим экземпляр транзакции, используя следующий код —

t = Transaction(
   Dinesh,
   Ramesh.identity,
   5.0
)

Обратите внимание, что первым параметром является отправитель, вторым параметром является открытый ключ получателя, а третьим параметром является сумма, подлежащая передаче. Метод sign_transaction извлекает закрытый ключ отправителя из первого параметра для подписания транзакции.

После создания объекта транзакции вы подпишите его, вызвав его метод sign_transaction . Этот метод возвращает сгенерированную подпись в формате для печати. Мы генерируем и печатаем подпись, используя следующие две строки кода:

signature = t.sign_transaction()
print (signature) 

Когда вы запустите приведенный выше код, вы увидите вывод, похожий на этот —

7c7e3c97629b218e9ec6e86b01f9abd8e361fd69e7d373c38420790b655b9abe3b575e343c7
13703ca1aee781acd7157a0624db3d57d7c2f1172730ee3f45af943338157f899965856f6b0
0e34db240b62673ad5a08c8e490f880b568efbc36035cae2e748f1d802d5e8e66298be826f5
c6363dc511222fb2416036ac04eb972

Теперь, когда наша базовая инфраструктура создания клиента и транзакции готова, у нас теперь будет несколько клиентов, выполняющих несколько транзакций, как в реальной жизни.