写点什么

《迅雷链精品课》第五课:账户与账本

用户头像
迅雷链
关注
发布于: 2020 年 11 月 19 日
《迅雷链精品课》第五课:账户与账本

上一节课我们深入了解区块链技术发展趋势,讨论区块链领域内较为重要的技术:共识机制、隐私保护、数据存储和查询分析、混合架构的探索及互操作性、以及标准化及规范化等区块链技术。今天我们将学习区块链中的账户与账本,了解区块链账户的特点,明白区块链账户本质就是非对称加密中的公钥和私钥。


在学习课程的时候,你也可以领取 BaaS 平台为期一个月的试用机会,免费使用高性能区块链服务(点击链接即可免费领取https://blockchain.xunlei.com/baas/try.html。课程学习结合实践操作,让你迅速成为区块链大牛!

*以下为第五课的内容~


第五课 账户与账本


背景


区块链中的账户和银行账户有什么区别?对于想了解区块链账户的人来说,这可能是第一个想知道的,要一窥究竟,还得先看看银行账户是什么样子。首先,银行账户有一串固定长度的数字,叫账号,账号唯一标识一个账户,账号可以公开;其次,账户所有者通过自己设定的密码控制该账户,密码是私密的;最后,转账时需要转出方的账号和密码,以及转入方的账号。不管是银行卡还是存折,我们看到的银行账户基本就是这样的两串字符(账号和密码)。


区块链账户也具备上面三个特点,即账号、密码和转账需要转出账户密码,另外也有一些不同。之所以不同的主要原因是,银行系统是中心化的,类似账户转账这样的交易只在一个地方校验,而区块链是去中心化的,账户发出的交易在每个地方都需要校验。也就是说区块链中,不仅转出账户 A 要用密码证明是自己在转账,转入账户或中间任何一个环节都要能证明这笔钱确实是 A 转出的。要理解区块链账户怎么做到发出的交易在每个地方都可以被校验,就需要了解一些密码学知识,下面先介绍一下加密、解密、密钥、对称加密和非对称加密,然后讲一下区块链账户和非对称加密的关系,最后通过以太坊让大家对区块链账户有个直观的认识。


密码学方案


加密就是把多数人能懂的东西变成少数人的秘密。这里面有很多有趣的故事,除了“天王盖地虎,宝塔镇河妖”,还有钱壮飞的“天亮已走,母病危,速转院”。当然,最经典的还属初中生 Alice 写给 Bob 那张纸条,帮忙递纸条的韩梅梅和李雷虽然看到内容,但都一脸懵逼,而 Bob 看完却很开心。Alice 显然把信息“加密”了。Bob 之所以开心,是因为他“解密”了纸条的内容“zvff lbh gbb”。最后,在班主任的逼问下,大家才知道 Bob 和 Alice 早就商量好一套字母替换规则:用 26 个字母构成一个环,然后对称替换。所以,Alice 实际写给 Bob 的是“miss you too”。信息加密后,即使不相关的人看到纸条,因为不知道替换规则也不明白什么意思。通过这个例子,大家应该明白什么是加密,什么是解密。这里再借用维基百科的定义规范一下。加密是将明文信息改变为难以读取的密文内容,使之不可读的过程。这个过程反过来,就是解密。密钥是指某个用来完成加密、解密、完整性验证等密码学应用的秘密信息。据此,明文是“miss you too”,密文是“zvff lbh gbb”,密钥就是那个字母替换规则。


图 1. 替换加密示意图


一般对数据加密,是为了安全传输,接收密文的一方要用密钥解密。如果 Alice 想知道韩梅梅的年龄是否和自己相同,但两人都不想暴露自己的年龄,这种情况下,就要用到一种特殊的加密,叫哈希函数。它能将任意长度的明文加密成一个固定长度的密文(哈希值),相同明文会得到相同的哈希值,明文的任何改动都将使得哈希值产生变化。我们可以把哈希函数当作一个特殊的密钥,它只能用作加密,不能用于解密。有了哈希函数,Alice 就可以不失礼貌的和韩梅梅比较年龄,只要比较两人年龄的哈希值是否相同。


在了解完加密、解密和密钥之后,就很容易定义对称加密了。对称加密就是在加密和解密时使用相同密钥的加密算法。因为加密方和解密方使用同一个密钥,所以对称加密又叫共享密钥加密。这里的密钥可以是能简单地相互推算的两个规则。上面 Alice 和 Bob 加解密信息都是根据 26 个字母构成的环对称替换,就是典型的对称加密,因为加密和解密用到的规则完全一样。再举个例子,李四想告诉张三秘密数字 N,他把 N+1 的结果 S 传给张三,张三拿到 S 只要减 1 就可以得到李四给他的秘密数字。虽然这里用了两条规则,加密用加法,解密用减法,但因为两条规则可以简单的相互推算,所以也属于对称加密。


加法和减法互为逆运算,用来加解密有点过于简单,就算换成乘法与除法、指数运算与对数运算、积分与微分,我们也可以由一个运算快速推出其逆运算。如果能找到互为逆运算的两条规则,在有限的时间内不能相互推算,将这样的两条规则应用到加密与解密会是什么样子?非对称加密就是基于这样一对运算关系。为了进一步理解这种逆运算关系,我们来看看李四和基友张三的故事:


图 2. 非对称加密示意图


这里我们可以理解为,密文是 507,明文是 521,李四用密钥 667 将明文加密传给张三,张三用密钥 3 将密文解密。这里加解密用到的两个不同规则,就不像加减法那么明显可以相互推算了,换句话说加解密用到看起来毫不相关的两个密钥。幸运/不幸的是,数学世界真的存在这样的互为逆运算的关系,由规则 A 推出规则 B 很容易,反过来却很难,比如大数因数分解、离散对数和椭圆曲线问题。非对称加密就是应用这样两条规则的加密方式。有关非对称加密更详细的原理,大家很容易找到相关资料。为了让更多的人在不深入数学细节的情况下理解非对称加密,这里直接给它一个定义。非对称加密就是加密和解密使用不同密钥的加密方式,其中一个是私钥需要小心保存,另一个是公钥则可以公开给别人,用公钥加密明文只能被私钥解密。公钥和私钥都是配对的数字,数字越大越安全。一般私钥可以推出公钥,但用公钥推出私钥几乎不可能。私钥用作加密叫签名,因为私钥只该本人所有,签名的数据可以用公钥解密。常见的非对称加密算法有 RSA、ElGamal、椭圆曲线加密(ECC)等


区块链账户


区块链账户本质就是非对称加密中的公钥和私钥,其中公钥“类似”银行账户中那串数字账号,私钥对应密码,一般使用基于椭圆曲线 secp256k1 的 ECDSA 算法生成 256 比特的公私钥。基于前面讲到的公私钥的特性,账户所有者公开公钥,用私有的私钥加密(签名)转账交易,那么这个交易只能被配对的公钥解密,因为公钥公开,所以交易可以在每个环节被校验。


我们要去银行开户才能有自己的银行账户,那怎么拥有区块链账户,也要拿着身份证去什么地方开户吗?当然不需要!你可以用任何方法随机生成 256 比特的数作私钥,再借用工具推出对应的公钥,这一对公私钥就是一个账户。区块链账户和区块链系统是分离的,获取账户不需要注册,坐在地上抛 256 次硬币也能生成账户。甚至可以看看新生成的账户有没有以太币或比特币,因为公私钥就是一对数字,大家都可以用,说不定你和中本聪选用了同样的一对数字,要知道聪哥拥有一百万比特币。如果新生成一个账户已经存在,这叫账户碰撞,如果账户已经有钱,就叫中彩票。既然如此,用程序快速的永不停息的去碰撞有钱的账户,岂不是发财之道?这其实是个概率问题,因为 256 位的二进制表示的数,没比整个宇宙的原子个数少多少,所以账户碰撞是小概率事件。程序运行几十年碰撞出来的账户,那点钱估计还不够电费,所以想那样发财是不可能的,亏本的概率非常大。

 

虽说区块链账户本质就是一对很大的数字表示的公私钥,但使用上还是有点不一样。下面用以太坊为例,让我们看看怎么生成一个账户,以及账户表现是什么样子。以太坊账户新建指令是 geth account new,具体参数使用可通过 geth account new -h 查看。下面是我在 Centos7 以管理密码 1234 创建账户时的输出:


图 3. 以太坊新建账户


在图中我们看到,以太坊账户创建成功会在 keystore 目录下生成一个 JSON 格式的文件。可以理解为,文件内容是以对称加密的方式隐藏的账户私钥,对称加密的密钥由管理密码和 kdfparams 参数经过 scrypt 算法生成。这样因为账户没有明文保存,所以提高了安全性;转账只需要输入管理密码,剩下的校验和签名都交给账户管理程序,所以账户使用也更方便。虽然只需要记住账户管理密码,但账户本质还是那对公私钥。现在将私钥加密存储在文件中,一旦文件丢失,就相当于把绣花针丢进了大海,幸运的话,几百年后某人才会碰撞到这个账户,所以一定要备份好这个文件。


现在我们对区块链账户也有了直观的认识,但是账户里的钱在哪里?答案就是,在“账户地址”里,账户地址相当于银行账号。前面我们讲,区块链账户与区块链系统是分离的。这里,账户地址就是它们的桥梁。账户地址是由字母和数字组成的字符串,由账户公钥经过一定规则计算生成。刚才新建的以太坊账户地址是“c31e97c5fce994ba449b05191bdda25d06fcaf83”,它是由账户公钥通过 keccak256 哈希取后 160 位生成(以 16 进制形式表示为 20 字节的字符串)。具体区块链系统的账户地址可能有所不同,比如比特币的账户地址包含了校验码,用来防止转账时输错目标账户地址;另外以太坊还有合约账户地址,用来存储和执行智能合约代码。账户地址在不同区块链虽然可能表现为不同形式,但大多是由账户公钥通过单向函数计算生成,一个公钥对应一个地址,从地址无法推算出公钥。因此,账户私钥推出公钥,公钥推出账户地址,是一个单向的推导过程,不能反推。


账户模型


那么怎么证明一个账户地址有钱?我们知道,账户转账用私钥签名,别人可以用公钥验证,但公钥验证的是交易确实由账户所有者发出。比如,账户 A 转 3 个以太币给账户 B,用 A 的私钥签名这笔交易,别人用 A 的公钥可以证明这笔交易是 A 发出,但这不能证明账户 A 转账前至少有 3 个以太币。区块链系统有两种机制可以防止账户透支不存在的钱。


一种是以太坊采用的账户余额模型,该模型与银行账户模型类似,区块链系统维护了账户地址的一个全局状态,账户余额就记录在这个全局状态里。该模型要求转账交易包含转出账户地址、转账金额和转入账户地址(合约创建不需要这个地址)。下图是以太坊记录账户全局状态的数据结构。为了防止一笔钱花两次(双花),区块链系统按 Nonce 递增顺序处理交易。


图 4. 以太坊账户数据结构


另一种就是比特币采用的 UTXO 模型(Unspent Transaction Output,未花费交易输出),该模型要求交易包含输入和输出两部分,输入是其它账户转钱给自己的交易,输出是目标账户地址和金额。具体如上图所示,输入包含的是交易哈希和交易在区块中的位置,输入可以包含多笔交易,输出也可以有多个目标账户地址和金额。一笔交易,只有用输出中的账户地址对应的私钥解密,才能使用该地址对应的金额。如果输入引用的交易总金额大于自己想要转账的金额,可以在输出添加自己的账户地址,并且指定该返回多少钱,输入的总金额减去输出的总金额将被系统当手续费收取。所以,账户余额在 UTXO 模型中表现为一系列交易的集合。要知道账户总余额,需要收集它所有的未花费交易,并将交易对应的输出金额累加起来。


图 5. UTXO 示意图


账本


区块链不管选用哪种账户模型,发出的交易只要成功,都会被系统永久记录下来。账本其实就是成功交易的集合,在区块链中表现为一个个可能包含多笔交易的数据块(区块),这些区块按时间顺序通过块哈希值构成单向链表,前一个块的哈希值包含在下一个块的数据中。因为修改一个旧区块会使得块哈希值改变,这个改变会传递给之后的每个区块,而区块链中每个节点都单独记录所有区块信息,所以想修改区块链系统的数据几乎不可能,也因此区块链账本是安全的。


*恭喜完成第五课的学习,第六课我们将学习主流区块链项目的数据存储,欢迎关注~


发布于: 2020 年 11 月 19 日阅读数: 36
用户头像

迅雷链

关注

还未添加个人签名 2018.05.23 加入

还未添加个人简介

评论

发布
暂无评论
《迅雷链精品课》第五课:账户与账本