-
Notifications
You must be signed in to change notification settings - Fork 22
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Denylist reload #101
base: main
Are you sure you want to change the base?
Denylist reload #101
Changes from all commits
a25f5bb
4196abe
188cd89
3e6178f
f74742d
7971dc2
7546f24
8182b42
5d21427
8f77454
20389b8
0414f94
b84653f
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,142 @@ | ||
/* | ||
* Copyright Consensys Software Inc. | ||
* | ||
* 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 linea.plugin.acc.test; | ||
|
||
import static org.assertj.core.api.Assertions.assertThat; | ||
|
||
import java.io.IOException; | ||
import java.math.BigInteger; | ||
import java.nio.file.Files; | ||
import java.nio.file.Path; | ||
import java.util.List; | ||
|
||
import org.hyperledger.besu.tests.acceptance.dsl.account.Accounts; | ||
import org.hyperledger.besu.tests.acceptance.dsl.transaction.NodeRequests; | ||
import org.hyperledger.besu.tests.acceptance.dsl.transaction.Transaction; | ||
import org.junit.jupiter.api.Test; | ||
import org.junit.jupiter.api.io.TempDir; | ||
import org.web3j.crypto.Credentials; | ||
import org.web3j.protocol.Web3j; | ||
import org.web3j.protocol.core.Request; | ||
import org.web3j.protocol.core.methods.response.EthSendTransaction; | ||
import org.web3j.tx.RawTransactionManager; | ||
import org.web3j.utils.Convert; | ||
|
||
public class TransactionPoolDenyListReloadTest extends LineaPluginTestBase { | ||
|
||
private static final BigInteger GAS_PRICE = Convert.toWei("20", Convert.Unit.GWEI).toBigInteger(); | ||
private static final BigInteger GAS_LIMIT = BigInteger.valueOf(210000); | ||
private static final BigInteger VALUE = BigInteger.ONE; // 1 wei | ||
|
||
final Credentials notDenied = Credentials.create(Accounts.GENESIS_ACCOUNT_ONE_PRIVATE_KEY); | ||
final Credentials willBeDenied = Credentials.create(Accounts.GENESIS_ACCOUNT_TWO_PRIVATE_KEY); | ||
|
||
@TempDir static Path tempDir; | ||
static Path tempDenyList; | ||
|
||
@Override | ||
public List<String> getTestCliOptions() { | ||
tempDenyList = tempDir.resolve("denyList.txt"); | ||
if (!Files.exists(tempDenyList)) { | ||
|
||
try { | ||
Files.createFile(tempDenyList); | ||
} catch (IOException e) { | ||
throw new RuntimeException(e); | ||
} | ||
} | ||
return new TestCommandLineOptionsBuilder() | ||
.set("--plugin-linea-deny-list-path=", tempDenyList.toString()) | ||
.build(); | ||
} | ||
|
||
@Test | ||
public void emptyDenyList() throws Exception { | ||
final Web3j miner = minerNode.nodeRequests().eth(); | ||
|
||
RawTransactionManager transactionManager = | ||
new RawTransactionManager(miner, willBeDenied, CHAIN_ID); | ||
assertAddressAllowed(transactionManager, willBeDenied.getAddress()); | ||
} | ||
|
||
@Test | ||
public void emptyDenyList_thenDenySender_cannotAddTxToPool() throws Exception { | ||
final Web3j miner = minerNode.nodeRequests().eth(); | ||
RawTransactionManager transactionManager = | ||
new RawTransactionManager(miner, willBeDenied, CHAIN_ID); | ||
|
||
assertAddressAllowed(transactionManager, willBeDenied.getAddress()); | ||
|
||
addAddressToDenyList(willBeDenied.getAddress()); | ||
reloadPluginConfig(); | ||
|
||
assertAddressNotAllowed(transactionManager, willBeDenied.getAddress()); | ||
} | ||
|
||
private void addAddressToDenyList(final String address) throws IOException { | ||
Files.writeString(tempDenyList, address); | ||
} | ||
|
||
private void assertAddressAllowed( | ||
final RawTransactionManager transactionManager, final String address) throws IOException { | ||
EthSendTransaction transactionResponse = | ||
transactionManager.sendTransaction(GAS_PRICE, GAS_LIMIT, address, "", VALUE); | ||
assertThat(transactionResponse.getTransactionHash()).isNotNull(); | ||
assertThat(transactionResponse.getError()).isNull(); | ||
} | ||
|
||
private void assertAddressNotAllowed( | ||
final RawTransactionManager transactionManager, final String address) throws IOException { | ||
EthSendTransaction transactionResponse = | ||
transactionManager.sendTransaction(GAS_PRICE, GAS_LIMIT, address, "", VALUE); | ||
|
||
assertThat(transactionResponse.getTransactionHash()).isNull(); | ||
assertThat(transactionResponse.getError().getMessage()) | ||
.isEqualTo( | ||
"sender " | ||
+ address | ||
+ " is blocked as appearing on the SDN or other legally prohibited list"); | ||
} | ||
|
||
private void reloadPluginConfig() { | ||
final var reqLinea = new ReloadPluginConfigRequest(); | ||
final var respLinea = reqLinea.execute(minerNode.nodeRequests()); | ||
assertThat(respLinea).isEqualTo("Success"); | ||
} | ||
|
||
static class ReloadPluginConfigRequest implements Transaction<String> { | ||
|
||
public ReloadPluginConfigRequest() {} | ||
|
||
@Override | ||
public String execute(final NodeRequests nodeRequests) { | ||
try { | ||
// plugin name is class name | ||
return new Request<>( | ||
"plugins_reloadPluginConfig", | ||
List.of( | ||
"net.consensys.linea.sequencer.txpoolvalidation.LineaTransactionPoolValidatorPlugin"), | ||
nodeRequests.getWeb3jService(), | ||
ReloadPluginConfigResponse.class) | ||
.send() | ||
.getResult(); | ||
} catch (IOException e) { | ||
throw new RuntimeException(e); | ||
} | ||
} | ||
} | ||
|
||
static class ReloadPluginConfigResponse extends org.web3j.protocol.core.Response<String> {} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -22,6 +22,7 @@ | |
import java.nio.file.Path; | ||
import java.util.Optional; | ||
import java.util.Set; | ||
import java.util.concurrent.CompletableFuture; | ||
import java.util.stream.Collectors; | ||
import java.util.stream.Stream; | ||
|
||
|
@@ -81,7 +82,10 @@ public void doRegister(final BesuContext context) { | |
@Override | ||
public void start() { | ||
super.start(); | ||
loadDenyListAndRegisterPluginTxValidatorFactory(); | ||
} | ||
|
||
private void loadDenyListAndRegisterPluginTxValidatorFactory() { | ||
try (Stream<String> lines = | ||
Files.lines( | ||
Path.of(new File(transactionPoolValidatorConfiguration().denyListPath()).toURI()))) { | ||
|
@@ -118,6 +122,12 @@ public void start() { | |
} | ||
} | ||
|
||
@Override | ||
public CompletableFuture<Void> reloadConfiguration() { | ||
loadDenyListAndRegisterPluginTxValidatorFactory(); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. need to look at rejectedTxJsonRpcManager - may need to do something different with that re start/stop lifecycle There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
return CompletableFuture.completedFuture(null); | ||
} | ||
|
||
@Override | ||
public void stop() { | ||
super.stop(); | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if plugin name == class name this extra logging may not be useful