@Test public void testWorkflow() { assertThat(idsToNames.getNextId()).isEqualTo(1); assertThat(idsToNames.get(1)).isEmpty(); assertThat(idsToNames.storeNewMapping(tableRef(0), 1)).isTrue(); assertThat(idsToNames.storeNewMapping(tableRef(1), 1)).isFalse(); assertThat(idsToNames.get(1)).contains(tableRef(0)); assertThat(idsToNames.getNextId()).isEqualTo(2); assertThat(idsToNames.storeNewMapping(tableRef(1), 2)).isTrue(); assertThat(idsToNames.getNextId()).isEqualTo(3); }
@Test public void testConcurrentCreationOfDifferentTable() { idsToNames.storeNewMapping(table(2), 1); assertThat(tableIndices.getTableId(table(1))).isEqualTo(2); }
@Test public void testConcurrentCreationOfMultipleTables() { namesToIds.storeAsPending(table(1), 1); idsToNames.storeNewMapping(table(2), 1); assertThat(tableIndices.getTableId(table(1))).isEqualTo(2); }
private int loadUncached(TableReference table) { while (true) { Optional<SweepTableIdentifier> identifier = namesToIds.currentMapping(table); if (identifier.isPresent() && !identifier.get().isPending()) { return identifier.get().identifier(); } log.info("Assigning table {} an identifier", LoggingArgs.tableRef(table)); // note - the second time through the loop this will fail, since on those iterations we're // doing our updates as CAS (at the bottom) not PUE, but it doubles as a get SweepTableIdentifier afterPendingPut = namesToIds.storeAsPending(table, idToNames.getNextId()); if (!afterPendingPut.isPending()) { log.info("Assigned table {} to id {}", LoggingArgs.tableRef(table), SafeArg.of("id", afterPendingPut.identifier())); return afterPendingPut.identifier(); } boolean assigmentWasSuccessful = idToNames.storeNewMapping(table, afterPendingPut.identifier()); if (assigmentWasSuccessful) { namesToIds.moveToComplete(table, afterPendingPut.identifier()); log.info("Assigned table {} to id {}", LoggingArgs.tableRef(table), SafeArg.of("id", afterPendingPut.identifier())); return afterPendingPut.identifier(); } // B namesToIds.storeAsPending(table, afterPendingPut.identifier(), idToNames.getNextId()); } } }
private int loadUncached(TableReference table) { while (true) { Optional<SweepTableIdentifier> identifier = namesToIds.currentMapping(table); if (identifier.isPresent() && !identifier.get().isPending()) { return identifier.get().identifier(); } log.info("Assigning table {} an identifier", LoggingArgs.tableRef(table)); // note - the second time through the loop this will fail, since on those iterations we're // doing our updates as CAS (at the bottom) not PUE, but it doubles as a get SweepTableIdentifier afterPendingPut = namesToIds.storeAsPending(table, idToNames.getNextId()); if (!afterPendingPut.isPending()) { log.info("Assigned table {} to id {}", LoggingArgs.tableRef(table), SafeArg.of("id", afterPendingPut.identifier())); return afterPendingPut.identifier(); } boolean assigmentWasSuccessful = idToNames.storeNewMapping(table, afterPendingPut.identifier()); if (assigmentWasSuccessful) { namesToIds.moveToComplete(table, afterPendingPut.identifier()); log.info("Assigned table {} to id {}", LoggingArgs.tableRef(table), SafeArg.of("id", afterPendingPut.identifier())); return afterPendingPut.identifier(); } // B namesToIds.storeAsPending(table, afterPendingPut.identifier(), idToNames.getNextId()); } } }