# Develop a simple blockchain with rust **Published by:** [skka3134](https://paragraph.com/@skka3134/) **Published on:** 2023-07-27 **URL:** https://paragraph.com/@skka3134/develop-a-simple-blockchain-with-rust ## Content The simple structure of a blockchain can be simply understood as countless such blocks connected like a chain to form a blockchain. The green part is called the block header, including (pre hash, tx hash, time) The black part and the blue part are called the block body, including (hash, transaction) Where pre hash is the hash of the previous block time represents the transaction time, timestamp The tx hash is used to ensure that the data is not tampered with. The data of each block can theoretically be tampered with, but the hash will not match after the modification. transaction is transaction information Finally, there is the hash value of the entire block, which is equivalent to the identification of each block. Similarly, as long as one piece of data in the block is changed, the hash value will change. On the code! ! ! 1.First we need to use the package, open the terminal cargo add serde cargo add bincode cargo add rust-crypto cargo add chrono 2.The package serde is used for serialization and deserialization. Serialization and deserialization are very common functions, which are extremely common in network transmission and data storage. The general explanation of serialization and deserialization is: seriallization serialization: convert the object into a format that is convenient for transmission, common serialization formats: binary format, byte array, json string, xml string. deseriallization deserialization: the process of restoring serialized data into objects. The package bincode is a binary encoding format. The package crypto is for hash The package chrono is for timestamp 3.Add the following code at the top use bincode; use serde::{Deserialize, Serialize}; use crypto::digest::Digest; use crypto::sha3::Sha3; use chrono::prelude::*; 4.Define the block header struct BlockHeader { time: i64, tx_hash: String, pre_hash: String, } 5.Define blocks struct Block { header: BlockHeader, hash: String, data: String, //transactions data } 6.Use the package just added to write two methods for serialization and deserialization. //Serializatize fn my_serialize<T: ?Sized>(value: &T) -> Vec<u8> where T: Serialize, { let seialized = bincode::serialize(value).unwrap(); seialized } //deserialize fn my_deserialize<'a, T>(bytes: &'a[u8]) -> T where T: Deserialize<'a>, { let deserialized = bincode::deserialize(bytes).unwrap(); deserialized } 7.Use the package rust-crypto to find the hash fn get_hash(value: &[u8]) -> String { let mut hasher = Sha3::sha3_256(); hasher.input(value); hasher.result_str() } 8.Implement these methods for the previously defined Block impl Block { fn set_hash(&mut self) { let header = coder::my_serialize(&(self.header)); self.hash = coder::get_hash(&header[..]); } fn new_block(data: String, pre_hash: String) -> Block { let transactions = coder::my_serialize(&data); let tx_hash = coder::get_hash(&transactions[..]); let time = Utc::now().timestamp(); let mut block = Block { header: BlockHeader { time: time, tx_hash: tx_hash, //transactions data merkle root hash pre_hash: pre_hash, }, hash: "".to_string(), data: data, }; block.set_hash(); block } } 9.Define blockchain struct BlockChain { blocks: Vec<block::Block>, } impl BlockChain { fn add_block(&mut self, data: String) { let pre_block = &self.blocks[self.blocks.len() - 1]; let new_block = block::Block::new_block(data, pre_block.hash.clone()); self.blocks.push(new_block); } fn new_genesis_block() -> block::Block { block::Block::new_block("This is genesis block".to_string(), String::from("")) } fn new_blockchain() -> BlockChain { BlockChain { blocks: vec![BlockChain::new_genesis_block()], } } } 10.Define the main method fn main() { let mut bc = blockchain::BlockChain::new_blockchain(); bc.add_block(String::from("a -> b: 5 btc")); bc.add_block("c -> d: 1 btc".to_string()); for b in bc.blocks { println!("++++++++++++++++++++++++++++++++++++++++++++"); println!("{:#?}", b); println!(""); } } The final code should look like this. use bincode; use serde::{Deserialize, Serialize}; use crypto::digest::Digest; use crypto::sha3::Sha3; use chrono::prelude::*; struct BlockHeader { time: i64, tx_hash: String, pre_hash: String, } struct Block { header: BlockHeader, hash: String, data: String, //transactions data } impl Block { fn set_hash(&mut self) { let header = coder::my_serialize(&(self.header)); self.hash = coder::get_hash(&header[..]); } fn new_block(data: String, pre_hash: String) -> Block { let transactions = coder::my_serialize(&data); let tx_hash = coder::get_hash(&transactions[..]); let time = Utc::now().timestamp(); let mut block = Block { header: BlockHeader { time: time, tx_hash: tx_hash, //transactions data merkle root hash pre_hash: pre_hash, }, hash: "".to_string(), data: data, }; block.set_hash(); block } } fn my_serialize<T: ?Sized>(value: &T) -> Vec<u8> where T: Serialize, { let seialized = bincode::serialize(value).unwrap(); seialized } fn my_deserialize<'a, T>(bytes: &'a[u8]) -> T where T: Deserialize<'a>, { let deserialized = bincode::deserialize(bytes).unwrap(); deserialized } fn get_hash(value: &[u8]) -> String { let mut hasher = Sha3::sha3_256(); hasher.input(value); hasher.result_str() } struct BlockChain { blocks: Vec<block::Block>, } impl BlockChain { fn add_block(&mut self, data: String) { let pre_block = &self.blocks[self.blocks.len() - 1]; let new_block = block::Block::new_block(data, pre_block.hash.clone()); self.blocks.push(new_block); } fn new_genesis_block() -> block::Block { block::Block::new_block("This is genesis block".to_string(), String::from("")) } fn new_blockchain() -> BlockChain { BlockChain { blocks: vec![BlockChain::new_genesis_block()], } } } Cargo run, the effect If you want to simulate mining, use sleep for about 10s ## Publication Information - [skka3134](https://paragraph.com/@skka3134/): Publication homepage - [All Posts](https://paragraph.com/@skka3134/): More posts from this publication - [RSS Feed](https://api.paragraph.com/blogs/rss/@skka3134): Subscribe to updates - [Twitter](https://twitter.com/skka3134): Follow on Twitter