mirror of https://github.com/hyperledger/besu
Clique block period transition (#6596)
Add BFT-style transitions to Clique, modelled with ForksSchedule<CliqueConfigOptions> Add ability to transition the blockperiodseconds config. --------- Signed-off-by: Jason Frame <jason.frame@consensys.net> Signed-off-by: Simon Dudley <simon.dudley@consensys.net> Co-authored-by: Jason Frame <jason.frame@consensys.net>pull/6642/head
parent
647750c201
commit
0e3d2f47d7
@ -0,0 +1,66 @@ |
||||
/* |
||||
* Copyright Hyperledger Besu Contributors. |
||||
* |
||||
* 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. |
||||
* |
||||
* SPDX-License-Identifier: Apache-2.0 |
||||
*/ |
||||
package org.hyperledger.besu.config; |
||||
|
||||
import java.util.OptionalInt; |
||||
|
||||
import com.fasterxml.jackson.annotation.JsonCreator; |
||||
import com.fasterxml.jackson.databind.node.ObjectNode; |
||||
|
||||
/** The Clique fork. */ |
||||
public class CliqueFork implements Fork { |
||||
|
||||
/** The constant FORK_BLOCK_KEY. */ |
||||
public static final String FORK_BLOCK_KEY = "block"; |
||||
|
||||
/** The constant BLOCK_PERIOD_SECONDS_KEY. */ |
||||
public static final String BLOCK_PERIOD_SECONDS_KEY = "blockperiodseconds"; |
||||
|
||||
/** The Fork config root. */ |
||||
protected final ObjectNode forkConfigRoot; |
||||
|
||||
/** |
||||
* Instantiates a new Clique fork. |
||||
* |
||||
* @param forkConfigRoot the fork config root |
||||
*/ |
||||
@JsonCreator |
||||
public CliqueFork(final ObjectNode forkConfigRoot) { |
||||
this.forkConfigRoot = forkConfigRoot; |
||||
} |
||||
|
||||
/** |
||||
* Gets fork block. |
||||
* |
||||
* @return the fork block |
||||
*/ |
||||
@Override |
||||
public long getForkBlock() { |
||||
return JsonUtil.getLong(forkConfigRoot, FORK_BLOCK_KEY) |
||||
.orElseThrow( |
||||
() -> |
||||
new IllegalArgumentException( |
||||
"Fork block not specified for Clique fork in custom forks")); |
||||
} |
||||
|
||||
/** |
||||
* Gets block period seconds. |
||||
* |
||||
* @return the block period seconds |
||||
*/ |
||||
public OptionalInt getBlockPeriodSeconds() { |
||||
return JsonUtil.getPositiveInt(forkConfigRoot, BLOCK_PERIOD_SECONDS_KEY); |
||||
} |
||||
} |
@ -0,0 +1,27 @@ |
||||
/* |
||||
* Copyright Hyperledger Besu Contributors. |
||||
* |
||||
* 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. |
||||
* |
||||
* SPDX-License-Identifier: Apache-2.0 |
||||
*/ |
||||
|
||||
package org.hyperledger.besu.config; |
||||
|
||||
/** A "custom hard fork" used for Proof of Authority network Transitions */ |
||||
public interface Fork { |
||||
|
||||
/** |
||||
* The block number at which the fork occurs. |
||||
* |
||||
* @return the block number at which the fork occurs |
||||
*/ |
||||
long getForkBlock(); |
||||
} |
@ -0,0 +1,90 @@ |
||||
/* |
||||
* Copyright Hyperledger Besu Contributors. |
||||
* |
||||
* 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. |
||||
* |
||||
* SPDX-License-Identifier: Apache-2.0 |
||||
*/ |
||||
package org.hyperledger.besu.config; |
||||
|
||||
import java.util.Map; |
||||
|
||||
import com.fasterxml.jackson.databind.node.ObjectNode; |
||||
import com.google.common.collect.ImmutableMap; |
||||
|
||||
/** The Clique config options. */ |
||||
public class JsonCliqueConfigOptions implements CliqueConfigOptions { |
||||
|
||||
private static final long DEFAULT_EPOCH_LENGTH = 30_000; |
||||
private static final int DEFAULT_BLOCK_PERIOD_SECONDS = 15; |
||||
private static final boolean DEFAULT_CREATE_EMPTY_BLOCKS = true; |
||||
|
||||
private final ObjectNode cliqueConfigRoot; |
||||
|
||||
/** The constant DEFAULT. */ |
||||
public static final JsonCliqueConfigOptions DEFAULT = |
||||
new JsonCliqueConfigOptions(JsonUtil.createEmptyObjectNode()); |
||||
|
||||
/** |
||||
* Instantiates a new Clique config options. |
||||
* |
||||
* @param cliqueConfigRoot the clique config root |
||||
*/ |
||||
JsonCliqueConfigOptions(final ObjectNode cliqueConfigRoot) { |
||||
this.cliqueConfigRoot = cliqueConfigRoot; |
||||
} |
||||
|
||||
/** |
||||
* The number of blocks in an epoch. |
||||
* |
||||
* @return the epoch length |
||||
*/ |
||||
@Override |
||||
public long getEpochLength() { |
||||
return JsonUtil.getLong(cliqueConfigRoot, "epochlength", DEFAULT_EPOCH_LENGTH); |
||||
} |
||||
|
||||
/** |
||||
* Gets block period seconds. |
||||
* |
||||
* @return the block period seconds |
||||
*/ |
||||
@Override |
||||
public int getBlockPeriodSeconds() { |
||||
return JsonUtil.getPositiveInt( |
||||
cliqueConfigRoot, "blockperiodseconds", DEFAULT_BLOCK_PERIOD_SECONDS); |
||||
} |
||||
|
||||
/** |
||||
* Whether the creation of empty blocks is allowed. |
||||
* |
||||
* @return the create empty block status |
||||
*/ |
||||
@Override |
||||
public boolean getCreateEmptyBlocks() { |
||||
return JsonUtil.getBoolean(cliqueConfigRoot, "createemptyblocks", DEFAULT_CREATE_EMPTY_BLOCKS); |
||||
} |
||||
|
||||
/** |
||||
* As map. |
||||
* |
||||
* @return the map |
||||
*/ |
||||
@Override |
||||
public Map<String, Object> asMap() { |
||||
return ImmutableMap.of( |
||||
"epochLength", |
||||
getEpochLength(), |
||||
"blockPeriodSeconds", |
||||
getBlockPeriodSeconds(), |
||||
"createemptyblocks", |
||||
getCreateEmptyBlocks()); |
||||
} |
||||
} |
@ -0,0 +1,49 @@ |
||||
/* |
||||
* Copyright Hyperledger Besu Contributors. |
||||
* |
||||
* 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. |
||||
* |
||||
* SPDX-License-Identifier: Apache-2.0 |
||||
*/ |
||||
package org.hyperledger.besu.consensus.clique; |
||||
|
||||
import org.hyperledger.besu.config.CliqueConfigOptions; |
||||
import org.hyperledger.besu.config.CliqueFork; |
||||
import org.hyperledger.besu.config.GenesisConfigOptions; |
||||
import org.hyperledger.besu.config.ImmutableCliqueConfigOptions; |
||||
import org.hyperledger.besu.consensus.common.ForkSpec; |
||||
import org.hyperledger.besu.consensus.common.ForksSchedule; |
||||
import org.hyperledger.besu.consensus.common.ForksScheduleFactory; |
||||
|
||||
/** The Clique forks schedules factory. */ |
||||
public class CliqueForksSchedulesFactory { |
||||
|
||||
/** |
||||
* Create forks schedule. |
||||
* |
||||
* @param genesisConfig the genesis config |
||||
* @return the forks schedule |
||||
*/ |
||||
public static ForksSchedule<CliqueConfigOptions> create( |
||||
final GenesisConfigOptions genesisConfig) { |
||||
return ForksScheduleFactory.create( |
||||
genesisConfig.getCliqueConfigOptions(), |
||||
genesisConfig.getTransitions().getCliqueForks(), |
||||
CliqueForksSchedulesFactory::createCliqueConfigOptions); |
||||
} |
||||
|
||||
private static CliqueConfigOptions createCliqueConfigOptions( |
||||
final ForkSpec<CliqueConfigOptions> lastSpec, final CliqueFork fork) { |
||||
|
||||
var options = ImmutableCliqueConfigOptions.builder().from(lastSpec.getValue()); |
||||
fork.getBlockPeriodSeconds().ifPresent(options::blockPeriodSeconds); |
||||
return options.build(); |
||||
} |
||||
} |
Loading…
Reference in new issue