将数据存储在数据库中是任何软件应用程序不可或缺的一部分。无论如何控制该数据库都有一个该数据的主控。区块链技术将数据存储到区块链网络内的区块中。因此,只要某个节点与网络同步,它们就会获得区块中数据的副本。因此,该技术中没有特定的数据主控。
在本教程中,我们将编写一份智能合约(我将进一步解释),以便在区块链上保留用户数据。我们将使用python web3(web3的python库)来开发和部署智能合约。一旦我们在区块链上部署了智能合约。我们将使用flask API与智能合约进行交互以存储一些数据/信息。我们将它存储在区块链上,它是不可变的。
环境要求
Python 3.6
安装
1.创建一个python虚拟环境。
Virtualenv将你的Python软件包本地化保存在你项目的虚拟环境中,而不是强迫你在系统范围内安装软件包。
$ virtualenv -p /usr/bin/python3.6 venv
$ source venv/bin/activate
2.现在我们需要Ganache
那样的以太坊测试链。
Ganache是以太坊开发的个人区块链,可用于部署合约,开发应用程序和运行测试。
$ npm install -g ganache-cli
3.安装python web3
Web3.py是一个用于与以太坊交互的python库。它的API源自Web3.js Javascript API,对于使用过web3.js的人来说应该很熟悉。
$ pip3 install web3
4.Flask
Flask是一个python轻量级框架。
$ pip3 install flask
5.Flask Restful
Flask-RESTful是Flask的扩展,增加了对快速构建REST API的支持。
$ pip3 install flask-restful
- Flask Marshmallow
Flask marshmallow是一个对象序列化/反序列化库。
$ pip3 install flask-marshmallow
启动以太坊测试区块链服务器
要部署智能合约,我们应该启动测试以太坊服务器。我们正在使用ganache进行测试。在终端中键入以下命令:
$ ganache-cli
Ganache为我们提供了10个默认测试帐户,每个帐户中有100个假ether,用于交易。我们将使用这些帐户在合约中部署和设置各种值。
我们可以看到gas价格和限制以及部署ganache
的host:port
。我们在部署合约时需要这个。
创建user.sol文件
现在我们将用Solidity编写智能合约。Solidity是在ethereum上编写智能合约的语言。智能合约包括我们将在区块链上存储的数据,数据和getter方法的可选验证函数,访问数据的setter方法。
例如,要在区块链上进行考勤注册,你将拥有一组用户对象。它将可以访问用户的getter,setter方法。由于每个用户每天只能标记一次出勤,因此你需要一个验证功能来检查,智能合约与我们通常用其他任何语言开发的应用程序非常相似。
在下面的文件中,我们使用getter,setter函数构建简单的用户合约。
1.在.sol文件中声明solidity编译器版本。
pragma solidity ^ 0.4.21;
了解使用的编译器版本。
$ solidity — version
2.导入库文件Import library。我们应该将库用于常用的实用程序函数。库可以只编译一次并反复使用(点击这里获取一些好的库资源)。
import“stringUtils.sol”;
3.为用户声明合约
contract userRecords {
}
4.现在,对于基本演示,我们将存储有关用户的名称和性别信息。因此,使用struct和enum数据类型初始化这两个变量。
//枚举类型变量来存储用户性别
enum genderType { male, female }
//我们将存储在以太坊合约中的实际用户对象
struct user{
string name; genderType gender;
}
5.现在我们将声明user(struct)
类型的用户对象。也可以将其声明为public,以便从合约外部访问它(有关可见范围,请单击此处)。
user user_obj;
6.现在为用户对象添加getter,setter方法。我们将在区块链上保留每个用户的信息。我们应该始终公开此方法,因为我们将从合约外部访问它们。
//设置用户公共功能
//这类似于db中的持久对象。
function setUser(string name, string gender) public {
genderType gender_type = getGenderFromString(gender);
user_obj = user({name:name, gender: gender_type});
}
//获取用户公共功能
//这类似于从db获取对象。
function getUser() public returns (string,