Zhuang's Diary

言之有物,持之以恒

在我看来,下面这些是加密货币钱包需要的:

  • 私钥 - 由钱包来控制用户的私钥
  • 易用性 - 优雅的用户界面,易于用户使用
  • 开发社群 - 活跃的开发社群支持钱包不断更新和优化
  • 备份和安全 - 备份和恢复的特性
  • 兼容性 - 与不同的操作系统相兼容

个人认为,在寻找钱包时,需要确保满足上述要求。在这里,我列出了以太坊最好的钱包。 它们都符合上述要求。

1.Ledger Nano S (Hardware Wallet)](https://www.ledger.com/)

Ledger Nano S是最便宜的以太坊硬钱包之一(65美元)。此处,以太币在设备上脱机存储。 无论何时想花费以太币,Ledger都会使用存储在设备上的私钥对其进行签名。您可以存储ETH和ETC。

关于Ledger Nano S最棒的地方是它配备了一个小型OLED屏幕,可以控制您的交易。安全性非常强大,即使在黑客计算机上也可以使用Nano S设备。

2. Trezor (Hardware Wallet)

Trezor是比特币发明的第一个硬件钱包。但是,现在Trezor也可以通过MyEtherWallet Web界面用于以太坊。它还将以太币脱机存储在安全的电子芯片上,只有在您使用密码登录时才能激活。它是一种非常轻便的便携式设备,售价99美元。

3. Atomic (Desktop)

Atomic钱包是以太坊和ERC20 Token的终极解决方案。钱包可以使用银行卡存储,交换和购买ETH。将来,以太坊将可用于交换Atomic Swaps——这是一种完全分布式的方式,用于在不涉及中介的情况下做 Token 交易。

Atomic Wallet支持300多种加密货币,提供所有ERC20 Token 报价的界面。基本上,您可以输入联系地址并在自己的原子钱包中使用自定义代币。钱包会对您设备上的私钥进行加密,并为您提供对资金的完全访问权限和控制权。

Atomic Wallet适用于任何桌面操作系统,适用于Android和iOS设备。

4. Exodus (Desktop Wallet)

Exodus是世界上第一个多加密货币桌面钱包。免费使用,用户界面非常具有吸引力。当您打开Exodus钱包,饼图就会显示您的整个Token组合。Exodus是第一款内置ShapeShift用于交换加密货币的桌面钱包。但是,在使用Exodus时,需要始终连接到互联网,但您不必担心,因为您的私钥永远不会离开您的机器。并且用于还原钱包的一键式电子邮件恢复和备份种子密钥等功能可确保您的资金安全。

Exodus现在支持近100种加密货币!他们还有多个交易所合作伙伴(不仅仅是ShapeShift),这意味着我们可以提供更多可交换资产。从各个合作伙伴那里获取流动资金使得Exodus的交换更快更可靠。

他们也不需要个人电子邮件 - 这是希望收到电子邮件备份链接的人的选项。可以使用任何电子邮件地址 - 或者根本不使用!电子邮件仅用于发送备份链接一次。隐私对Exodus非常重要,他们不存储任何客户个人数据 - 甚至不包括电子邮件地址。

5. Jaxx (Mobile Wallet)

Jaxx是一个多资产钱包,由总部位于加拿大Decentral创建。它支持13种加密货币(包括ETH),具有优雅的设计和健壮的安全特性。

在Jaxx上,私有密匙永远不会离开设备,而种子密匙等特性使您能够在需要时恢复资金。

它有一个惊人的开发社区,负责产品的创新和维护。

支持平台桌面(Windows, Mac OS, Linux),扩展(Chrome, Firefox),移动/平板(苹果,Android)。不需要注册或个人信息。支持智能合同。

Jaxx钱包适用于Android、iOS、Mac OS、Windows和Linux。他们还将在未来几个月推出一款硬件钱包。

6.MetaMask (Desktop Wallet)

MestaMask是我最喜欢的以太钱包之一。

它就像一个浏览器访问以太网络。它不仅使您能够存储和发送Ethereum,还允许您访问Dapp程序。

它有一个直观的设计,您可以在测试网络和主要以太网络之间快速切换。

私钥是密码加密的,存储在您的机器上,您可以随时导出。

支持的平台:Firefox,Chrome extensions。不需要注册或个人信息。支持智能合同。

7.MyEtherWallet (Web Wallet)

MestaMask是我最喜欢的以太钱包之二 :)。

