Blockchain Python - Criando Mineiros

Para habilitar a mineração, precisamos desenvolver uma função de mineração. A funcionalidade de mineração precisa gerar um resumo em uma determinada string de mensagem e fornecer uma prova de trabalho. Vamos discutir isso neste capítulo.

Função Message Digest

Vamos escrever uma função de utilidade chamada sha256 para criar um resumo de uma determinada mensagem -

def sha256(message):
return hashlib.sha256(message.encode('ascii')).hexdigest()

o sha256 função leva um message como um parâmetro, o codifica para ASCII, gera um resumo hexadecimal e retorna o valor ao chamador.

Função Mineira

Agora desenvolvemos o minefunção que implementa nossa própria estratégia de mineração. Nossa estratégia, nesse caso, seria gerar um hash na mensagem fornecida, prefixado com um determinado número de 1s. O número de 1 fornecido é especificado como um parâmetro paramine função especificada como o nível de dificuldade.

Por exemplo, se você especificar um nível de dificuldade de 2, o hash gerado em uma determinada mensagem deve começar com dois 1s - como 11xxxxxxxx. Se o nível de dificuldade for 3, o hash gerado deve começar com três 1's - como 111xxxxxxxx. Dados esses requisitos, desenvolveremos agora a função de mineração conforme mostrado nas etapas fornecidas a seguir.

Passo 1

A função de mineração leva dois parâmetros - a mensagem e o nível de dificuldade.

def mine(message, difficulty=1):

Passo 2

O nível de dificuldade deve ser maior ou igual a 1, garantimos isso com a seguinte declaração assert -

assert difficulty >= 1

etapa 3

Nós criamos um prefix variável usando o nível de dificuldade definido.

prefix = '1' * difficulty

Observe que se o nível de dificuldade for 2, o prefixo será “11” e se o nível de dificuldade for 3, o prefixo será “111” e assim por diante. Verificaremos se este prefixo existe no resumo gerado da mensagem. Para digerir a mensagem em si, usamos as duas linhas de código a seguir -

for i in range(1000):
   digest = sha256(str(hash(message)) + str(i))

Continuamos adicionando um novo número iao hash da mensagem em cada iteração e gere um novo resumo da mensagem combinada. Como entrada para osha256 a função muda em cada iteração, o digesto valor também mudaria. Nós verificamos se estedigest o valor está acima do definido prefix.

if digest.startswith(prefix):

Se a condição for satisfeita, encerraremos o for fazer um loop e retornar o digest valor para o chamador.

O todo mine o código é mostrado aqui -

def mine(message, difficulty=1):
   assert difficulty >= 1
   prefix = '1' * difficulty
   for i in range(1000):
      digest = sha256(str(hash(message)) + str(i))
      if digest.startswith(prefix):
         print ("after " + str(i) + " iterations found nonce: "+ digest)
      return digest

Para sua compreensão, adicionamos o print instrução que imprime o valor de resumo e o número de iterações necessárias para atender à condição antes de retornar da função.

Teste de função de mineração

Para testar nossa função de mineração, basta executar a seguinte instrução -

mine ("test message", 2)

Ao executar o código acima, você verá uma saída semelhante a esta abaixo -

after 138 iterations found nonce:
11008a740eb2fa6bf8d55baecda42a41993ca65ce66b2d3889477e6bfad1484c

Observe que o resumo gerado começa com “11”. Se você alterar o nível de dificuldade para 3, o resumo gerado começará com “111” e, claro, provavelmente exigirá mais número de iterações. Como você pode ver, um minerador com mais poder de processamento será capaz de minerar uma determinada mensagem antes. É assim que as mineradoras competem entre si para obter suas receitas.

Agora, estamos prontos para adicionar mais blocos ao nosso blockchain. Vamos aprender isso em nosso próximo capítulo.