diff --git a/.github/workflows/maven.yml b/.github/workflows/maven.yml index 4fed43166..4eb1c5e57 100644 --- a/.github/workflows/maven.yml +++ b/.github/workflows/maven.yml @@ -16,4 +16,4 @@ jobs: cache: 'maven' github-token: ${{ secrets.GITHUB_TOKEN }} - name: Build with Maven - run: ./mvnw -batch-mode clean install -Ppre --file pom.xml + run: ./mvnw -T 0.5C -batch-mode clean install -Ppre --file pom.xml -Dforks=2 diff --git a/.gitignore b/.gitignore index 05e6c9389..e63ce2e46 100644 --- a/.gitignore +++ b/.gitignore @@ -14,6 +14,7 @@ **/dependency-reduced-pom.xml pom.xml.bak /ff.log +chkpoint.txt ## Intellij stuff .idea diff --git a/choam/pom.xml b/choam/pom.xml index 70f417052..d4c07c80e 100644 --- a/choam/pom.xml +++ b/choam/pom.xml @@ -53,17 +53,4 @@ test - - - - - org.apache.maven.plugins - maven-surefire-plugin - - 1 - false - - - - diff --git a/choam/src/main/java/com/salesforce/apollo/choam/CHOAM.java b/choam/src/main/java/com/salesforce/apollo/choam/CHOAM.java index 21518ba43..f8385d32d 100644 --- a/choam/src/main/java/com/salesforce/apollo/choam/CHOAM.java +++ b/choam/src/main/java/com/salesforce/apollo/choam/CHOAM.java @@ -896,7 +896,6 @@ private void synchronize(SynchronizedState state) { CertifiedBlock current1; if (state.lastCheckpoint() == null) { log.info("Synchronizing from genesis: {} on: {}", state.genesis().hash, params.member().getId()); - restore(); current1 = state.genesis().certifiedBlock; } else { log.info("Synchronizing from checkpoint: {} on: {}", state.lastCheckpoint().hash, params.member().getId()); diff --git a/choam/src/main/java/com/salesforce/apollo/choam/Committee.java b/choam/src/main/java/com/salesforce/apollo/choam/Committee.java index 1d4f1ba5d..2184f2f8e 100644 --- a/choam/src/main/java/com/salesforce/apollo/choam/Committee.java +++ b/choam/src/main/java/com/salesforce/apollo/choam/Committee.java @@ -115,10 +115,10 @@ default boolean validate(HashedCertifiedBlock hb, Certification c, Map(); - final var clientCount = LARGE_TESTS ? 1_500 : 50; + final var clientCount = LARGE_TESTS ? 1_500 : 5; final var max = LARGE_TESTS ? 100 : 10; final var countdown = new CountDownLatch(clientCount * choams.size()); choams.values().forEach(c -> { diff --git a/model/src/main/java/com/salesforce/apollo/model/Domain.java b/model/src/main/java/com/salesforce/apollo/model/Domain.java index 36eb635f7..da874920f 100644 --- a/model/src/main/java/com/salesforce/apollo/model/Domain.java +++ b/model/src/main/java/com/salesforce/apollo/model/Domain.java @@ -83,7 +83,7 @@ public Domain(ControlledIdentifierMember member, Parameters.Builder params, Stri throw new IllegalArgumentException("Must be a directory: " + checkpointBaseDir); } var checkpointDir = new File(dir, qb64(member.getIdentifier().getDigest())); - sqlStateMachine = new SqlStateMachine(dbURL, new Properties(), checkpointDir); + sqlStateMachine = new SqlStateMachine(member.getId(), dbURL, new Properties(), checkpointDir); paramsClone.getProducer().ethereal().setSigner(member); this.params = paramsClone.build(runtimeClone.setCheckpointer(sqlStateMachine.getCheckpointer()) diff --git a/sql-state/pom.xml b/sql-state/pom.xml index 890ebc727..1e73a795c 100644 --- a/sql-state/pom.xml +++ b/sql-state/pom.xml @@ -84,14 +84,6 @@ org.codehaus.mojo build-helper-maven-plugin - - org.apache.maven.plugins - maven-surefire-plugin - - 1 - false - - diff --git a/sql-state/src/test/java/com/salesforce/apollo/state/AbstractLifecycleTest.java b/sql-state/src/test/java/com/salesforce/apollo/state/AbstractLifecycleTest.java index 434697fc3..e9474fc8d 100644 --- a/sql-state/src/test/java/com/salesforce/apollo/state/AbstractLifecycleTest.java +++ b/sql-state/src/test/java/com/salesforce/apollo/state/AbstractLifecycleTest.java @@ -10,7 +10,6 @@ import com.salesforce.apollo.archipelago.Router; import com.salesforce.apollo.archipelago.ServerConnectionCache; import com.salesforce.apollo.choam.CHOAM; -import com.salesforce.apollo.choam.CHOAM.TransactionExecutor; import com.salesforce.apollo.choam.Parameters; import com.salesforce.apollo.choam.Parameters.BootstrapParameters; import com.salesforce.apollo.choam.Parameters.Builder; @@ -41,8 +40,8 @@ import java.sql.Statement; import java.time.Duration; import java.util.*; -import java.util.concurrent.*; -import java.util.concurrent.atomic.AtomicInteger; +import java.util.concurrent.CountDownLatch; +import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicReference; import java.util.function.Function; import java.util.stream.Collectors; @@ -82,7 +81,6 @@ abstract public class AbstractLifecycleTest { protected final AtomicReference checkpointHeight = new AtomicReference<>(); protected final Map updaters = new HashMap<>(); private final Map parameters = new HashMap<>(); - protected Map blocks; protected CountDownLatch checkpointOccurred; protected Map choams; protected List members; @@ -134,9 +132,8 @@ public void before() throws Exception { baseDir = new File(System.getProperty("user.dir"), "target/cluster-" + Entropy.nextBitsStreamLong()); Utils.clean(baseDir); baseDir.mkdirs(); - blocks = new ConcurrentHashMap<>(); var entropy = SecureRandom.getInstance("SHA1PRNG"); - entropy.setSeed(new byte[] { 6, 6, 6 }); + entropy.setSeed(new byte[] { 6, 6, 6, disc() }); context = new DynamicContextImpl<>(DigestAlgorithm.DEFAULT.getOrigin(), CARDINALITY, 0.2, 3); toleranceLevel = context.toleranceLevel(); @@ -145,7 +142,7 @@ public void before() throws Exception { members = IntStream.range(0, CARDINALITY).mapToObj(i -> { return stereotomy.newIdentifier(); - }).map(cpk -> new ControlledIdentifierMember(cpk)).map(e -> (SigningMember) e).toList(); + }).map(cpk -> new ControlledIdentifierMember(cpk)).map(e -> (SigningMember) e).collect(Collectors.toList()); System.out.println("Members: " + members.stream().map(s -> s.getId()).toList()); members.forEach(m -> context.activate(m)); @@ -171,14 +168,16 @@ public void before() throws Exception { protected abstract int checkpointBlockSize(); + abstract protected byte disc(); + protected void post() throws Exception { - final var clearTxns = Utils.waitForCondition(120_000, 1000, () -> + final var clearTxns = Utils.waitForCondition(30_000, 1000, () -> transactioneers.stream().mapToInt(t -> t.inFlight()).filter(t -> t == 0).count() == transactioneers.size()); assertTrue(clearTxns, "Transactions did not clear: " + Collections.singletonList( transactioneers.stream().mapToInt(t -> t.inFlight()).filter(t -> t == 0).toArray())); - final var synchd = Utils.waitForCondition(120_000, 1000, () -> { + final var synchd = Utils.waitForCondition(30_000, 1000, () -> { var max = members.stream() .map(m -> updaters.get(m)) @@ -326,10 +325,9 @@ protected Txn update(Random entropy, Mutator mutator) { private CHOAM createChoam(Random entropy, Builder params, SigningMember m, boolean testSubject, Context context) { - blocks.put(m.getId(), new AtomicInteger()); String url = String.format("jdbc:h2:mem:test_engine-%s-%s", m.getId(), entropy.nextLong()); System.out.println("DB URL: " + url); - SqlStateMachine up = new SqlStateMachine(DigestAlgorithm.DEFAULT.getOrigin(), url, new Properties(), + SqlStateMachine up = new SqlStateMachine(m.getId(), url, new Properties(), new File(checkpointDirBase, m.getId().toString())); updaters.put(m, up); @@ -342,7 +340,7 @@ private CHOAM createChoam(Random entropy, Builder params, SigningMember m, boole .setCommunications(routers.get(m.getId())) .setCheckpointer(wrap(up)) .setRestorer(up.getBootstrapper()) - .setProcessor(wrap(m, up)) + .setProcessor(up.getExecutor()) .build())); } @@ -364,7 +362,6 @@ private Builder parameters(Context context) { .setGossipDuration(Duration.ofMillis(10)) .setCheckpointBlockDelta(checkpointBlockSize()) .setCheckpointSegmentSize(128); - params.getProducer().ethereal().setNumberOfEpochs(10); params.getDrainPolicy().setInitialBackoff(Duration.ofMillis(1)).setMaxBackoff(Duration.ofMillis(1)); params.getProducer().ethereal().setNumberOfEpochs(2).setEpochLength(20); @@ -372,33 +369,6 @@ private Builder parameters(Context context) { return params; } - private TransactionExecutor wrap(SigningMember m, SqlStateMachine up) { - return new TransactionExecutor() { - @Override - public void beginBlock(ULong height, Digest hash) { - blocks.get(m.getId()).incrementAndGet(); - up.getExecutor().beginBlock(height, hash); - } - - @Override - public void endBlock(ULong height, Digest hash) { - up.getExecutor().endBlock(height, hash); - } - - @Override - public void execute(int i, Digest hash, Transaction tx, - @SuppressWarnings("rawtypes") CompletableFuture onComplete, Executor executor) { - up.getExecutor().execute(i, hash, tx, onComplete, executor); - } - - @Override - public void genesis(Digest hash, List initialization) { - blocks.get(m.getId()).incrementAndGet(); - up.getExecutor().genesis(hash, initialization); - } - }; - } - private Function wrap(SqlStateMachine up) { final var checkpointer = up.getCheckpointer(); return l -> { diff --git a/sql-state/src/test/java/com/salesforce/apollo/state/CheckpointBootstrapTest.java b/sql-state/src/test/java/com/salesforce/apollo/state/CheckpointBootstrapTest.java index 294a8ab85..53f7c34d3 100644 --- a/sql-state/src/test/java/com/salesforce/apollo/state/CheckpointBootstrapTest.java +++ b/sql-state/src/test/java/com/salesforce/apollo/state/CheckpointBootstrapTest.java @@ -71,7 +71,7 @@ public void checkpointBootstrap() throws Exception { assertTrue(Utils.waitForCondition(30_000, 1_000, () -> choam.active()), "Test subject did not become active: " + choam.logState()); - + members.add(testSubject); post(); } @@ -79,4 +79,9 @@ public void checkpointBootstrap() throws Exception { protected int checkpointBlockSize() { return 3; } + + @Override + protected byte disc() { + return 1; + } } diff --git a/sql-state/src/test/java/com/salesforce/apollo/state/GenesisBootstrapTest.java b/sql-state/src/test/java/com/salesforce/apollo/state/GenesisBootstrapTest.java index 13dd31727..d8ecab38b 100644 --- a/sql-state/src/test/java/com/salesforce/apollo/state/GenesisBootstrapTest.java +++ b/sql-state/src/test/java/com/salesforce/apollo/state/GenesisBootstrapTest.java @@ -7,8 +7,11 @@ package com.salesforce.apollo.state; import com.salesforce.apollo.context.DynamicContext; +import com.salesforce.apollo.utils.Utils; import org.junit.jupiter.api.Test; +import static org.junit.jupiter.api.Assertions.assertTrue; + /** * @author hal.hildebrand */ @@ -22,6 +25,10 @@ public void genesisBootstrap() throws Exception { ((DynamicContext) choam.context().delegate()).activate(testSubject); choam.start(); routers.get(testSubject.getId()).start(); + + assertTrue(Utils.waitForCondition(30_000, 1_000, () -> choam.active()), + "Test subject did not become active: " + choam.logState()); + members.add(testSubject); post(); } @@ -29,4 +36,9 @@ public void genesisBootstrap() throws Exception { protected int checkpointBlockSize() { return 1000; } + + @Override + protected byte disc() { + return 2; + } } diff --git a/sql-state/src/test/java/com/salesforce/apollo/state/Transactioneer.java b/sql-state/src/test/java/com/salesforce/apollo/state/Transactioneer.java index da88d2fd1..19c3ded10 100644 --- a/sql-state/src/test/java/com/salesforce/apollo/state/Transactioneer.java +++ b/sql-state/src/test/java/com/salesforce/apollo/state/Transactioneer.java @@ -76,8 +76,8 @@ void decorate(CompletableFuture fs) { } catch (InvalidTransaction e) { e.printStackTrace(); } - }, log)), entropy.nextInt(100), TimeUnit.MILLISECONDS); - } else if (finished.compareAndSet(false, true)) { + }, log)), entropy.nextInt(2000), TimeUnit.MILLISECONDS); + } else { countdown.countDown(); } } diff --git a/sql-state/src/test/resources/logback-test.xml b/sql-state/src/test/resources/logback-test.xml index 3b1bf7940..eec177829 100644 --- a/sql-state/src/test/resources/logback-test.xml +++ b/sql-state/src/test/resources/logback-test.xml @@ -44,6 +44,10 @@ + + + +