java开源区块链jdchain入门

目录
  • 前言
  • 部署组件
  • 傻瓜式部署
    • 获取部署包
    • 效果预览
  • 部署遇到的问题:
    • 网关里的异常
  • 结语

前言

jdchain是京东数科开源的区块链平台,目标是实现一个面向企业应用场景的通用区块链框架系统,能够作为企业级基础设施,为业务创新提供高效、灵活和安全的解决方案。

之所以选择jdchain研究是因为jdchain是为数不多的底层也是采用java实现的一个区块链平台

项目地址:https://github.com/blockchain...

文档地址:https://gitee.com/jdchain

部署组件

  • peer:区块链主节点,参与共识、账本操作等
  • gateway:与Peer节点通信,负责区块链浏览器及消息传递
  • 客户端:采用SDK和网关链接,通过网关发起交易

傻瓜式部署

获取部署包

有两种途径可以拿到部署包,一、直接从官网下载.二、从github上拉源码,然后自己构建,在deployment目录下会生成部署包,自己构建的需要注意,如果是在Windows系统上构建的包,包里的启动脚本在linux系统下运行会有转义字符的问题,需要在assembly.xml里设置lineEnding为unix

效果预览

区块链部署工具

区块链浏览器

部署遇到的问题:

官方文档算比较详细,但是很多细节没有写明,一般体验和开发时部署的环境比较简单,可能在一个主机上部署4个节点的peer。这个时候端口的编排要非常注意,因为jdchain目前的共识算法采用的开源的bftsmart实现,共识端口在同一台主机上不能连续,不然就会端口冲突。博主就遇到了这个问题,下面是详细排错过程:采用SDK创建用户时抛如下异常,网关可以正常连接,秘钥认证没有问题:

Caused by: java.lang.IndexOutOfBoundsException: The accessing index is out of BytesSlice's bounds!
	at com.jd.blockchain.utils.io.BytesSlice.checkBoundary(BytesSlice.java:174)
	at com.jd.blockchain.utils.io.BytesSlice.getInt(BytesSlice.java:97)
	at com.jd.blockchain.utils.io.BytesSlice.getInt(BytesSlice.java:86)
	at com.jd.blockchain.binaryproto.impl.HeaderEncoder.resolveCode(HeaderEncoder.java:71)
	at com.jd.blockchain.binaryproto.BinaryProtocol.decode(BinaryProtocol.java:41)
	at com.jd.blockchain.sdk.converters.BinarySerializeResponseConverter.getResponse(BinarySerializeResponseConverter.java:33)
	at com.jd.blockchain.utils.http.agent.HttpServiceAgent.invoke(HttpServiceAgent.java:587)
	... 7 more

网关里的异常

