@@ -17,6 +17,7 @@ public interface LedgerInitSetting { | |||||
/** | /** | ||||
* 账本的种子; | * 账本的种子; | ||||
* | |||||
* @return | * @return | ||||
*/ | */ | ||||
@DataField(order = 1, primitiveType = PrimitiveType.BYTES) | @DataField(order = 1, primitiveType = PrimitiveType.BYTES) | ||||
@@ -37,9 +38,8 @@ public interface LedgerInitSetting { | |||||
*/ | */ | ||||
@DataField(order = 3, refContract = true) | @DataField(order = 3, refContract = true) | ||||
CryptoSetting getCryptoSetting(); | CryptoSetting getCryptoSetting(); | ||||
@DataField(order = 4, primitiveType=PrimitiveType.TEXT) | |||||
@DataField(order = 4, primitiveType = PrimitiveType.TEXT) | |||||
String getConsensusProvider(); | String getConsensusProvider(); | ||||
/** | /** | ||||
@@ -47,7 +47,15 @@ public interface LedgerInitSetting { | |||||
* | * | ||||
* @return | * @return | ||||
*/ | */ | ||||
@DataField(order = 5, primitiveType=PrimitiveType.BYTES) | |||||
@DataField(order = 5, primitiveType = PrimitiveType.BYTES) | |||||
Bytes getConsensusSettings(); | Bytes getConsensusSettings(); | ||||
/** | |||||
* 账本创建时间; | |||||
* | |||||
* @return | |||||
*/ | |||||
@DataField(order = 6, primitiveType = PrimitiveType.INT64) | |||||
long getCreatedTime(); | |||||
} | } |
@@ -11,22 +11,41 @@ import com.jd.blockchain.transaction.LedgerInitOperator; | |||||
* | * | ||||
*/ | */ | ||||
public interface TransactionBuilder extends ClientOperator, LedgerInitOperator { | public interface TransactionBuilder extends ClientOperator, LedgerInitOperator { | ||||
HashDigest getLedgerHash(); | HashDigest getLedgerHash(); | ||||
/** | /** | ||||
* 完成交易定义,并生成就绪的交易数据; <br> | |||||
* 基于当前的系统时间完成交易定义,并生成就绪的交易数据; <br> | |||||
* | * | ||||
* 注:调用此方法后,不能再向当前对象加入更多的操作; | |||||
* 注:调用此方法后,不能再向当前对象加入更多的操作;<br> | |||||
* | * | ||||
* @return | * @return | ||||
*/ | */ | ||||
TransactionRequestBuilder prepareRequest(); | TransactionRequestBuilder prepareRequest(); | ||||
/** | /** | ||||
* 生成交易内容; | * 生成交易内容; | ||||
* | |||||
* @return | * @return | ||||
*/ | */ | ||||
TransactionContent prepareContent(); | TransactionContent prepareContent(); | ||||
/** | |||||
* 基于当前的系统时间完成交易定义,并生成就绪的交易数据; <br> | |||||
* | |||||
* 注:调用此方法后,不能再向当前对象加入更多的操作; | |||||
* | |||||
* @param time 交易时间戳; | |||||
* @return | |||||
*/ | |||||
TransactionRequestBuilder prepareRequest(long time); | |||||
/** | |||||
* 生成交易内容; | |||||
* | |||||
* @param time 交易时间戳; | |||||
* @return | |||||
*/ | |||||
TransactionContent prepareContent(long time); | |||||
} | } |
@@ -33,4 +33,13 @@ public interface TransactionContentBody { | |||||
@DataField(order = 2, list = true, refContract = true, genericContract = true) | @DataField(order = 2, list = true, refContract = true, genericContract = true) | ||||
Operation[] getOperations(); | Operation[] getOperations(); | ||||
/** | |||||
* 生成交易的时间;<br> | |||||
* 以毫秒为单位,表示距离 1970-1-1 00:00:00 (UTC) 的毫秒数;<br> | |||||
* | |||||
* @return | |||||
*/ | |||||
@DataField(order = 3, primitiveType = PrimitiveType.INT64) | |||||
long getTime(); | |||||
} | } |
@@ -16,6 +16,8 @@ public class LedgerInitSettingData implements LedgerInitSetting { | |||||
private String consensusProvider; | private String consensusProvider; | ||||
private Bytes consensusSettings; | private Bytes consensusSettings; | ||||
private long createdTime; | |||||
@Override | @Override | ||||
public byte[] getLedgerSeed() { | public byte[] getLedgerSeed() { | ||||
@@ -62,4 +64,12 @@ public class LedgerInitSettingData implements LedgerInitSetting { | |||||
this.consensusProvider = consensusProvider; | this.consensusProvider = consensusProvider; | ||||
} | } | ||||
@Override | |||||
public long getCreatedTime() { | |||||
return createdTime; | |||||
} | |||||
public void setCreatedTime(long createdTime) { | |||||
this.createdTime = createdTime; | |||||
} | |||||
} | } |
@@ -35,14 +35,25 @@ public class TxBuilder implements TransactionBuilder { | |||||
@Override | @Override | ||||
public TransactionRequestBuilder prepareRequest() { | public TransactionRequestBuilder prepareRequest() { | ||||
TransactionContent txContent = prepareContent(); | |||||
return new TxRequestBuilder(txContent); | |||||
return prepareRequest(System.currentTimeMillis()); | |||||
} | } | ||||
@Override | @Override | ||||
public TransactionContent prepareContent() { | public TransactionContent prepareContent() { | ||||
return prepareContent(System.currentTimeMillis()); | |||||
} | |||||
@Override | |||||
public TransactionRequestBuilder prepareRequest(long time) { | |||||
TransactionContent txContent = prepareContent(time); | |||||
return new TxRequestBuilder(txContent); | |||||
} | |||||
@Override | |||||
public TransactionContent prepareContent(long time) { | |||||
TxContentBlob txContent = new TxContentBlob(ledgerHash); | TxContentBlob txContent = new TxContentBlob(ledgerHash); | ||||
txContent.addOperations(opFactory.getOperations()); | txContent.addOperations(opFactory.getOperations()); | ||||
txContent.setTime(time); | |||||
byte[] contentBodyBytes = BinaryProtocol.encode(txContent, TransactionContentBody.class); | byte[] contentBodyBytes = BinaryProtocol.encode(txContent, TransactionContentBody.class); | ||||
HashDigest contentHash = Crypto.getHashFunction(DEFAULT_HASH_ALGORITHM).hash(contentBodyBytes); | HashDigest contentHash = Crypto.getHashFunction(DEFAULT_HASH_ALGORITHM).hash(contentBodyBytes); | ||||
@@ -30,6 +30,8 @@ public class TxContentBlob implements TransactionContent { | |||||
private HashDigest hash; | private HashDigest hash; | ||||
private HashDigest ledgerHash; | private HashDigest ledgerHash; | ||||
private long time; | |||||
public TxContentBlob(HashDigest ledgerHash) { | public TxContentBlob(HashDigest ledgerHash) { | ||||
this.ledgerHash = ledgerHash; | this.ledgerHash = ledgerHash; | ||||
@@ -80,6 +82,15 @@ public class TxContentBlob implements TransactionContent { | |||||
addOperation(op); | addOperation(op); | ||||
} | } | ||||
} | } | ||||
@Override | |||||
public long getTime() { | |||||
return time; | |||||
} | |||||
public void setTime(long time) { | |||||
this.time = time; | |||||
} | |||||
public void addOperation(Operation operation) { | public void addOperation(Operation operation) { | ||||
operationList.add(operation); | operationList.add(operation); | ||||
@@ -1,85 +0,0 @@ | |||||
#账本的种子;一段16进制字符,最长可以包含64个字符;可以用字符“-”分隔,以便更容易读取; | |||||
ledger.seed=932dfe23-fe23232f-283f32fa-dd32aa76-8322ca2f-56236cda-7136b322-cb323ffe | |||||
#账本的描述名称;此属性不参与共识,仅仅在当前参与方的本地节点用于描述用途; | |||||
ledger.name= | |||||
#参与方的个数,后续以 cons_parti.id 分别标识每一个参与方的配置; | |||||
cons_parti.count=4 | |||||
#第0个参与方的名称; | |||||
cons_parti.0.name=jd.com | |||||
#第0个参与方的公钥文件路径; | |||||
cons_parti.0.pubkey-path=keys/jd-com.pub | |||||
#第0个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | |||||
cons_parti.0.pubkey=endPsK36koyFr1D245Sa9j83vt6pZUdFBJoJRB3xAsWM6cwhRbna | |||||
#第0个参与方的共识服务的主机地址; | |||||
cons_parti.0.consensus.host=127.0.0.1 | |||||
#第0个参与方的共识服务的端口; | |||||
cons_parti.0.consensus.port=8900 | |||||
#第0个参与方的共识服务是否开启安全连接; | |||||
cons_parti.0.consensus.secure=true | |||||
#第0个参与方的账本初始服务的主机; | |||||
cons_parti.0.initializer.host=127.0.0.1 | |||||
#第0个参与方的账本初始服务的端口; | |||||
cons_parti.0.initializer.port=8800 | |||||
#第0个参与方的账本初始服务是否开启安全连接; | |||||
cons_parti.0.initializer.secure=true | |||||
#第1个参与方的名称; | |||||
cons_parti.1.name=at.com | |||||
#第1个参与方的公钥文件路径; | |||||
cons_parti.1.pubkey-path=keys/at-com.pub | |||||
#第1个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | |||||
cons_parti.1.pubkey=endPsK36sC5JdPCDPDAXUwZtS3sxEmqEhFcC4whayAsTTh8Z6eoZ | |||||
#第1个参与方的共识服务的主机地址; | |||||
cons_parti.1.consensus.host=127.0.0.1 | |||||
#第1个参与方的共识服务的端口; | |||||
cons_parti.1.consensus.port=8910 | |||||
#第1个参与方的共识服务是否开启安全连接; | |||||
cons_parti.1.consensus.secure=false | |||||
#第1个参与方的账本初始服务的主机; | |||||
cons_parti.1.initializer.host=127.0.0.1 | |||||
#第1个参与方的账本初始服务的端口; | |||||
cons_parti.1.initializer.port=8810 | |||||
#第1个参与方的账本初始服务是否开启安全连接; | |||||
cons_parti.1.initializer.secure=false | |||||
#第2个参与方的名称; | |||||
cons_parti.2.name=bt.com | |||||
#第2个参与方的公钥文件路径; | |||||
cons_parti.2.pubkey-path=keys/bt-com.pub | |||||
#第2个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | |||||
cons_parti.2.pubkey=endPsK36jEG281HMHeh6oSqzqLkT95DTnCM6REDURjdb2c67uR3R | |||||
#第2个参与方的共识服务的主机地址; | |||||
cons_parti.2.consensus.host=127.0.0.1 | |||||
#第2个参与方的共识服务的端口; | |||||
cons_parti.2.consensus.port=8920 | |||||
#第2个参与方的共识服务是否开启安全连接; | |||||
cons_parti.2.consensus.secure=false | |||||
#第2个参与方的账本初始服务的主机; | |||||
cons_parti.2.initializer.host=127.0.0.1 | |||||
#第2个参与方的账本初始服务的端口; | |||||
cons_parti.2.initializer.port=8820 | |||||
#第2个参与方的账本初始服务是否开启安全连接; | |||||
cons_parti.2.initializer.secure=true | |||||
#第3个参与方的名称; | |||||
cons_parti.3.name=xt.com | |||||
#第3个参与方的公钥文件路径; | |||||
cons_parti.3.pubkey-path=keys/xt-com.pub | |||||
#第3个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | |||||
cons_parti.3.pubkey=endPsK36nse1dck4uF19zPvAMijCV336Y3zWdgb4rQG8QoRj5ktR | |||||
#第3个参与方的共识服务的主机地址; | |||||
cons_parti.3.consensus.host=127.0.0.1 | |||||
#第3个参与方的共识服务的端口; | |||||
cons_parti.3.consensus.port=8930 | |||||
#第3个参与方的共识服务是否开启安全连接; | |||||
cons_parti.3.consensus.secure=false | |||||
#第3个参与方的账本初始服务的主机; | |||||
cons_parti.3.initializer.host=127.0.0.1 | |||||
#第3个参与方的账本初始服务的端口; | |||||
cons_parti.3.initializer.port=8830 | |||||
#第3个参与方的账本初始服务是否开启安全连接; | |||||
cons_parti.3.initializer.secure=false |
@@ -1,8 +1,5 @@ | |||||
package com.jd.blockchain.tools.initializer; | package com.jd.blockchain.tools.initializer; | ||||
import com.jd.blockchain.consensus.ConsensusProvider; | |||||
import com.jd.blockchain.consensus.ConsensusSettings; | |||||
import com.jd.blockchain.consensus.service.ConsensusServiceProvider; | |||||
import com.jd.blockchain.crypto.HashDigest; | import com.jd.blockchain.crypto.HashDigest; | ||||
import com.jd.blockchain.crypto.PrivKey; | import com.jd.blockchain.crypto.PrivKey; | ||||
import com.jd.blockchain.ledger.CryptoSetting; | import com.jd.blockchain.ledger.CryptoSetting; | ||||
@@ -3,6 +3,8 @@ package com.jd.blockchain.tools.initializer; | |||||
import java.io.File; | import java.io.File; | ||||
import java.io.FileNotFoundException; | import java.io.FileNotFoundException; | ||||
import java.io.InputStream; | import java.io.InputStream; | ||||
import java.text.ParseException; | |||||
import java.text.SimpleDateFormat; | |||||
import java.util.ArrayList; | import java.util.ArrayList; | ||||
import java.util.List; | import java.util.List; | ||||
import java.util.Properties; | import java.util.Properties; | ||||
@@ -22,6 +24,12 @@ public class LedgerInitProperties { | |||||
// 账本种子; | // 账本种子; | ||||
public static final String LEDGER_SEED = "ledger.seed"; | public static final String LEDGER_SEED = "ledger.seed"; | ||||
// 声明的账本建立时间; | |||||
public static final String CREATED_TIME = "created-time"; | |||||
// 创建时间的格式; | |||||
public static final String CREATED_TIME_FORMAT = "yyyy-MM-dd HH:mm:ss.SSSZ"; | |||||
// 共识参与方的个数,后续以 part.id 分别标识每一个参与方的配置; | // 共识参与方的个数,后续以 part.id 分别标识每一个参与方的配置; | ||||
public static final String PART_COUNT = "cons_parti.count"; | public static final String PART_COUNT = "cons_parti.count"; | ||||
// 共识参与方的名称的模式; | // 共识参与方的名称的模式; | ||||
@@ -61,10 +69,16 @@ public class LedgerInitProperties { | |||||
private String[] cryptoProviders; | private String[] cryptoProviders; | ||||
private long createdTime; | |||||
public byte[] getLedgerSeed() { | public byte[] getLedgerSeed() { | ||||
return ledgerSeed.clone(); | return ledgerSeed.clone(); | ||||
} | } | ||||
public long getCreatedTime() { | |||||
return createdTime; | |||||
} | |||||
public Properties getConsensusConfig() { | public Properties getConsensusConfig() { | ||||
return consensusConfig; | return consensusConfig; | ||||
} | } | ||||
@@ -80,11 +94,11 @@ public class LedgerInitProperties { | |||||
public List<ConsensusParticipantConfig> getConsensusParticipants() { | public List<ConsensusParticipantConfig> getConsensusParticipants() { | ||||
return consensusParticipants; | return consensusParticipants; | ||||
} | } | ||||
public String[] getCryptoProviders() { | public String[] getCryptoProviders() { | ||||
return cryptoProviders.clone(); | return cryptoProviders.clone(); | ||||
} | } | ||||
public void setCryptoProviders(String[] cryptoProviders) { | public void setCryptoProviders(String[] cryptoProviders) { | ||||
this.cryptoProviders = cryptoProviders; | this.cryptoProviders = cryptoProviders; | ||||
} | } | ||||
@@ -132,6 +146,14 @@ public class LedgerInitProperties { | |||||
byte[] ledgerSeed = HexUtils.decode(hexLedgerSeed); | byte[] ledgerSeed = HexUtils.decode(hexLedgerSeed); | ||||
LedgerInitProperties initProps = new LedgerInitProperties(ledgerSeed); | LedgerInitProperties initProps = new LedgerInitProperties(ledgerSeed); | ||||
// 创建时间; | |||||
String strCreatedTime = PropertiesUtils.getRequiredProperty(props, CREATED_TIME); | |||||
try { | |||||
initProps.createdTime = new SimpleDateFormat(CREATED_TIME_FORMAT).parse(strCreatedTime).getTime(); | |||||
} catch (ParseException ex) { | |||||
throw new IllegalArgumentException(ex.getMessage(), ex); | |||||
} | |||||
// 解析共识相关的属性; | // 解析共识相关的属性; | ||||
initProps.consensusProvider = PropertiesUtils.getRequiredProperty(props, CONSENSUS_SERVICE_PROVIDER); | initProps.consensusProvider = PropertiesUtils.getRequiredProperty(props, CONSENSUS_SERVICE_PROVIDER); | ||||
String consensusConfigFilePath = PropertiesUtils.getRequiredProperty(props, CONSENSUS_CONFIG); | String consensusConfigFilePath = PropertiesUtils.getRequiredProperty(props, CONSENSUS_CONFIG); | ||||
@@ -338,6 +338,7 @@ public class LedgerInitializeWebController implements LedgerInitProcess, LedgerI | |||||
ConsensusParticipantConfig[] parties = partiList.toArray(new ConsensusParticipantConfig[partiList.size()]); | ConsensusParticipantConfig[] parties = partiList.toArray(new ConsensusParticipantConfig[partiList.size()]); | ||||
ConsensusParticipantConfig[] orderedParties = sortAndVerify(parties); | ConsensusParticipantConfig[] orderedParties = sortAndVerify(parties); | ||||
initSetting.setConsensusParticipants(orderedParties); | initSetting.setConsensusParticipants(orderedParties); | ||||
initSetting.setCreatedTime(ledgerProps.getCreatedTime()); | |||||
// 创建默认的共识配置; | // 创建默认的共识配置; | ||||
try { | try { | ||||
@@ -377,7 +378,8 @@ public class LedgerInitializeWebController implements LedgerInitProcess, LedgerI | |||||
BlockchainIdentity superUserId = new BlockchainIdentityData(p.getPubKey()); | BlockchainIdentity superUserId = new BlockchainIdentityData(p.getPubKey()); | ||||
initTxBuilder.users().register(superUserId); | initTxBuilder.users().register(superUserId); | ||||
} | } | ||||
this.initTxContent = initTxBuilder.prepareContent(); | |||||
// 账本初始化配置声明的创建时间来初始化交易时间戳;注:不能用本地时间,因为共识节点之间的本地时间系统不一致; | |||||
this.initTxContent = initTxBuilder.prepareContent(initSetting.getCreatedTime()); | |||||
// 对初始交易签名,生成当前参与者的账本初始化许可; | // 对初始交易签名,生成当前参与者的账本初始化许可; | ||||
SignatureDigest permissionSign = TxRequestBuilder.sign(initTxContent, privKey); | SignatureDigest permissionSign = TxRequestBuilder.sign(initTxContent, privKey); | ||||
@@ -755,7 +757,7 @@ public class LedgerInitializeWebController implements LedgerInitProcess, LedgerI | |||||
prompter.info("Received request of synchronizing decision! --[RemoteId=%s][CurrentId=%s]", remoteId, currentId); | prompter.info("Received request of synchronizing decision! --[RemoteId=%s][CurrentId=%s]", remoteId, currentId); | ||||
try { | try { | ||||
DecisionResultHandle resultHandle = this.decisions[remoteId]; | DecisionResultHandle resultHandle = this.decisions[remoteId]; | ||||
if (!validateAndRecordDecision(initDecision, resultHandle)) { | if (!validateAndRecordDecision(initDecision, resultHandle)) { | ||||
// 签名无效; | // 签名无效; | ||||
@@ -1,9 +1,12 @@ | |||||
package test.com.jd.blockchain.intgr.initializer; | |||||
package test.com.jd.blockchain.tools.initializer; | |||||
import static org.junit.Assert.*; | import static org.junit.Assert.*; | ||||
import java.io.IOException; | import java.io.IOException; | ||||
import java.io.InputStream; | import java.io.InputStream; | ||||
import java.text.ParseException; | |||||
import java.text.SimpleDateFormat; | |||||
import java.util.Date; | |||||
import com.jd.blockchain.crypto.AddressEncoding; | import com.jd.blockchain.crypto.AddressEncoding; | ||||
import org.junit.Test; | import org.junit.Test; | ||||
@@ -14,12 +17,21 @@ import com.jd.blockchain.tools.initializer.LedgerInitProperties; | |||||
import com.jd.blockchain.tools.initializer.LedgerInitProperties.ConsensusParticipantConfig; | import com.jd.blockchain.tools.initializer.LedgerInitProperties.ConsensusParticipantConfig; | ||||
import com.jd.blockchain.tools.keygen.KeyGenCommand; | import com.jd.blockchain.tools.keygen.KeyGenCommand; | ||||
import com.jd.blockchain.utils.codec.HexUtils; | import com.jd.blockchain.utils.codec.HexUtils; | ||||
import test.com.jd.blockchain.intgr.IntegrationBase; | |||||
public class LedgerInitPropertiesTest { | public class LedgerInitPropertiesTest { | ||||
private static String expectedCreatedTimeStr = "2019-08-01 14:26:58.069+0800"; | |||||
@Test | @Test | ||||
public void test() throws IOException { | |||||
public void testTimeFormat() throws ParseException { | |||||
SimpleDateFormat timeFormat = new SimpleDateFormat(LedgerInitProperties.CREATED_TIME_FORMAT); | |||||
Date time = timeFormat.parse(expectedCreatedTimeStr); | |||||
String actualTimeStr = timeFormat.format(time); | |||||
assertEquals(expectedCreatedTimeStr, actualTimeStr); | |||||
} | |||||
@Test | |||||
public void testProperties() throws IOException, ParseException { | |||||
ClassPathResource ledgerInitSettingResource = new ClassPathResource("ledger.init"); | ClassPathResource ledgerInitSettingResource = new ClassPathResource("ledger.init"); | ||||
InputStream in = ledgerInitSettingResource.getInputStream(); | InputStream in = ledgerInitSettingResource.getInputStream(); | ||||
try { | try { | ||||
@@ -30,6 +42,13 @@ public class LedgerInitPropertiesTest { | |||||
String actualLedgerSeed = HexUtils.encode(initProps.getLedgerSeed()); | String actualLedgerSeed = HexUtils.encode(initProps.getLedgerSeed()); | ||||
assertEquals(expectedLedgerSeed, actualLedgerSeed); | assertEquals(expectedLedgerSeed, actualLedgerSeed); | ||||
SimpleDateFormat timeFormat = new SimpleDateFormat(LedgerInitProperties.CREATED_TIME_FORMAT); | |||||
long expectedTs = timeFormat.parse(expectedCreatedTimeStr).getTime(); | |||||
assertEquals(expectedTs, initProps.getCreatedTime()); | |||||
String createdTimeStr = timeFormat.format(new Date(initProps.getCreatedTime())); | |||||
assertEquals(expectedCreatedTimeStr, createdTimeStr); | |||||
assertEquals("com.jd.blockchain.consensus.bftsmart.BftsmartConsensusProvider", | assertEquals("com.jd.blockchain.consensus.bftsmart.BftsmartConsensusProvider", | ||||
initProps.getConsensusProvider()); | initProps.getConsensusProvider()); | ||||
@@ -61,7 +80,7 @@ public class LedgerInitPropertiesTest { | |||||
@Test | @Test | ||||
public void testPubKeyAddress() { | public void testPubKeyAddress() { | ||||
String[] pubKeys = IntegrationBase.PUB_KEYS; | |||||
String[] pubKeys = TestConsts.PUB_KEYS; | |||||
int index = 0; | int index = 0; | ||||
for (String pubKeyStr : pubKeys) { | for (String pubKeyStr : pubKeys) { | ||||
System.out.println("[" + index + "][配置] = " + pubKeyStr); | System.out.println("[" + index + "][配置] = " + pubKeyStr); |
@@ -0,0 +1,37 @@ | |||||
/** | |||||
* Copyright: Copyright 2016-2020 JD.COM All Right Reserved | |||||
* FileName: test.com.jd.blockchain.intgr.perf.IntegrationBase | |||||
* Author: shaozhuguang | |||||
* Department: 区块链研发部 | |||||
* Date: 2018/12/25 下午3:40 | |||||
* Description: | |||||
*/ | |||||
package test.com.jd.blockchain.tools.initializer; | |||||
import java.util.concurrent.atomic.AtomicLong; | |||||
import com.jd.blockchain.binaryproto.DataContractRegistry; | |||||
import com.jd.blockchain.ledger.LedgerInitOperation; | |||||
import com.jd.blockchain.ledger.UserRegisterOperation; | |||||
public class TestConsts { | |||||
static { | |||||
DataContractRegistry.register(LedgerInitOperation.class); | |||||
DataContractRegistry.register(UserRegisterOperation.class); | |||||
} | |||||
public static final String PASSWORD = "abc"; | |||||
public static final String[] PUB_KEYS = { "3snPdw7i7PjVKiTH2VnXZu5H8QmNaSXpnk4ei533jFpuifyjS5zzH9", | |||||
"3snPdw7i7PajLB35tEau1kmixc6ZrjLXgxwKbkv5bHhP7nT5dhD9eX", | |||||
"3snPdw7i7PZi6TStiyc6mzjprnNhgs2atSGNS8wPYzhbKaUWGFJt7x", | |||||
"3snPdw7i7PifPuRX7fu3jBjsb3rJRfDe9GtbDfvFJaJ4V4hHXQfhwk" }; | |||||
public static final String[] PRIV_KEYS = { | |||||
"177gjzHTznYdPgWqZrH43W3yp37onm74wYXT4v9FukpCHBrhRysBBZh7Pzdo5AMRyQGJD7x", | |||||
"177gju9p5zrNdHJVEQnEEKF4ZjDDYmAXyfG84V5RPGVc5xFfmtwnHA7j51nyNLUFffzz5UT", | |||||
"177gjtwLgmSx5v1hFb46ijh7L9kdbKUpJYqdKVf9afiEmAuLgo8Rck9yu5UuUcHknWJuWaF", | |||||
"177gk1pudweTq5zgJTh8y3ENCTwtSFsKyX7YnpuKPo7rKgCkCBXVXh5z2syaTCPEMbuWRns" }; | |||||
} |
@@ -0,0 +1,144 @@ | |||||
# Copyright (c) 2007-2013 Alysson Bessani, Eduardo Alchieri, Paulo Sousa, and the authors indicated in the @author tags | |||||
# | |||||
# Licensed under the Apache License, Version 2.0 (the "License"); | |||||
# you may not use this file except in compliance with the License. | |||||
# You may obtain a copy of the License at | |||||
# | |||||
# http://www.apache.org/licenses/LICENSE-2.0 | |||||
# | |||||
# Unless required by applicable law or agreed to in writing, software | |||||
# distributed under the License is distributed on an "AS IS" BASIS, | |||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||||
# See the License for the specific language governing permissions and | |||||
# limitations under the License. | |||||
############################################ | |||||
####### Communication Configurations ####### | |||||
############################################ | |||||
#HMAC algorithm used to authenticate messages between processes (HmacMD5 is the default value) | |||||
#This parameter is not currently being used being used | |||||
#system.authentication.hmacAlgorithm = HmacSHA1 | |||||
#Specify if the communication system should use a thread to send data (true or false) | |||||
system.communication.useSenderThread = true | |||||
#Force all processes to use the same public/private keys pair and secret key. This is useful when deploying experiments | |||||
#and benchmarks, but must not be used in production systems. | |||||
system.communication.defaultkeys = true | |||||
############################################ | |||||
### Replication Algorithm Configurations ### | |||||
############################################ | |||||
#Timeout to asking for a client request | |||||
system.totalordermulticast.timeout = 2000 | |||||
#Maximum batch size (in number of messages) | |||||
system.totalordermulticast.maxbatchsize = 400 | |||||
#Number of nonces (for non-determinism actions) generated | |||||
system.totalordermulticast.nonces = 10 | |||||
#if verification of leader-generated timestamps are increasing | |||||
#it can only be used on systems in which the network clocks | |||||
#are synchronized | |||||
system.totalordermulticast.verifyTimestamps = false | |||||
#Quantity of messages that can be stored in the receive queue of the communication system | |||||
system.communication.inQueueSize = 500000 | |||||
# Quantity of messages that can be stored in the send queue of each replica | |||||
system.communication.outQueueSize = 500000 | |||||
#Set to 1 if SMaRt should use signatures, set to 0 if otherwise | |||||
system.communication.useSignatures = 0 | |||||
#Set to 1 if SMaRt should use MAC's, set to 0 if otherwise | |||||
system.communication.useMACs = 1 | |||||
#Set to 1 if SMaRt should use the standard output to display debug messages, set to 0 if otherwise | |||||
system.debug = 0 | |||||
#Print information about the replica when it is shutdown | |||||
system.shutdownhook = true | |||||
############################################ | |||||
###### State Transfer Configurations ####### | |||||
############################################ | |||||
#Activate the state transfer protocol ('true' to activate, 'false' to de-activate) | |||||
system.totalordermulticast.state_transfer = true | |||||
#Maximum ahead-of-time message not discarded | |||||
system.totalordermulticast.highMark = 10000 | |||||
#Maximum ahead-of-time message not discarded when the replica is still on EID 0 (after which the state transfer is triggered) | |||||
system.totalordermulticast.revival_highMark = 10 | |||||
#Number of ahead-of-time messages necessary to trigger the state transfer after a request timeout occurs | |||||
system.totalordermulticast.timeout_highMark = 200 | |||||
############################################ | |||||
###### Log and Checkpoint Configurations ### | |||||
############################################ | |||||
system.totalordermulticast.log = true | |||||
system.totalordermulticast.log_parallel = false | |||||
system.totalordermulticast.log_to_disk = false | |||||
system.totalordermulticast.sync_log = false | |||||
#Period at which BFT-SMaRt requests the state to the application (for the state transfer state protocol) | |||||
system.totalordermulticast.checkpoint_period = 1000 | |||||
system.totalordermulticast.global_checkpoint_period = 120000 | |||||
system.totalordermulticast.checkpoint_to_disk = false | |||||
system.totalordermulticast.sync_ckp = false | |||||
############################################ | |||||
###### Reconfiguration Configurations ###### | |||||
############################################ | |||||
#The ID of the trust third party (TTP) | |||||
system.ttp.id = 7002 | |||||
#This sets if the system will function in Byzantine or crash-only mode. Set to "true" to support Byzantine faults | |||||
system.bft = true | |||||
#Custom View Storage; | |||||
#view.storage.handler=bftsmart.reconfiguration.views.DefaultViewStorage | |||||
#Number of servers in the group | |||||
system.servers.num = 4 | |||||
#Maximum number of faulty replicas | |||||
system.servers.f = 1 | |||||
#Replicas ID for the initial view, separated by a comma. | |||||
# The number of replicas in this parameter should be equal to that specified in 'system.servers.num' | |||||
system.initial.view = 0,1,2,3 | |||||
#Configuration of all node servers; | |||||
#PubKey of node server with specified ID, with base58 encoding. | |||||
system.server.0.pubkey= | |||||
system.server.0.network.host=127.0.0.1 | |||||
system.server.0.network.port=8900 | |||||
system.server.0.network.secure=false | |||||
system.server.1.pubkey= | |||||
system.server.1.network.host=127.0.0.1 | |||||
system.server.1.network.port=8910 | |||||
system.server.1.network.secure=false | |||||
system.server.2.pubkey= | |||||
system.server.2.network.host=127.0.0.1 | |||||
system.server.2.network.port=8920 | |||||
system.server.2.network.secure=false | |||||
system.server.3.pubkey= | |||||
system.server.3.network.host=127.0.0.1 | |||||
system.server.3.network.port=8920 | |||||
system.server.3.network.secure=false |
@@ -0,0 +1 @@ | |||||
3snPdw7i7PZi6TStiyc6mzjprnNhgs2atSGNS8wPYzhbKaUWGFJt7x |
@@ -5,6 +5,20 @@ ledger.seed=932dfe23-fe23232f-283f32fa-dd32aa76-8322ca2f-56236cda-7136b322-cb323 | |||||
#账本的描述名称;此属性不参与共识,仅仅在当前参与方的本地节点用于描述用途; | #账本的描述名称;此属性不参与共识,仅仅在当前参与方的本地节点用于描述用途; | ||||
ledger.name= | ledger.name= | ||||
#声明的账本创建时间;格式为 “yyyy-MM-dd HH:mm:ss.SSSZ”,表示”年-月-日 时:分:秒:毫秒时区“;例如:“2019-08-01 14:26:58.069+0800”,其中,+0800 表示时区是东8区 | |||||
created-time=2019-08-01 14:26:58.069+0800 | |||||
#共识服务提供者;必须; | |||||
consensus.service-provider=com.jd.blockchain.consensus.bftsmart.BftsmartConsensusProvider | |||||
#共识服务的参数配置;必须; | |||||
consensus.conf=classpath:bftsmart.config | |||||
#密码服务提供者列表,以英文逗点“,”分隔;必须; | |||||
crypto.service-providers=com.jd.blockchain.crypto.service.classic.ClassicCryptoService, \ | |||||
com.jd.blockchain.crypto.service.sm.SMCryptoService | |||||
#参与方的个数,后续以 cons_parti.id 分别标识每一个参与方的配置; | #参与方的个数,后续以 cons_parti.id 分别标识每一个参与方的配置; | ||||
cons_parti.count=4 | cons_parti.count=4 | ||||
@@ -13,7 +27,7 @@ cons_parti.0.name=jd.com | |||||
#第0个参与方的公钥文件路径; | #第0个参与方的公钥文件路径; | ||||
cons_parti.0.pubkey-path=keys/jd-com.pub | cons_parti.0.pubkey-path=keys/jd-com.pub | ||||
#第0个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | #第0个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | ||||
cons_parti.0.pubkey=endPsK36koyFr1D245Sa9j83vt6pZUdFBJoJRB3xAsWM6cwhRbna | |||||
cons_parti.0.pubkey=3snPdw7i7PjVKiTH2VnXZu5H8QmNaSXpnk4ei533jFpuifyjS5zzH9 | |||||
#第0个参与方的共识服务的主机地址; | #第0个参与方的共识服务的主机地址; | ||||
cons_parti.0.consensus.host=127.0.0.1 | cons_parti.0.consensus.host=127.0.0.1 | ||||
#第0个参与方的共识服务的端口; | #第0个参与方的共识服务的端口; | ||||
@@ -32,7 +46,7 @@ cons_parti.1.name=at.com | |||||
#第1个参与方的公钥文件路径; | #第1个参与方的公钥文件路径; | ||||
cons_parti.1.pubkey-path=keys/at-com.pub | cons_parti.1.pubkey-path=keys/at-com.pub | ||||
#第1个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | #第1个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | ||||
cons_parti.1.pubkey=endPsK36sC5JdPCDPDAXUwZtS3sxEmqEhFcC4whayAsTTh8Z6eoZ | |||||
cons_parti.1.pubkey=3snPdw7i7PajLB35tEau1kmixc6ZrjLXgxwKbkv5bHhP7nT5dhD9eX | |||||
#第1个参与方的共识服务的主机地址; | #第1个参与方的共识服务的主机地址; | ||||
cons_parti.1.consensus.host=127.0.0.1 | cons_parti.1.consensus.host=127.0.0.1 | ||||
#第1个参与方的共识服务的端口; | #第1个参与方的共识服务的端口; | ||||
@@ -49,9 +63,9 @@ cons_parti.1.initializer.secure=false | |||||
#第2个参与方的名称; | #第2个参与方的名称; | ||||
cons_parti.2.name=bt.com | cons_parti.2.name=bt.com | ||||
#第2个参与方的公钥文件路径; | #第2个参与方的公钥文件路径; | ||||
cons_parti.2.pubkey-path=keys/bt-com.pub | |||||
cons_parti.2.pubkey-path=classpath:keys/parti2.pub | |||||
#第2个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | #第2个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | ||||
cons_parti.2.pubkey=endPsK36jEG281HMHeh6oSqzqLkT95DTnCM6REDURjdb2c67uR3R | |||||
cons_parti.2.pubkey= | |||||
#第2个参与方的共识服务的主机地址; | #第2个参与方的共识服务的主机地址; | ||||
cons_parti.2.consensus.host=127.0.0.1 | cons_parti.2.consensus.host=127.0.0.1 | ||||
#第2个参与方的共识服务的端口; | #第2个参与方的共识服务的端口; | ||||
@@ -70,7 +84,7 @@ cons_parti.3.name=xt.com | |||||
#第3个参与方的公钥文件路径; | #第3个参与方的公钥文件路径; | ||||
cons_parti.3.pubkey-path=keys/xt-com.pub | cons_parti.3.pubkey-path=keys/xt-com.pub | ||||
#第3个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | #第3个参与方的公钥内容(由keygen工具生成);此参数优先于 pubkey-path 参数; | ||||
cons_parti.3.pubkey=endPsK36nse1dck4uF19zPvAMijCV336Y3zWdgb4rQG8QoRj5ktR | |||||
cons_parti.3.pubkey=3snPdw7i7PifPuRX7fu3jBjsb3rJRfDe9GtbDfvFJaJ4V4hHXQfhwk | |||||
#第3个参与方的共识服务的主机地址; | #第3个参与方的共识服务的主机地址; | ||||
cons_parti.3.consensus.host=127.0.0.1 | cons_parti.3.consensus.host=127.0.0.1 | ||||
#第3个参与方的共识服务的端口; | #第3个参与方的共识服务的端口; | ||||