当前位置: 首页 > news >正文

【SpringBoot】SpringBoot实现基本的区块链的步骤与代码

以下是Spring Boot实现基本的区块链代码的步骤:

  1. 创建一个Block类,它表示一个区块,包含一个区块头和一个区块体。区块头包括版本号、时间戳、前一个区块的哈希值和当前区块的哈希值。区块体包含交易数据。

  2. 创建一个Blockchain类,它表示整个区块链,包含一个链列表和一个未确认交易列表。添加一个Genesis区块(创世区块)。

  3. 实现哈希函数,可以使用SHA256算法对数据进行哈希。

  4. 实现一个简单的工作量证明算法,目的是确保新区块的生成需要付出一定的计算力。可以使用计算拼图的方式来实现工作量证明算法。

  5. 实现一个简单的交易系统,包括交易数据的创建和验证。可以将交易数据保存在未确认交易列表中,然后在新区块生成后将其加入到区块链中。

  6. 实现一个简单的P2P网络,让不同的节点之间可以互相通信。可以使用websocket协议来实现P2P网络。

  7. 实现一个简单的共识协议,让不同的节点之间可以达成共识,确保区块链的一致性。可以使用最长链原则来实现共识协议。

  8. 创建一个Spring Boot应用程序,将以上所有代码整合起来,并提供简单的REST接口,让外部应用程序可以调用区块链的各种功能。

下面是一个简单实现的代码示例:

  1. Block类
public class Block {private int version;private long timeStamp;private String previousHash;private String hash;private List<Transaction> transactions;// getters and setters
}

    2.Blockchain类