11:57:05.537 ERROR com.jd.blockchain.gateway.web.GatewayGlobalExceptionHandler 34 json - Unexpected exception occurred! --[RequestURL=[POST] http://192.168.1.190:8081/rpc/tx][class java.lang.IllegalStateException]Returned object not currently part of this pool java.lang.IllegalStateException: Returned object not currently part of this pool
	at org.apache.commons.pool2.impl.GenericObjectPool.returnObject(GenericObjectPool.java:530) ~[commons-pool2-2.5.0.jar!/:2.5.0]
	at com.jd.blockchain.consensus.bftsmart.client.BftsmartMessageService.sendOrderedMessage(BftsmartMessageService.java:46) ~[consensus-bftsmart-1.1.1.RELEASE.jar!/:1.1.1.RELEASE]
	at com.jd.blockchain.consensus.bftsmart.client.BftsmartMessageService.sendOrdered(BftsmartMessageService.java:22) ~[consensus-bftsmart-1.1.1.RELEASE.jar!/:1.1.1.RELEASE]
	at com.jd.blockchain.sdk.service.NodeSigningAppender.process(NodeSigningAppender.java:84) ~[sdk-base-1.1.1.RELEASE.jar!/:1.1.1.RELEASE]
	at com.jd.blockchain.sdk.service.PeerServiceProxy.process(PeerServiceProxy.java:89) ~[sdk-base-1.1.1.RELEASE.jar!/:1.1.1.RELEASE]
	at com.jd.blockchain.gateway.web.TxProcessingController.process(TxProcessingController.java:70) ~[gateway-1.1.1.RELEASE.jar!/:1.1.1.RELEASE]
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[?:1.8.0_231]
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[?:1.8.0_231]
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[?:1.8.0_231]
	at java.lang.reflect.Method.invoke(Method.java:498) ~[?:1.8.0_231]

最终查明异常是由于网关里创建AsynchServiceProxy失败导致的,这部分实现采用了Apache-commons-pool2。实现如下:

public class BftsmartPeerProxyFactory extends BasePooledObjectFactory{
    private BftsmartClientSettings bftsmartClientSettings;
    private int gatewayId;
    private AtomicInteger index = new AtomicInteger(1);
    public BftsmartPeerProxyFactory(BftsmartClientSettings bftsmartClientSettings, int gatewayId) {
        this.bftsmartClientSettings = bftsmartClientSettings;
        this.gatewayId = gatewayId;
    }
    @Override
    public AsynchServiceProxy create() throws Exception {
        BftsmartTopology topology = BinarySerializeUtils.deserialize(bftsmartClientSettings.getTopology());
        MemoryBasedViewStorage viewStorage = new MemoryBasedViewStorage(topology.getView());
        TOMConfiguration tomConfiguration = BinarySerializeUtils.deserialize(bftsmartClientSettings.getTomConfig());
        //every proxy client has unique id;
        tomConfiguration.setProcessId(gatewayId + index.getAndIncrement());
        AsynchServiceProxy peerProxy = new AsynchServiceProxy(tomConfiguration, viewStorage);
        return peerProxy;
    }
    @Override
    public PooledObjectwrap(AsynchServiceProxy asynchServiceProxy) {
        return new DefaultPooledObject<>(asynchServiceProxy);
    }
}

这个代码BinarySerializeUtils.deserialize(bftsmartClientSettings.getTopology())返回的是null,没有正确拿到Bftsmart的网络拓扑。进而查看peer节点,发现只有节点0成功了,其他都抛如下异常,初步判断bftsmart的副本服务因为端口占用启动失败了:

11:36:48.479 ERROR bftsmart.tom.ServiceReplica 247 init - null java.net.BindException: 地址已在使用
	at sun.nio.ch.Net.bind0(Native Method) ~[?:1.8.0_231]
	at sun.nio.ch.Net.bind(Net.java:433) ~[?:1.8.0_231]
	at sun.nio.ch.Net.bind(Net.java:425) ~[?:1.8.0_231]
	at sun.nio.ch.ServerSocketChannelImpl.bind(ServerSocketChannelImpl.java:223) ~[?:1.8.0_231]
	at io.netty.channel.socket.nio.NioServerSocketChannel.doBind(NioServerSocketChannel.java:130) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.channel.AbstractChannel$AbstractUnsafe.bind(AbstractChannel.java:558) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.channel.DefaultChannelPipeline$HeadContext.bind(DefaultChannelPipeline.java:1358) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.channel.AbstractChannelHandlerContext.invokeBind(AbstractChannelHandlerContext.java:501) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.channel.AbstractChannelHandlerContext.bind(AbstractChannelHandlerContext.java:486) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.channel.DefaultChannelPipeline.bind(DefaultChannelPipeline.java:1019) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.channel.AbstractChannel.bind(AbstractChannel.java:254) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.bootstrap.AbstractBootstrap$2.run(AbstractBootstrap.java:366) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.util.concurrent.AbstractEventExecutor.safeExecute(AbstractEventExecutor.java:163) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.util.concurrent.SingleThreadEventExecutor.runAllTasks(SingleThreadEventExecutor.java:404) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:446) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.util.concurrent.SingleThreadEventExecutor$5.run(SingleThreadEventExecutor.java:884) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30) ~[netty-all-4.1.29.Final.jar:4.1.29.Final]
	at java.lang.Thread.run(Thread.java:748) ~[?:1.8.0_231]