MyEtherWallet是一个离线的冷钱包,在这里你可以控制本地机器上以太坊的私钥。

它是一个开源钱包,无需第三方服务器,可以在其中编写和访问智能合同。它有一个内置的BTC到ETH,以及多币种(反之亦然)交易设施。您还可以连接您的Trezor或Ledger Nano S,以访问您的资金在MyEther的浏览器环境。

8. Coinbase (Mobile Wallet)

Coinbase支持比特币和以太坊。

这是一种既便宜又快捷的储存以太的方法,前提是它们为你的国家服务。你可以在这里查一下你们国家是否有他们的服务。如果是,请按照以下步骤使用Coinbase:

  1. 在Coinbase登记(邮箱注册,注册个人信息)。

  2. 获取你的公共地址。

  3. 把你的电子计算机转移到Coinbase的公共地址。

  4. 将ETH存储在Coinbase上。

然而,缺点是私钥不在您的控制中,因为它们存储在Coinbase的托管服务器上。Coinbase不支持智能合约。

也就是说,这是一种很好的短期储存ETH的方法。如果打算长期持有以太币,应该使用纸质钱包的方法或使用像Ledger Nano S这样的硬件钱包。

Research on Blockchain Application in Insurance Industry

全文: PDF (4379 KB) HTML (1 KB)

输出: BibTeX | EndNote (RIS)

Abstract:Blockchain technology will play an important role in digital transformation in insurance industry. This paper attempts to introduce CBGM (Consortium Blockchain Governance Model) which can help insurance institutions to leverage blockchain technology to build insurance digital ecosystem more efficiently. This paper leverages authors experience of applying blockchain technology in insurance industry recent years. Firstly, application scenarios of blockchain in insurance industry has been sorted out. Meanwhile, the challenges of using blockchain technology has been analyzed, whose one of the key challenges is how to manage consortium. Secondly, CBGM and 6 sub-modules have been developed and introduced which is targeted to provide common method to manage consortium. Finally, an example of using CBGM has been shared and proposal for insurance institution has been provided.
Key words: blockchain insurance consortium governance model project implementation

产品从0到1的原则:

  • MVP 最小化可用产品

    以旅游产品为例,可以考虑 hotel 客房预订作为 MVP,而不是选择这个旅行安排作为第一步。

  • 以目标用户为本,而不是所有人

    为目标用户的需求而设计,为解决需求的同事提供更高的价值。

    核心需求—> 体验需求—>更高价值(使用价值、情感价值、尊重价值、自我实现价值)

    以 hotel 客房预订为例,目标用户为商务旅行的人员?个人度假的人员?

    商务人员的核心需求是hotel城市分布广泛,梯度价位适度。

    个人度假的核心需求是 hotel 的性价比。

  • 综上,以中小型公司商务人员和个人用户针对Hotel客房预订的核心需求是性价比。

Hotel 客房预订的产品 MVP 的最主要需求是实时性,可靠性,正确性和容易地得到价格(曲线)

  • ChainID和NetworkID有什么不同?
    ChainID在EIP-155中有介绍,当NetworkID都为1时,ChainID来防止在ETH和ETC之间的replay attacks—重放攻击。

  • ChainID和NetworkID在没有个区块中都需要标识吗?还是只在genesis block创世区块中标识?

    ChainID通常是需要的。例如在为txs签名时,这样才能将ETH和ETC的tx区分开来。在EIP-155之前,为txs签名时需要NetworkID。

  • 目前ChainID和NetworkID有哪些已经被使用?