public class Blockchain {private List<Block> chain = new ArrayList<>();private List<Transaction> currentTransactions = new ArrayList<>();public Blockchain() {// create genesis blockBlock genesisBlock = new Block(1, System.currentTimeMillis(), "", "");chain.add(genesisBlock);}public void addBlock(Block block) {String previousHash = getLastBlock().getHash();String hash = calculateHash(block.getVersion(), block.getTimeStamp(), previousHash, block.getTransactions());block.setHash(hash);chain.add(block);currentTransactions.clear();}public Block getLastBlock() {return chain.get(chain.size() - 1);}public void addTransaction(Transaction transaction) {currentTransactions.add(transaction);}// getters and setters
}

3.哈希函数

public static String calculateHash(int version, long timeStamp, String previousHash, List<Transaction> transactions) {String data = version + timeStamp + previousHash + transactions.toString();MessageDigest digest = MessageDigest.getInstance("SHA-256");byte[] hash = digest.digest(data.getBytes(StandardCharsets.UTF_8));return bytesToHex(hash);
}private static String bytesToHex(byte[] hash) {StringBuffer hexString = new StringBuffer();for (int i = 0; i < hash.length; i++) {String hex = Integer.toHexString(0xff & hash[i]);if(hex.length() == 1) hexString.append('0');hexString.append(hex);}return hexString.toString();
}

4.工作量证明算法

public static Block mineBlock(Block block, int difficulty) {String target = new String(new char[difficulty]).replace('\0', '0');while (!block.getHash().substring(0, difficulty).equals(target)) {block.setNonce(block.getNonce() + 1);block.setHash(calculateHash(block.getVersion(), block.getTimeStamp(), block.getPreviousHash(), block.getTransactions(), block.getNonce()));}return block;
}public static String calculateHash(int version, long timeStamp, String previousHash, List<Transaction> transactions, int nonce) {String data = version + timeStamp + previousHash + transactions.toString() + nonce;MessageDigest digest = MessageDigest.getInstance("SHA-256");byte[] hash = digest.digest(data.getBytes(StandardCharsets.UTF_8));return bytesToHex(hash);
}

5.交易系统

public class Transaction {private String sender;private String recipient;private int amount;// getters and setters
}@RestController
public class TransactionController {@Autowiredprivate Blockchain blockchain;@PostMapping("/transactions/new")public ResponseEntity<String> addTransaction(@RequestBody Transaction transaction) {blockchain.addTransaction(transaction);return ResponseEntity.ok("Transaction added");}
}

6.P2P网络

@Component
public class P2PClient {@Autowiredprivate Blockchain blockchain;@Autowiredprivate P2PServer p2pServer;private WebSocketSession session;private String address;@EventListenerpublic void handleWebSocketConnectListener(SessionConnectedEvent event) {session = event.getSession();address = session.getRemoteAddress().getHostName();p2pServer.addClient(this);}@EventListenerpublic void handleWebSocketCloseListener(SessionDisconnectEvent event) {p2pServer.removeClient(this);}public void sendMessage(String message) throws IOException {session.sendMessage(new TextMessage(message));}public void broadcast(String message) throws IOException {for (P2PClient client : p2pServer.getClients()) {if (!client.getAddress().equals(address)) {client.sendMessage(message);}}}// getters and setters
}@Component
public class P2PServer {@Autowiredprivate Blockchain blockchain;private List<P2PClient> clients = new ArrayList<>();public void addClient(P2PClient client) {clients.add(client);}public void removeClient(P2PClient client) {clients.remove(client);}public List<P2PClient> getClients() {return clients;}@Scheduled(fixedDelay = 1000)public void broadcastBlockchain() throws IOException {ObjectMapper objectMapper = new ObjectMapper();String blockchainJson = objectMapper.writeValueAsString(blockchain);for (P2PClient client : clients) {client.sendMessage(blockchainJson);}}
}

7.共识协议

public class Consensus {public static boolean resolveConflicts(List<Blockchain> blockchains) {int maxLength = blockchains.size();Blockchain longestBlockchain = null;for (Blockchain blockchain : blockchains) {if (blockchain.getChain().size() > maxLength && isValidChain(blockchain.getChain())) {maxLength = blockchain.getChain().size();longestBlockchain = blockchain;}}if (longestBlockchain != null) {blockchain.setChain(longestBlockchain.getChain());blockchain.setCurrentTransactions(longestBlockchain.getCurrentTransactions());return true;} else {return false;}}private static boolean isValidChain(List<Block> chain) {Block lastBlock = chain.get(0);int currentIndex = 1;while (currentIndex < chain.size()) {Block block = chain.get(currentIndex);if (!block.getPreviousHash().equals(lastBlock.getHash())) {return false;}currentIndex++;}return true;}
}@RestController
public class ConsensusController {@Autowiredprivate List<P2PClient> peers;@GetMapping("/nodes/resolve")public ResponseEntity<String> resolveConflicts() throws IOException {List<Blockchain> blockchains = new ArrayList<>();blockchains.add(blockchain);for (P2PClient peer : peers) {RestTemplate restTemplate = new RestTemplate();ResponseEntity<String> response = restTemplate.getForEntity(peer.getUrl() + "/chain", String.class);if (response.getStatusCode() == HttpStatus.OK) {Blockchain remoteBlockchain = objectMapper.readValue(response.getBody(), Blockchain.class);blockchains.add(remoteBlockchain);}}if (Consensus.resolveConflicts(blockchains)) {return ResponseEntity.ok("Conflict resolved. Blockchain updated.");} else {return ResponseEntity.ok("No conflicts found.");}}
}

8.Spring Boot应用程序

@SpringBootApplication
public class Application {public static void main(String[] args) {SpringApplication.run(Application.class, args);}
}

这只是一个简单的实现示例,实际上要实现一个完整的区块链系统需要更多的功能和细节。此外,还需要处理各种安全问题,例如拒绝服务攻击、双重支付等。因此,建议在实际应用中使用成熟的区块链框架,而不是从头开始编写自己的区块链代码。

相关文章:

【SpringBoot】SpringBoot实现基本的区块链的步骤与代码

以下是Spring Boot实现基本的区块链代码的步骤&#xff1a; 创建一个Block类&#xff0c;它表示一个区块&#xff0c;包含一个区块头和一个区块体。区块头包括版本号、时间戳、前一个区块的哈希值和当前区块的哈希值。区块体包含交易数据。 创建一个Blockchain类&#xff0c;它…...

Photoscan/Metashape 2.0.0中的地面激光扫描处理

在Metashape(原Photoscan)2.0.0, 结构化地面激光扫描和非结构化航空激光扫描都可以使用导入点云&#xff08;文件>导入>导入点云&#xff09;命令导入。导入时会保留所有点属性&#xff08;包括结构化信息&#xff09;。 本文讨论以下主题 如何将激光扫描数据导入项目&am…...

git快速使用

1、下载git 设置签名 2、基本概念 工作区&#xff1a;写代码的地方。 暂存区&#xff1a;.git的.index 工作区&#xff1a;.git 3、常用操作 本地codinggit init&#xff0c; 初始化一个本地仓库&#xff0c;项目根目录下会出现个.gitgit remote add origin gitgithub.com…...

java 实现代理模式

代理模式&#xff08;Proxy Pattern&#xff09;是一种结构型设计模式&#xff0c;它允许一个对象&#xff08;代理对象&#xff09;充当另一个对象&#xff08;被代理对象&#xff09;的接口&#xff0c;以控制对该对象的访问。代理模式通常用于以下情况&#xff1a; 远程代理…...

【每日一题】力扣1768. 交替合并字符串

题目以及链接&#xff1a; 1768. 交替合并字符串 给你两个字符串 word1 和 word2 。请你从 word1 开始&#xff0c;通过交替添加字母来合并字符串。如果一个字符串比另一个字符串长&#xff0c;就将多出来的字母追加到合并后字符串的末尾。 返回 合并后的字符串 。 示例 1&…...

vscode新建vue3文件模板

输入快捷新建的名字 enter 确认后在文件中输入以下内容 {// Place your snippets for vue here. Each snippet is defined under a snippet name and has a prefix, body and// description. The prefix is what is used to trigger the snippet and the body will be expand…...

MySql学习笔记02——MySql的简单介绍

MySQL 常用命令 注意在mysql中使用的命令需要用英文分号结尾&#xff08;启动/关闭mysql服务不需要带分号&#xff09; net start mysql 启动mysql服务&#xff08;需要管理员启动cmd&#xff09; net stop mysql关闭mysql服务&#xff08;需要管理员启动cmd&#xff09; m…...

mysql-1:认识mysql

文章目录 数据库概述什么是数据库什么是关系型数据库 MySQL的概述MySQL是什么MySQL发展历程 SQL的概述什么是SQLSQL发展的简要历史&#xff1a;SQL语言分类 数据库概述 什么是数据库 数据库就是[存储数据的仓库]&#xff0c;其本质是一个[文件系统]&#xff0c;数据按照特定的…...

算法通关村-----堆在查找和排序中的应用

数组中的第K个最大元素 问题描述 给定整数数组 nums 和整数 k&#xff0c;请返回数组中第 k 个最大的元素。请注意&#xff0c;你需要找的是数组排序后的第 k 个最大的元素&#xff0c;而不是第 k 个不同的元素。你必须设计并实现时间复杂度为 O(n) 的算法解决此问题。详见le…...

直方图统计增强方法

直方图统计增强方法的原理&#xff1a;   直方图统计增强是一种基于像素值分布的图像增强技术&#xff0c;通过调整像素值的分布来增强图像的对比度和细节。其原理是根据图像的直方图信息&#xff0c;将原始像素值映射到一个新的像素值域&#xff0c;从而改变图像的亮度和对比…...

字节二面:如果高性能渲染十万条数据?

前言 最近博主在字节面试中遇到这样一个面试题&#xff0c;这个问题也是前端面试的高频问题&#xff0c;作为一名前端开发工程师&#xff0c;我们虽然可能很少会遇到后端返回十万条数据的情况&#xff0c;但是了解掌握如何处理这种情况&#xff0c;能让你对前端性能优化有更深的…...

Mysql高阶语句(二)

一、设置别名&#xff08;alias ——>as&#xff09; 在 MySQL 查询时&#xff0c;当表的名字比较长或者表内某些字段比较长时&#xff0c;为了方便书写或者 多次使用相同的表&#xff0c;可以给字段列或表设置别名。使用的时候直接使用别名&#xff0c;简洁明了&#xff0…...

算法笔记 二叉搜索树

二叉搜索树&#xff08;Binary Search Tree&#xff0c;简称 BST&#xff09;是一种数据结构&#xff0c;用于存储具有可比较键&#xff08;通常是数字或字符串&#xff09;的元素 1 结构特点 节点结构&#xff1a;每个节点都有一个键和两个子节点&#xff08;左子节点和右子…...

微软牵手Linux:Ubuntu“系统”上架win10应用商店啦

导读继SUSE Linux登陆之后&#xff0c;Ubuntu今天正式以UWP应用的身份上架Win10应用商店。Windows Insider用户升级到Win10秋季创意者更新预览版Build 16190及以上就可以下载和安装Ubuntu系统应用。一旦下载和安装完Ubuntu应用后&#xff0c;它将开始在你的Windows10 PC上安装U…...

leetcode做题笔记126. 单词接龙 II

按字典 wordList 完成从单词 beginWord 到单词 endWord 转化&#xff0c;一个表示此过程的 转换序列 是形式上像 beginWord -> s1 -> s2 -> ... -> sk 这样的单词序列&#xff0c;并满足&#xff1a; 每对相邻的单词之间仅有单个字母不同。转换过程中的每个单词 s…...

windows下运行springboot的jar包,修改替换class文件,修改配置文件application,打包

在windows下跑springboot的jar包&#xff0c;经常会用到一些命令行和操作。 1、修改配置文件&#xff08;以application.yml为例&#xff09; #提取文件 jar xvf mqtt-10.1.0.jar BOOT-INF/classes/application.yml#将文件装回jar包 jar uvf mqtt-10.1.0.jar BOOT-INF/classe…...

PMD 检查java代码:可以去掉无用的括号(UselessParentheses)

这个规则的优先级比较低。 https://docs.pmd-code.org/pmd-doc-6.55.0/pmd_rules_java_codestyle.html#uselessparentheses 无用的括号可以去掉。当然&#xff0c;有时候为了避免理解起来困难&#xff0c;加上括号反而更加清晰。 例如&#xff1a; public static short calc…...

【数据结构练习】栈的面试题集锦

目录 前言&#xff1a; 1.进栈过程中可以出栈的选择题 2.将递归转化为循环 3.逆波兰表达式求值 4.有效的括号 5. 栈的压入、弹出序列 6. 最小栈 前言&#xff1a; 数据结构想要学的好&#xff0c;刷题少不了&#xff0c;我们不仅要多刷题&#xff0c;还要刷好题&#x…...

简单工厂模式概述和使用

目录 一、简单工厂模式简介1. 定义2. 使用动机 二、简单工厂模式结构1.模式结构2. 时序图 三、简单工厂的使用实例四、简单工厂模式优缺点五、简单工厂模式在Java中的应用 一、简单工厂模式简介 原文链接 1. 定义 简单工厂模式(Simple Factory Pattern)&#xff1a;又称为静…...

软件工程概述

软件工程概述 软件工程指的是应用计算机科学、数学及管理科学等原理&#xff0c;以工程化的原则和方法来解决软件问题的工程&#xff0c;目的是提高软件生产效率、提高软件质量、降低软件成本。 1. 计算机软件 计算机软件指的是计算机系统中的程序及其文档。程序是计算任务的…...

Python|GIF 解析与构建(5):手搓截屏和帧率控制

目录 Python&#xff5c;GIF 解析与构建&#xff08;5&#xff09;&#xff1a;手搓截屏和帧率控制 一、引言 二、技术实现&#xff1a;手搓截屏模块 2.1 核心原理 2.2 代码解析&#xff1a;ScreenshotData类 2.2.1 截图函数&#xff1a;capture_screen 三、技术实现&…...

HTML 语义化

目录 HTML 语义化HTML5 新特性HTML 语义化的好处语义化标签的使用场景最佳实践 HTML 语义化 HTML5 新特性 标准答案&#xff1a; 语义化标签&#xff1a; <header>&#xff1a;页头<nav>&#xff1a;导航<main>&#xff1a;主要内容<article>&#x…...

阿里云ACP云计算备考笔记 (5)——弹性伸缩

目录 第一章 概述 第二章 弹性伸缩简介 1、弹性伸缩 2、垂直伸缩 3、优势 4、应用场景 ① 无规律的业务量波动 ② 有规律的业务量波动 ③ 无明显业务量波动 ④ 混合型业务 ⑤ 消息通知 ⑥ 生命周期挂钩 ⑦ 自定义方式 ⑧ 滚的升级 5、使用限制 第三章 主要定义 …...

3.3.1_1 检错编码(奇偶校验码)

从这节课开始&#xff0c;我们会探讨数据链路层的差错控制功能&#xff0c;差错控制功能的主要目标是要发现并且解决一个帧内部的位错误&#xff0c;我们需要使用特殊的编码技术去发现帧内部的位错误&#xff0c;当我们发现位错误之后&#xff0c;通常来说有两种解决方案。第一…...

条件运算符

C中的三目运算符&#xff08;也称条件运算符&#xff0c;英文&#xff1a;ternary operator&#xff09;是一种简洁的条件选择语句&#xff0c;语法如下&#xff1a; 条件表达式 ? 表达式1 : 表达式2• 如果“条件表达式”为true&#xff0c;则整个表达式的结果为“表达式1”…...

《用户共鸣指数(E)驱动品牌大模型种草:如何抢占大模型搜索结果情感高地》

在注意力分散、内容高度同质化的时代&#xff0c;情感连接已成为品牌破圈的关键通道。我们在服务大量品牌客户的过程中发现&#xff0c;消费者对内容的“有感”程度&#xff0c;正日益成为影响品牌传播效率与转化率的核心变量。在生成式AI驱动的内容生成与推荐环境中&#xff0…...

sqlserver 根据指定字符 解析拼接字符串

DECLARE LotNo NVARCHAR(50)A,B,C DECLARE xml XML ( SELECT <x> REPLACE(LotNo, ,, </x><x>) </x> ) DECLARE ErrorCode NVARCHAR(50) -- 提取 XML 中的值 SELECT value x.value(., VARCHAR(MAX))…...

Psychopy音频的使用

Psychopy音频的使用 本文主要解决以下问题&#xff1a; 指定音频引擎与设备&#xff1b;播放音频文件 本文所使用的环境&#xff1a; Python3.10 numpy2.2.6 psychopy2025.1.1 psychtoolbox3.0.19.14 一、音频配置 Psychopy文档链接为Sound - for audio playback — Psy…...

12.找到字符串中所有字母异位词

&#x1f9e0; 题目解析 题目描述&#xff1a; 给定两个字符串 s 和 p&#xff0c;找出 s 中所有 p 的字母异位词的起始索引。 返回的答案以数组形式表示。 字母异位词定义&#xff1a; 若两个字符串包含的字符种类和出现次数完全相同&#xff0c;顺序无所谓&#xff0c;则互为…...

CMake 从 GitHub 下载第三方库并使用

有时我们希望直接使用 GitHub 上的开源库,而不想手动下载、编译和安装。 可以利用 CMake 提供的 FetchContent 模块来实现自动下载、构建和链接第三方库。 FetchContent 命令官方文档✅ 示例代码 我们将以 fmt 这个流行的格式化库为例,演示如何: 使用 FetchContent 从 GitH…...