Blockchain

Go로 만드는 블록체인 part 1 - Base of Blockchain

hou27 2021. 12. 9. 20:26

이제 본격적으로 GO를 이용하여 암호화폐를 구현해볼 것이다.

Type block, blockchain

block과 blockchain의 type을 선언하겠다.

type block struct {
	timeStamp int64 `validate:"required"`
	hash	  string `validate:"required"`
	prevHash  string `validate:"required"`
	data	  string `validate:"required"`
}

type blockchain struct {
	blocks []*block
}


time stamp
hash
previous hash
data

초기 단계에서의 블록은 위와 같은 요소를 가진다.
이전 포스트에서 다룬 typescript로 구현해본 blockchain의 block의 구조에서 약간만 수정했다.

그리고 blockchain은 당연하게도 block들이 모인 배열이 될 것이다.

Function AddBlock

// Add Blockchain
func (bc *blockchain) AddBlock(data string) {
	prevHash := bc.getPrevHash()
	newBlock := NewBlock(data, prevHash)

	isValidated := bc.validateStructure(*newBlock)

	if isValidated != nil {
		fmt.Println(isValidated)
	} else {
		bc.blocks = append(GetBlockchain().blocks, newBlock)
	}
}

새로운 블록을 추가하는 함수이다.

여기서 getPrevHash는

func (bc blockchain) getPrevHash() string {
	if len(GetBlockchain().blocks) > 0 {
		return GetBlockchain().blocks[len(GetBlockchain().blocks)-1].hash
	}
	return "First Block"
}

Genesis Block일 경우를 제외하고 이전 블록의 Hash값을 반환한다.

그렇게 얻은 이전 블록의 hash값과 data를 NewBlock에 넘겨주고
리턴받은 새로운 블록 객체를 blockchain에 추가한다.

Function NewBlock

func NewBlock(data string, prevHash string) *block {
	newblock := &block{time.Now().Unix(), "", prevHash, data}
	newblock.calculateHash()
	return newblock
}

새로운 블록을 준비해주는 함수이다.

block의 struct에 맞게
새로운 block 객체를 생성한 후

calculateHash를 통해
 
func (b *block) calculateHash() {
	hash := sha256.Sum256([]byte(b.data + b.prevHash))
	b.hash = fmt.Sprintf("%x", hash)
}
 

해당 data와 이전 블록의 hash를 더하여 hash한 값을 string값으로 변환한 후,
생성된 새로운 블록을 반환한다.

Function GetBlockchain

// Get All Blockchains
func GetBlockchain() *blockchain {
	if bc == nil {
		generateGenesis()
	}
	return bc
}

Genesis Block일 경우 genesis block을 발행하고
나머지 경우엔 blockchain을 반환하는 함수이다.

main.go

package main

import "github.com/hou27/blockchain_go/blockchain"

func main() {
	chain := blockchain.GetBlockchain()
	chain.AddBlock("Genesis Block?")
	chain.AddBlock("Second Block")
	chain.AddBlock("Third Block")
	chain.ShowBlocks()
}

main.go의 모습이다.

마지막 열의 showblocks 함수는 각 block들을 순회하며 출력해주는 함수이다.

 

가장 먼저 chain에 현재 블록체인을 불러와 초기화해주고,

하나씩 블록을 추가한 후,

모든 블록을 출력하도록 했다.

실행 시 모습 :

TimeStamp: 1641634656 
Data: Genesis Block 
Hash: 1947284bcf5356ccdb7b84fda8eaf211620ae91ff676b108e192d2f2413b454a 
Prev Hash: First Block 
TimeStamp: 1641634656 
Data: Genesis Block? 
Hash: 0f8b1e858b3c12d78ee1aaace1ef277f4636434b02d767abce99eae5a09b24cb 
Prev Hash: 1947284bcf5356ccdb7b84fda8eaf211620ae91ff676b108e192d2f2413b454a 
TimeStamp: 1641634656 
Data: Second Block 
Hash: 1ae70791238777b139ce13abd16d9e70e717da49e06072402aa2b34cf24eccaa 
Prev Hash: 0f8b1e858b3c12d78ee1aaace1ef277f4636434b02d767abce99eae5a09b24cb 
TimeStamp: 1641634656 
Data: Third Block 
Hash: 8306effdbbd659d00ab29c83b6993ed798f395f043cc607a73ffed366f187c9e 
Prev Hash: 1ae70791238777b139ce13abd16d9e70e717da49e06072402aa2b34cf24eccaa


이렇게 go로 암호화폐를 구현하기 위한 기본적인 구성을 마쳤다.

여기까지의 상세 코드는
https://github.com/hou27/blockchain_go/tree/part1

 

GitHub - hou27/blockchain_go: Making a Cryptocurrency with GO.

Making a Cryptocurrency with GO. . Contribute to hou27/blockchain_go development by creating an account on GitHub.

github.com

위에서 확인할 수 있다.