从bftsmart官方文档得知,如果在同一个主机运行,不能使用顺序的端口号,即一开始编排的peer的共识端口,6000、6001、6002、6003是不行的,原因如下:如果在同一台计算机(127.0.0.1)中部署/执行了某些(或全部)副本,config/hosts.config则不能具有顺序的端口号(例如10000、10001、10002、10003)。这是因为每个副本都绑定了两个端口:一个用于接收来自客户端的消息,另一个用于接收来自其他副本的消息(通过获取下一个端口号选择) 。更一般而言,如果为副本R分配了端口号P,它将尝试将端口P(绑定到接收到的客户端请求)和端口P + 1(绑定到其他副本)进行绑定。如果不执行此准则,则副本可能无法绑定所有需要的端口。

结语

jdchain是完整采用java实现的区块链项目,是java开发者研究区块链的一大福音,而且项目开源后一直在迭代,文档和社区支持方面都比较友好。入门虽然很简单,但是要深入到这个项目后面还有很多的东西要研究。楼主计划,后面先把SDK和网关的交互搞清楚,然后在研究下最新的共识实现(基于RabbitMQ),然后在研究下智能合约的应用,最后深入代码实现,可能后面还会有其他的关于jdchain的内容输出。最后希望全部掌握后能给社区贡献点代码、提供点案例、解答点问题。为开源尽自己的绵薄之力

以上就是java开源区块链jdchain入门的详细内容,更多关于java开源区块链jdchain的资料请关注我们其它相关文章!

(0)

