Skip to content

Commit

Permalink
linea_estimateGas compatibility mode multiplier (#646)
Browse files Browse the repository at this point in the history
Signed-off-by: Fabio Di Fabio <fabio.difabio@consensys.net>
  • Loading branch information
fab-10 authored Mar 14, 2024
1 parent cdbe27b commit 07db824
Show file tree
Hide file tree
Showing 6 changed files with 74 additions and 17 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -16,30 +16,52 @@

import static org.assertj.core.api.Assertions.assertThat;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.List;

import org.hyperledger.besu.datatypes.Wei;
import org.hyperledger.besu.ethereum.core.Transaction;

public class EstimateGasCompatibilityModeTest extends EstimateGasTest {
private static final BigDecimal PRICE_MULTIPLIER = BigDecimal.valueOf(1.2);

@Override
public List<String> getTestCliOptions() {
return getTestCommandLineOptionsBuilder()
.set("--plugin-linea-estimate-gas-compatibility-mode-enabled=", "true")
.set(
"--plugin-linea-estimate-gas-compatibility-mode-multiplier=",
PRICE_MULTIPLIER.toPlainString())
.build();
}

@Override
protected void assertIsProfitable(
final Transaction tx,
final Wei baseFee,
final Wei estimatedPriorityFee,
final Wei estimatedMaxGasPrice,
final long estimatedGasLimit) {
final var minGasPrice = minerNode.getMiningParameters().getMinTransactionGasPrice();
final var minPriorityFee = minGasPrice.subtract(baseFee);
final var compatibilityMinPriorityFee =
Wei.of(
PRICE_MULTIPLIER
.multiply(new BigDecimal(minPriorityFee.getAsBigInteger()))
.setScale(0, RoundingMode.CEILING)
.toBigInteger());

// since we are in compatibility mode, we want to check that returned profitable priority fee is
// the min mineable gas price
assertThat(estimatedMaxGasPrice).isEqualTo(minGasPrice);
// the min priority fee per gas * multiplier + base fee
final var expectedMaxGasPrice = baseFee.add(compatibilityMinPriorityFee);
assertThat(estimatedMaxGasPrice).isEqualTo(expectedMaxGasPrice);
}

@Override
protected void assertMinGasPriceLowerBound(final Wei baseFee, final Wei estimatedMaxGasPrice) {
// since we are in compatibility mode, we want to check that returned profitable priority fee is
// the min priority fee per gas * multiplier + base fee
assertIsProfitable(null, baseFee, null, estimatedMaxGasPrice, 0);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@
import net.consensys.linea.bl.TransactionProfitabilityCalculator;
import net.consensys.linea.config.LineaProfitabilityCliOptions;
import net.consensys.linea.config.LineaProfitabilityConfiguration;
import net.consensys.linea.config.LineaTransactionSelectorConfiguration;
import net.consensys.linea.rpc.linea.LineaEstimateGas;
import org.apache.tuweni.bytes.Bytes;
import org.apache.tuweni.units.bigints.UInt64;
Expand All @@ -48,7 +47,6 @@ public class EstimateGasTest extends LineaPluginTestBase {
protected static final double ESTIMATE_GAS_MIN_MARGIN = 1.0;
protected static final Wei MIN_GAS_PRICE = Wei.of(1_000_000_000);
protected static final int MAX_TRANSACTION_GAS_LIMIT = 30_000_000;
protected LineaTransactionSelectorConfiguration txSelectorConf;
protected LineaProfitabilityConfiguration profitabilityConf;

@Override
Expand Down Expand Up @@ -137,11 +135,12 @@ public void lineaEstimateGasIsProfitable() {
.signature(LineaEstimateGas.FAKE_SIGNATURE_FOR_SIZE_CALCULATION)
.build();

assertIsProfitable(tx, estimatedPriorityFee, estimatedMaxGasPrice, estimatedGasLimit);
assertIsProfitable(tx, baseFee, estimatedPriorityFee, estimatedMaxGasPrice, estimatedGasLimit);
}

protected void assertIsProfitable(
final org.hyperledger.besu.ethereum.core.Transaction tx,
final Wei baseFee,
final Wei estimatedPriorityFee,
final Wei estimatedMaxGasPrice,
final long estimatedGasLimit) {
Expand Down Expand Up @@ -180,8 +179,12 @@ public void lineaEstimateGasPriorityFeeMinGasPriceLowerBound() {
final var baseFee = Wei.fromHexString(respLinea.baseFeePerGas());
final var estimatedPriorityFee = Wei.fromHexString(respLinea.priorityFeePerGas());
final var estimatedMaxGasPrice = baseFee.add(estimatedPriorityFee);
final var minGasPrice = minerNode.getMiningParameters().getMinTransactionGasPrice();

assertMinGasPriceLowerBound(baseFee, estimatedMaxGasPrice);
}

protected void assertMinGasPriceLowerBound(final Wei baseFee, final Wei estimatedMaxGasPrice) {
final var minGasPrice = minerNode.getMiningParameters().getMinTransactionGasPrice();
assertThat(estimatedMaxGasPrice).isEqualTo(minGasPrice);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,36 @@

package net.consensys.linea.config;

import java.math.BigDecimal;

import com.google.common.base.MoreObjects;
import picocli.CommandLine;

/** The Linea RPC CLI options. */
public class LineaRpcCliOptions {
private static final String ESTIMATE_GAS_COMPATIBILITY_MODE_ENABLED =
"--plugin-linea-estimate-gas-compatibility-mode-enabled";
private static final boolean DEFAULT_ESTIMATE_GAS_COMPATIBILITY_MODE_ENABLED = false;
private static final String ESTIMATE_GAS_COMPATIBILITY_MODE_MULTIPLIER =
"--plugin-linea-estimate-gas-compatibility-mode-multiplier";
private static final BigDecimal DEFAULT_ESTIMATE_GAS_COMPATIBILITY_MODE_MULTIPLIER =
BigDecimal.valueOf(1.2);

@CommandLine.Option(
names = {ESTIMATE_GAS_COMPATIBILITY_MODE_ENABLED},
paramLabel = "<BOOLEAN>",
description =
"Set to true to return the min mineable gas price, instead of the profitable price (default: ${DEFAULT-VALUE})")
private boolean estimateGasCompatibilityModeEnabled = false;
"Set to true to return the min mineable gas price * multiplier, instead of the profitable price (default: ${DEFAULT-VALUE})")
private boolean estimateGasCompatibilityModeEnabled =
DEFAULT_ESTIMATE_GAS_COMPATIBILITY_MODE_ENABLED;

@CommandLine.Option(
names = {ESTIMATE_GAS_COMPATIBILITY_MODE_MULTIPLIER},
paramLabel = "<FLOAT>",
description =
"Set to multiplier to apply to the min priority fee per gas when the compatibility mode is enabled (default: ${DEFAULT-VALUE})")
private BigDecimal estimateGasCompatibilityMultiplier =
DEFAULT_ESTIMATE_GAS_COMPATIBILITY_MODE_MULTIPLIER;

private LineaRpcCliOptions() {}

Expand All @@ -50,6 +66,7 @@ public static LineaRpcCliOptions create() {
public static LineaRpcCliOptions fromConfig(final LineaRpcConfiguration config) {
final LineaRpcCliOptions options = create();
options.estimateGasCompatibilityModeEnabled = config.estimateGasCompatibilityModeEnabled();
options.estimateGasCompatibilityMultiplier = config.estimateGasCompatibilityMultiplier();
return options;
}

Expand All @@ -61,13 +78,15 @@ public static LineaRpcCliOptions fromConfig(final LineaRpcConfiguration config)
public LineaRpcConfiguration toDomainObject() {
return LineaRpcConfiguration.builder()
.estimateGasCompatibilityModeEnabled(estimateGasCompatibilityModeEnabled)
.estimateGasCompatibilityMultiplier(estimateGasCompatibilityMultiplier)
.build();
}

@Override
public String toString() {
return MoreObjects.toStringHelper(this)
.add(ESTIMATE_GAS_COMPATIBILITY_MODE_ENABLED, estimateGasCompatibilityModeEnabled)
.add(ESTIMATE_GAS_COMPATIBILITY_MODE_MULTIPLIER, estimateGasCompatibilityMultiplier)
.toString();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,11 @@

package net.consensys.linea.config;

import java.math.BigDecimal;

import lombok.Builder;

/** The Linea RPC configuration. */
@Builder(toBuilder = true)
public record LineaRpcConfiguration(boolean estimateGasCompatibilityModeEnabled) {}
public record LineaRpcConfiguration(
boolean estimateGasCompatibilityModeEnabled, BigDecimal estimateGasCompatibilityMultiplier) {}
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,9 @@

import static org.hyperledger.besu.ethereum.api.jsonrpc.internal.results.Quantity.create;

import java.math.BigDecimal;
import java.math.BigInteger;
import java.math.RoundingMode;

import com.fasterxml.jackson.annotation.JsonProperty;
import com.google.common.annotations.VisibleForTesting;
Expand Down Expand Up @@ -112,17 +114,13 @@ public LineaEstimateGas.Response execute(final PluginRpcRequest request) {
.log();
final var estimatedGasUsed = estimateGasUsed(callParameters, transaction, minGasPrice);

final Wei profitablePriorityFee =
txProfitabilityCalculator.profitablePriorityFeePerGas(
transaction, profitabilityConf.estimateGasMinMargin(), minGasPrice, estimatedGasUsed);

final Wei baseFee =
blockchainService
.getNextBlockBaseFee()
.orElseThrow(() -> new IllegalStateException("Not on a baseFee market"));

final Wei estimatedPriorityFee =
getEstimatedPriorityFee(baseFee, profitablePriorityFee, minGasPrice);
getEstimatedPriorityFee(transaction, baseFee, minGasPrice, estimatedGasUsed);

final var response =
new Response(create(estimatedGasUsed), create(baseFee), create(estimatedPriorityFee));
Expand All @@ -132,13 +130,25 @@ public LineaEstimateGas.Response execute(final PluginRpcRequest request) {
}

private Wei getEstimatedPriorityFee(
final Wei baseFee, final Wei profitablePriorityFee, final Wei minGasPrice) {
final Transaction transaction,
final Wei baseFee,
final Wei minGasPrice,
final long estimatedGasUsed) {
final Wei priorityFeeLowerBound = minGasPrice.subtract(baseFee);

if (rpcConfiguration.estimateGasCompatibilityModeEnabled()) {
return priorityFeeLowerBound;
return Wei.of(
rpcConfiguration
.estimateGasCompatibilityMultiplier()
.multiply(new BigDecimal(priorityFeeLowerBound.getAsBigInteger()))
.setScale(0, RoundingMode.CEILING)
.toBigInteger());
}

final Wei profitablePriorityFee =
txProfitabilityCalculator.profitablePriorityFeePerGas(
transaction, profitabilityConf.estimateGasMinMargin(), minGasPrice, estimatedGasUsed);

if (profitablePriorityFee.greaterOrEqualThan(priorityFeeLowerBound)) {
return profitablePriorityFee;
}
Expand Down
2 changes: 1 addition & 1 deletion gradle/dependency-management.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,7 @@ dependencyManagement {

dependency 'com.splunk.logging:splunk-library-javalogging:1.11.5'

dependency 'io.vertx:vertx-core:4.3.8'
dependency 'io.vertx:vertx-core:4.5.4'

dependency 'com.slack.api:slack-api-client:1.32.1'

Expand Down

0 comments on commit 07db824

Please sign in to comment.