生成创世区块并挖矿生成第二个区块

代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
package main

import (
"crypto/sha256"
"encoding/hex"
"fmt"
"strconv"
"time"
)

// Block represents each 'item' in the blockchain
type Block struct {
Index int
Timestamp string
Data string
Hash string
PrevHash string
Nonce int
Difficulty int
}

// Blockchain is a series of validated Blocks
var Blockchain []Block

// calculateHash is a simple SHA256 hashing function
func calculateHash(block Block) string {
record := strconv.Itoa(block.Index) + block.Timestamp + block.Data + block.PrevHash + strconv.Itoa(block.Nonce)
h := sha256.New()
h.Write([]byte(record))
hashed := h.Sum(nil)
return hex.EncodeToString(hashed)
}

// generateBlock creates a new block using previous block's hash
func generateBlock(oldBlock Block, Data string, Difficulty int) Block {
var newBlock Block

t := time.Now()

newBlock.Index = oldBlock.Index + 1
newBlock.Timestamp = t.String()
newBlock.Data = Data
newBlock.PrevHash = oldBlock.Hash
newBlock.Difficulty = Difficulty
newBlock.Hash = calculateHash(newBlock)

// Implement the Proof of Work (PoW)
for i := 0; ; i++ {
// hex := fmt.Sprintf("%x", i)
newBlock.Nonce = i
if !isHashValid(calculateHash(newBlock), newBlock.Difficulty) {
fmt.Println(calculateHash(newBlock), " do more work!")
continue
} else {
fmt.Println(calculateHash(newBlock), " work done!")
newBlock.Hash = calculateHash(newBlock)
break
}
}

return newBlock
}

// isHashValid checks if the hash meets the criteria defined by difficulty
func isHashValid(hash string, difficulty int) bool {
prefix := ""
for i := 0; i < difficulty; i++ {
prefix += "0"
}
return hash[:difficulty] == prefix
}

func main() {
// Set difficulty
difficulty := 4

// Create the genesis block
t := time.Now()
genesisBlock := Block{0, t.String(), "Genesis Block", "", "", 0, difficulty}
genesisBlock.Hash = calculateHash(genesisBlock)
Blockchain = append(Blockchain, genesisBlock)

// Add a new block
newBlock := generateBlock(genesisBlock, "Block #1", difficulty)
Blockchain = append(Blockchain, newBlock)

// Print the blockchain
for _, block := range Blockchain {
fmt.Printf("Index: %d\n", block.Index)
fmt.Printf("Timestamp: %s\n", block.Timestamp)
fmt.Printf("Data: %s\n", block.Data)
fmt.Printf("Hash: %s\n", block.Hash)
fmt.Printf("nonce:%d PrevHash: %s\n", block.Nonce, block.PrevHash)
fmt.Println()
}
}