相关推荐

  • 如何用120行Java代码写一个自己的区块链

    区块链是目前最热门的话题,广大读者都听说过比特币,或许还有智能合约,相信大家都非常想了解这一切是如何工作的.这篇文章就是帮助你使用 Java 语言来实现一个简单的区块链,用不到 120 行代码来揭示区块链的原理! "用不到120行 Java 代码就能实现一个自己的区块链!" 听起来不可思议吧?有什么能比开发一个自己的区块链更好的学习实践方法呢?那我们就一起来实践下! 因为我们是一家从事互联网金融的科技公司,所以我们采用虚拟资产金额作为这篇文章中的示例数据.大家可以先为自己想一个数字,后

  • 使用Java实现简单的区块链程序的方法

    在本文中,我们将学习区块链技术的基本概念.我们还将用Java实现一个基本的应用程序,重点介绍这些概念. 此外,我们还将讨论该技术的一些先进概念和实际应用. 什么是区块链? 那么,让我们先来了解一下区块链到底是什么- 好吧,它的起源可以追溯到Satoshi Nakamoto在2008年发表的关于比特币的白皮书. 区块链是一个分散的信息分类帐.它由通过使用密码学连接的数据块组成.它属于通过公共网络连接的节点网络.当我们稍后尝试构建一个基本教程时,我们将更好地理解这一点. 我们必须了解一些重要的属性,

  • 基于Java编写第一个区块链项目

    前言 区块链是数字加密货币比特币的核心技术. 区块链是一个称为块的记录列表,这些记录使用链表链接在一起并使用加密技术. 每个数据块都包含自己的数字指纹(称为散列).前一个数据块的散列.时间戳和所做事务的数据,使其在任何类型的数据泄露时都更加安全. 因此,如果一个块的数据被改变,那么它的散列也会改变.如果散列被更改,那么它的散列将不同于下一个块,下一个块包含前一个块的散列,影响它之后的所有块的散列.更改哈希值,然后将其与其他块进行比较,这允许我们检查区块链. 区块链实施:以下是区块链实施中使用的功

  • 区块链常用数据库leveldb用java来实现常规操作的方法

    前言 LevelDB 是一种Key-Value存储数据库百度百科上介绍 性能非常强悍 可以支撑十亿级这段时间在研究区块链的时候发现的这个数据库.LevelDB 是单进程的服务,性能非常之高,在一台4核Q6600的CPU机器上,每秒钟写数据超过40w,而随机读的性能每秒钟超过10w. 此处随机读是完全命中内存的速度,如果是不命中 速度大大下降,LevelDB 只是一个 C/C++ 编程语言的库, 不包含网络服务封装, 所以无法像一般意义的存储服务器(如 MySQL)那样, 用客户端来连接它. Le

  • java开源区块链初始化创世区块jdchain服务搭建

    目录 初始化创世区块 第一步.生成公私钥 第二步.准备配置 第三步.执行初始化脚本 创世区块创建过程 结语 初始化创世区块 搭建区块链服务第一步就是初始化创世区块,创建账本.生成dchain初始化创世区块有两种方式,一种是通过官方提供的区块链部署工具,在页面上操作初始化,一种是通过初始化脚本创建.目前,部署工具初始化账本功能有限,只支持btfsmart共识算法的节点初始化,如果要支持mq的共识,只能使用初始化账本的脚本创建 第一步.生成公私钥 使用部署工具生成公私钥,虽然部署工具不支持mq共识的

  • java开源区块链jdchain入门

    目录 前言 部署组件 傻瓜式部署 获取部署包 效果预览 部署遇到的问题: 网关里的异常 结语 前言 jdchain是京东数科开源的区块链平台,目标是实现一个面向企业应用场景的通用区块链框架系统,能够作为企业级基础设施,为业务创新提供高效.灵活和安全的解决方案. 之所以选择jdchain研究是因为jdchain是为数不多的底层也是采用java实现的一个区块链平台 项目地址:https://github.com/blockchain... 文档地址:https://gitee.com/jdchain

  • 利用Java代码实现区块链技术

    目录 不变性 块散列 Chain 链 添加事务 Merkle树 采矿工作证明 单元测试 最后的想法 前言: 比特币很热门——这是多么轻描淡写的说法啊.虽然加密货币的未来有些不确定,但用于驱动比特币的区块链技术也非常流行. 区块链的应用范围几乎无穷无尽.可以说,它还有可能破坏企业自动化. 本文将重点关注区块链体系结构,特别是演示“不可变.仅附加”分布式账本如何与简化的代码示例一起工作. 作为开发人员,与简单地阅读技术文章相比,在理解代码的工作原理时,从代码中看到东西要有用得多.至少对我来说是这样.

  • 区块链java代码实现

    概述 MerkleTree被广泛的应用在比特币技术中,本文旨在通过代码实现一个简单的MerkleTree,并计算出Merkle tree的 TreeRoot. Merkle Tree 是一种数据结构,用于验证在计算机之间和之间存储,处理和传输的任何类型的数据. 目前,Merkle树的主要用途是确保从对等网络中接收的数据块未受损和未改变,和检查其他对等网络没有撒谎发送假数据块. Merkle Tree应用举例 比特币 GitA mazon's Dynamo Gassandra 比特币中的应用 比特

  • Python学习入门之区块链详解

    前言 本文将给大家简单介绍关于区块链(BlockChain)的相关知识,并用Python做一简单实现.下面话不多说,来一起看看详细的介绍: 什么是区块链 简单来说,区块链就是把加密数据(区块)按照时间顺序进行叠加(链)生成的永久.不可逆向修改的记录.具体来说,它区块链是由一串使用密码学方法产生的数据块组成的,每一个区块都包含了上一个区块的哈希值(hash),从创始区块(genesis block)开始连接到当前区块,形成块链.每一个区块都确保按照时间顺序在上一个区块之后产生,否则前一个区块的哈希

  • Spring Boot 整合 Fisco Bcos的案例分析(区块链)

    目录 简介 本地环境 主要流程: 1.Fisco Bcos环境搭建与验证 1.1.搭建单群组4节点联盟链: 1.2.检查证书 1.3.使用证书验证节点正确性 2.创建SpringBoot工程并配置依赖 2.1.创建SpringBoot工程: 2.2.配置pom.xml 3.2.配置节点证书: 3.3.编写controller 3.4.DemoBcosApplication默认不做修改 3.5.application.properties什么也没配置 4.生成jar包.部署服务器验证 4.1.本地

随机推荐