CHAIN_ID Chain(s)
1 Ethereum mainnet
2 Morden (disused), Expanse mainnet
3 Ropsten
4 Rinkeby
5 Goerli
42 Kovan
1337 Geth private chains (default)

###在https://chainid.network/中有更加详细的介绍。

##参考链接:

https://github.com/ethereum/EIPs/blob/master/EIPS/eip-155.md

什么是稳定币

稳定币就是一种相对稳定的加密货币。这里的“稳定”主要是指价格稳定,即,在一段时间内的价格不会有大幅波动。

  1. 第一代以USDT为代表稳定币,其特征是无监管、无透明、属于自说自话的一种。

  2. 第二代以TrueUSD为代表的稳定币,比USDT进了一步,它的在透明度上要比USDT好很多,因为TUSD宣称使用托管帐户作为基金管理中使用最广泛的合法工具,为持有人提供定期审计和强有力的法律保护,即多银行负责托管帐户、第三方出具帐户余额认证、团队绝不和存入的USDT直接打交道等等,所以不会出现裁判员和运动员于一身的情况。

  3. 第三代以GUSD和PAX为代表的稳定币,则更进一步,直接以美国国家信用为背书。2018年9月10日,纽约金融服务部(NYDFS)同时批准了两种基于以太坊-ERC20发行的稳定币,分别是 Gemini 公司发行的稳定币Gemini Dollar(GUSD),与Paxos公司发行的稳定币Paxos。Standard (PAX),每个稳定币都有 1 美元支撑。此外,还有两个非常突出的特点:一个是获得政府部门纽约金融服务部正式批准,成为第一个合规合法、接受监督的稳定币(也就意味着受到法律保护),信用背书大幅提升;另一个是基于以太坊的ERC20来发行的,这意味着财务相关数据完全公开透明、不可窜改,而且完全去中心化。那么理论上说,每一笔GUSD的增发都会有相应的资金入账。和完全中心化的稳定币对比,对于投资者来说,无疑更加具有可信度。

但我们也应该看到,这次给GUSD颁发执照的,是NYDFS(纽约州金融服务部门),即一个地方金融部门。美国州级金融部门的监管并不意味着在全美有效,NYDFS(纽约州金融服务部门)上面还有SEC和美联储,这两个部门的态度才是决定稳定币未来的关键。而且GUSD目前只有25万美金上限的保额(GUSD发行的美元是存放在美国的在岸银行账户上的,这个账户适用FDIC的存款保险)。所以此次GUSD作为试点的目的很浓,就像我们国家一样,新东西慢慢来,先搞个试点,从中总结经验、完善相关法律法规,待成熟后逐步全面推广。

关于ERC20代币

如果问以太坊的智能合约应用最广泛的地方在哪里, 肯定就是发币了。 虽然可能V神也没想到世界还没被改变, ICO(圈钱)的方式倒是又多出了一个。

既然是数字token, 代码实现起来就可以有各种各样的方案。 实质无外乎就是记录下每个用户拥有的数字token数量, 具有转账,查询余额等功能就行了。 上面我们说到只要调用对应相关的函数去执行即可完成相关的功能。 可是这个时候假如某个ICO方A 写了代币转账功能, 它的转账函数叫做tx(uint256). 那么如果想调用它的转账就要调用tx这个函数, 我们知道只要调用函数不相同, input的内容就不会一样。 如果所有的ICO方写的这些函数名称均不一样。 调用者就要查看每一个ICO方的合约代码。 于是这个时候ERC20就来了, 它定义了一些发币(圈钱)的规范。也即是如果你想发行ICO, 最好按着我的规范来, 这样大家用起来就跟方便了。ERC20简而言之就是定义了下面几个接口

1
2
3
4
5
6
7
8
9
10
11
12
13
14
contract ERC20 {

uint256 public totalSupply;

event Transfer(address indexed from, address indexed to, uint256 value); // 转账触发
event Approval(address indexed owner, address indexed spender, uint256 value); // 容许提取触发

function balanceOf(address who) public view returns (uint256); // 查询余额函数
function transfer(address to, uint256 value) public returns (bool); // 进行转账函数

function approve(address spender, uint256 value) public returns (bool); // 容许某个地址提款
function transferFrom(address from, address to, uint256 value) public returns (bool); // 从一方向另一方转账的余额

}

有了这个规范, 各个ICO方在发行token时都实现上面的接口, 这样无论任何的ERC20代币, 均可以用一套方法实现所有代币转账,查询余额等功能。

分析一下PAX稳定币的智能合约代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
pragma solidity ^0.4.24;
pragma experimental "v0.5.0";

// 导入外部包 此包中主要是一些
// 安全的数学运算
// 因为在一些场景 出现了数据溢出没有考虑的问题导致了
// 一些ico币直接归零
import "./zeppelin/SafeMath.sol";

contract PAXImplementation {

using SafeMath for uint256;
bool private initialized = false;

// 定义了ERC20规定的代币名称 符号 精度
mapping(address => uint256) internal balances;
uint256 internal totalSupply_;
string public constant name = "PAX"; // solium-disable-line uppercase
string public constant symbol = "PAX"; // solium-disable-line uppercase
uint8 public constant decimals = 18; // solium-disable-line uppercase

// ERC20 DATA
mapping (address => mapping (address => uint256)) internal allowed;

// OWNER DATA
address public owner;

// PAUSABILITY DATA
bool public paused = false;

// LAW ENFORCEMENT DATA
address public lawEnforcementRole;
mapping(address => bool) internal frozen;

// SUPPLY CONTROL DATA
address public supplyController;

// 定义触发时间 当转账或者授权别人转账时 调用此事件 当调用时 其实质会在以太坊节点区块上写入日志。
event Transfer(address indexed from, address indexed to, uint256 value);
event Approval(
address indexed owner,
address indexed spender,
uint256 value
);

// OWNABLE EVENTS
event OwnershipTransferred(
address indexed oldOwner,
address indexed newOwner
);

// PAUSABLE EVENTS
event Pause();
event Unpause();

// LAW ENFORCEMENT EVENTS
event AddressFrozen(address indexed addr);
event AddressUnfrozen(address indexed addr);
event FrozenAddressWiped(address indexed addr);
event LawEnforcementRoleSet (
address indexed oldLawEnforcementRole,
address indexed newLawEnforcementRole
);

// SUPPLY CONTROL EVENTS
event SupplyIncreased(address indexed to, uint256 value);
event SupplyDecreased(address indexed from, uint256 value);
event SupplyControllerSet(
address indexed oldSupplyController,
address indexed newSupplyController
);

/**
* FUNCTIONALITY
*/

// INITIALIZATION FUNCTIONALITY

/**
合约部署时的初始化过程
设置合约拥有者为部署合约的账户
设置总供应量为0
并保证此函数只会被调用一次
*/
function initialize() public {
require(!initialized, "already initialized");
owner = msg.sender;
lawEnforcementRole = address(0);
totalSupply_ = 0;
supplyController = msg.sender;
initialized = true;
}

/**
合约的构造函数 调用上面的初始化函数 并且设置暂停交易
*/
constructor() public {
initialize();
pause();
}

// ERC20 BASIC FUNCTIONALITY

/**
ERC20接口 返回总的供应量
*/
function totalSupply() public view returns (uint256) {
return totalSupply_;
}

/*
转账函数 实现将调用者的token转给其他人
msg.sender 即为合约的调用者
并且此函数要求必须是非暂停状态 即whenNotPaused返回真

这个函数有需要验证条件
1.交易没有被暂停
2.接收方地址不能是0
3.接收方和发起方均不可以是冻结地址
4.转账的token余额要足够。
*/
function transfer(address _to, uint256 _value) public whenNotPaused returns (bool) {
require(_to != address(0), "cannot transfer to address zero");
require(!frozen[_to] && !frozen[msg.sender], "address frozen");
require(_value <= balances[msg.sender], "insufficient funds");

balances[msg.sender] = balances[msg.sender].sub(_value);
balances[_to] = balances[_to].add(_value);
emit Transfer(msg.sender, _to, _value);
return true;
}

/**
ERC20接口 返回某个账户的token余额
*/
function balanceOf(address _addr) public view returns (uint256) {
return balances[_addr];
}

// ERC20 FUNCTIONALITY

/*
ERC20接口 实现了 _from地址下容许调用方可以转出金额到其他_to
此函数要求必须是非暂停状态
*/
function transferFrom(
address _from,
address _to,
uint256 _value
)
public
whenNotPaused
returns (bool)
{
require(_to != address(0), "cannot transfer to address zero");
require(!frozen[_to] && !frozen[_from] && !frozen[msg.sender], "address frozen");
require(_value <= balances[_from], "insufficient funds");
require(_value <= allowed[_from][msg.sender], "insufficient allowance");

balances[_from] = balances[_from].sub(_value);
balances[_to] = balances[_to].add(_value);
allowed[_from][msg.sender] = allowed[_from][msg.sender].sub(_value);
emit Transfer(_from, _to, _value);
return true;
}

/**
ERC20接口 实现调用方容许_spender 可以从我的账户转出的金额 这个函数和上面的函数是相对应的。
只有一个账户容许了其他账户能从我的账户转出的金额 上述的函数才能转账成功。
*/
function approve(address _spender, uint256 _value) public whenNotPaused returns (bool) {
require(!frozen[_spender] && !frozen[msg.sender], "address frozen");
allowed[msg.sender][_spender] = _value;
emit Approval(msg.sender, _spender, _value);
return true;
}

/**
ERC20接口 返回_owner账户容许_spender账户从自己名下转移出去的资产数量
*/
function allowance(
address _owner,
address _spender
)
public
view
returns (uint256)
{
return allowed[_owner][_spender];
}

// OWNER FUNCTIONALITY

/**
这个函数被称为修饰函数 上面的whenNotPaused 也是一个修饰函数 实质是一种断言。 只有
断言通过 才会执行函数内部的内容
*/
modifier onlyOwner() {
require(msg.sender == owner, "onlyOwner");
_;
}

/*
将只能合约的拥有者转给别人
*/
function transferOwnership(address _newOwner) public onlyOwner {
require(_newOwner != address(0), "cannot transfer ownership to address zero");
emit OwnershipTransferred(owner, _newOwner);
owner = _newOwner;
}

// PAUSABILITY FUNCTIONALITY

/**
* 修饰函数 要求处于非暂停交易状态
*/
modifier whenNotPaused() {
require(!paused, "whenNotPaused");
_;
}

/**
* 只有合约的拥有者才可以设置暂停交易
*/
function pause() public onlyOwner {
require(!paused, "already paused");
paused = true;
emit Pause();
}

/**
* 只有合约的拥有者才能取消暂停交易
*/
function unpause() public onlyOwner {
require(paused, "already unpaused");
paused = false;
emit Unpause();
}

// LAW ENFORCEMENT FUNCTIONALITY

/**
设置一个法定的的强制角色 这个角色可以冻结或者解冻别人账户的token
设置一个这样的角色要求首先调用方要么是合约的拥有者 要么自己已经是法定的强制者
* @param _newLawEnforcementRole The new address allowed to freeze/unfreeze addresses and seize their tokens.
*/
function setLawEnforcementRole(address _newLawEnforcementRole) public {
require(msg.sender == lawEnforcementRole || msg.sender == owner, "only lawEnforcementRole or Owner");
emit LawEnforcementRoleSet(lawEnforcementRole, _newLawEnforcementRole);
lawEnforcementRole = _newLawEnforcementRole;
}

// 断言函数 要求调用方必须是强制者角色
modifier onlyLawEnforcementRole() {
require(msg.sender == lawEnforcementRole, "onlyLawEnforcementRole");
_;
}

/**
冻结某个账户的token 使用了断言 onlyLawEnforcementRole 也是只有调用方角色是
法定强制者才有权限冻结别人的token
*/
function freeze(address _addr) public onlyLawEnforcementRole {
require(!frozen[_addr], "address already frozen");
frozen[_addr] = true;
emit AddressFrozen(_addr);
}

/**
解冻某个账户的token 使用了断言 onlyLawEnforcementRole 也是只有调用方角色是
法定强制者才有权限解冻别人的token
*/
function unfreeze(address _addr) public onlyLawEnforcementRole {
require(frozen[_addr], "address already unfrozen");
frozen[_addr] = false;
emit AddressUnfrozen(_addr);
}

/**
摧毁冻结账户的token 也就是说如果这个地址是一个冻结地址调用这个函数会把这个地址的token销毁同时总供应数量也会被减少
当然这个函数也不是谁都可以调用的 只有法定的强制者才有权限
*/
function wipeFrozenAddress(address _addr) public onlyLawEnforcementRole {
require(frozen[_addr], "address is not frozen");
uint256 _balance = balances[_addr];
balances[_addr] = 0;
totalSupply_ = totalSupply_.sub(_balance);
emit FrozenAddressWiped(_addr);
emit SupplyDecreased(_addr, _balance);
emit Transfer(_addr, address(0), _balance);
}

/**
用于检查某个地址是否被冻结了
*/
function isFrozen(address _addr) public view returns (bool) {
return frozen[_addr];
}

// SUPPLY CONTROL FUNCTIONALITY

/**
设置token供应量的控制着 在合约初始化时 token供应量是合约发起则 调用这个函数可以更改
这个函数只有调用方已经是token供应量控制着或者整个合约的拥有者才能调用成功
也就是在整个合约中 合约的拥有者实质是可以控制一切权限的。 它能更改法定强制者 更改总token
供应量的控制者。
*/
function setSupplyController(address _newSupplyController) public {
require(msg.sender == supplyController || msg.sender == owner, "only SupplyController or Owner");
require(_newSupplyController != address(0), "cannot set supply controller to address zero");
emit SupplyControllerSet(supplyController, _newSupplyController);
supplyController = _newSupplyController;
}

modifier onlySupplyController() {
require(msg.sender == supplyController, "onlySupplyController");
_;
}

/**
增加总的token供应量 并把新增供应量加到supplyController这个账户的名下。
*/
function increaseSupply(uint256 _value) public onlySupplyController returns (bool success) {
totalSupply_ = totalSupply_.add(_value);
balances[supplyController] = balances[supplyController].add(_value);
emit SupplyIncreased(supplyController, _value);
emit Transfer(address(0), supplyController, _value);
return true;
}

/**
减少总的token供应量 待减少供应量从supplyController这个账户的名下减掉 。
这个函数要求supplyController
*/
function decreaseSupply(uint256 _value) public onlySupplyController returns (bool success) {
require(_value <= balances[supplyController], "not enough supply");
balances[supplyController] = balances[supplyController].sub(_value);
totalSupply_ = totalSupply_.sub(_value);
emit SupplyDecreased(supplyController, _value);
emit Transfer(supplyController, address(0), _value);
return true;
}
}

PAX稳定币功能概述

PAX除了具有这个ERC20的功能外,还具有一些其他功能:

  1. 可以暂停整个代币转账
  2. 可以增加或者减少整个代币的数量
  3. 可以任意冻结或者解冻某个账户的代币
  4. 可以销毁某个冻结账户的代币
  5. 可以转移合约控制权。可以转移总供应量控制权。

总的来说PAX币做的限制特别多, 它的合约拥有机会可以做任何事情。 就算token转移给你了, 依然能分分钟钟消失。