Search in sources :

Example 76 with MemoryRecords

use of org.apache.kafka.common.record.MemoryRecords in project kafka by apache.

the class KafkaRaftClientSnapshotTest method testCreateSnapshotAsFollowerWithInvalidSnapshotId.

@Test
public void testCreateSnapshotAsFollowerWithInvalidSnapshotId() throws Exception {
    int localId = 0;
    int leaderId = 1;
    int otherFollowerId = 2;
    int epoch = 5;
    Set<Integer> voters = Utils.mkSet(localId, leaderId, otherFollowerId);
    RaftClientTestContext context = new RaftClientTestContext.Builder(localId, voters).withElectedLeader(epoch, leaderId).build();
    context.assertElectedLeader(epoch, leaderId);
    // When follower creating snapshot:
    // 1) The high watermark cannot be empty
    assertEquals(OptionalLong.empty(), context.client.highWatermark());
    OffsetAndEpoch invalidSnapshotId1 = new OffsetAndEpoch(0, 0);
    assertThrows(IllegalArgumentException.class, () -> context.client.createSnapshot(invalidSnapshotId1.offset, invalidSnapshotId1.epoch, 0));
    // Poll for our first fetch request
    context.pollUntilRequest();
    RaftRequest.Outbound fetchRequest = context.assertSentFetchRequest();
    assertTrue(voters.contains(fetchRequest.destinationId()));
    context.assertFetchRequestData(fetchRequest, epoch, 0L, 0);
    // The response does not advance the high watermark
    List<String> records1 = Arrays.asList("a", "b", "c");
    MemoryRecords batch1 = context.buildBatch(0L, 3, records1);
    context.deliverResponse(fetchRequest.correlationId, fetchRequest.destinationId(), context.fetchResponse(epoch, leaderId, batch1, 0L, Errors.NONE));
    context.client.poll();
    // 2) The high watermark must be larger than or equal to the snapshotId's endOffset
    int currentEpoch = context.currentEpoch();
    OffsetAndEpoch invalidSnapshotId2 = new OffsetAndEpoch(context.client.highWatermark().getAsLong() + 1, currentEpoch);
    assertThrows(IllegalArgumentException.class, () -> context.client.createSnapshot(invalidSnapshotId2.offset, invalidSnapshotId2.epoch, 0));
    // 3) The quorum epoch must be larger than or equal to the snapshotId's epoch
    OffsetAndEpoch invalidSnapshotId3 = new OffsetAndEpoch(context.client.highWatermark().getAsLong(), currentEpoch + 1);
    assertThrows(IllegalArgumentException.class, () -> context.client.createSnapshot(invalidSnapshotId3.offset, invalidSnapshotId3.epoch, 0));
    // The high watermark advances to be larger than log.endOffsetForEpoch(3), to test the case 3
    context.pollUntilRequest();
    fetchRequest = context.assertSentFetchRequest();
    assertTrue(voters.contains(fetchRequest.destinationId()));
    context.assertFetchRequestData(fetchRequest, epoch, 3L, 3);
    List<String> records2 = Arrays.asList("d", "e", "f");
    MemoryRecords batch2 = context.buildBatch(3L, 4, records2);
    context.deliverResponse(fetchRequest.correlationId, fetchRequest.destinationId(), context.fetchResponse(epoch, leaderId, batch2, 6L, Errors.NONE));
    context.client.poll();
    assertEquals(6L, context.client.highWatermark().getAsLong());
    // 4) The snapshotId should be validated against endOffsetForEpoch
    OffsetAndEpoch endOffsetForEpoch = context.log.endOffsetForEpoch(3);
    assertEquals(3, endOffsetForEpoch.epoch);
    OffsetAndEpoch invalidSnapshotId4 = new OffsetAndEpoch(endOffsetForEpoch.offset + 1, epoch);
    assertThrows(IllegalArgumentException.class, () -> context.client.createSnapshot(invalidSnapshotId4.offset, invalidSnapshotId4.epoch, 0));
}
Also used : MemoryRecords(org.apache.kafka.common.record.MemoryRecords) UnalignedMemoryRecords(org.apache.kafka.common.record.UnalignedMemoryRecords) SnapshotWriterReaderTest(org.apache.kafka.snapshot.SnapshotWriterReaderTest) Test(org.junit.jupiter.api.Test)

Example 77 with MemoryRecords

use of org.apache.kafka.common.record.MemoryRecords in project kafka by apache.

the class KafkaRaftClientTest method testPurgatoryFetchCompletedByFollowerTransition.

@Test
public void testPurgatoryFetchCompletedByFollowerTransition() throws Exception {
    int localId = 0;
    int voter1 = localId;
    int voter2 = localId + 1;
    int voter3 = localId + 2;
    int epoch = 5;
    Set<Integer> voters = Utils.mkSet(voter1, voter2, voter3);
    RaftClientTestContext context = RaftClientTestContext.initializeAsLeader(localId, voters, epoch);
    // Follower sends a fetch which cannot be satisfied immediately
    context.deliverRequest(context.fetchRequest(epoch, voter2, 1L, epoch, 500));
    context.client.poll();
    assertTrue(context.channel.drainSendQueue().stream().noneMatch(msg -> msg.data() instanceof FetchResponseData));
    // Now we get a BeginEpoch from the other voter and become a follower
    context.deliverRequest(context.beginEpochRequest(epoch + 1, voter3));
    context.pollUntilResponse();
    context.assertElectedLeader(epoch + 1, voter3);
    // We expect the BeginQuorumEpoch response and a failed Fetch response
    context.assertSentBeginQuorumEpochResponse(Errors.NONE, epoch + 1, OptionalInt.of(voter3));
    // The fetch should be satisfied immediately and return an error
    MemoryRecords fetchedRecords = context.assertSentFetchPartitionResponse(Errors.NOT_LEADER_OR_FOLLOWER, epoch + 1, OptionalInt.of(voter3));
    assertEquals(0, fetchedRecords.sizeInBytes());
}
Also used : Records(org.apache.kafka.common.record.Records) Assertions.assertThrows(org.junit.jupiter.api.Assertions.assertThrows) NotLeaderException(org.apache.kafka.raft.errors.NotLeaderException) Assertions.assertNotNull(org.junit.jupiter.api.Assertions.assertNotNull) Arrays(java.util.Arrays) Assertions.assertNotEquals(org.junit.jupiter.api.Assertions.assertNotEquals) Assertions.assertNull(org.junit.jupiter.api.Assertions.assertNull) TimeoutException(java.util.concurrent.TimeoutException) CompletableFuture(java.util.concurrent.CompletableFuture) DescribeQuorumRequest(org.apache.kafka.common.requests.DescribeQuorumRequest) ClusterAuthorizationException(org.apache.kafka.common.errors.ClusterAuthorizationException) OptionalInt(java.util.OptionalInt) ByteBuffer(java.nio.ByteBuffer) FetchResponseData(org.apache.kafka.common.message.FetchResponseData) Record(org.apache.kafka.common.record.Record) ArrayList(java.util.ArrayList) Collections.singletonList(java.util.Collections.singletonList) ReplicaState(org.apache.kafka.common.message.DescribeQuorumResponseData.ReplicaState) OptionalLong(java.util.OptionalLong) MemoryPool(org.apache.kafka.common.memory.MemoryPool) RecordBatchTooLargeException(org.apache.kafka.common.errors.RecordBatchTooLargeException) Assertions.assertFalse(org.junit.jupiter.api.Assertions.assertFalse) RecordBatch(org.apache.kafka.common.record.RecordBatch) MutableRecordBatch(org.apache.kafka.common.record.MutableRecordBatch) Assertions.assertEquals(org.junit.jupiter.api.Assertions.assertEquals) Utils(org.apache.kafka.common.utils.Utils) EndQuorumEpochResponse(org.apache.kafka.common.requests.EndQuorumEpochResponse) DEFAULT_ELECTION_TIMEOUT_MS(org.apache.kafka.raft.RaftClientTestContext.Builder.DEFAULT_ELECTION_TIMEOUT_MS) TestUtils(org.apache.kafka.test.TestUtils) EndQuorumEpochResponseData(org.apache.kafka.common.message.EndQuorumEpochResponseData) BufferAllocationException(org.apache.kafka.raft.errors.BufferAllocationException) Set(java.util.Set) TestUtils.assertFutureThrows(org.apache.kafka.test.TestUtils.assertFutureThrows) IOException(java.io.IOException) Test(org.junit.jupiter.api.Test) Mockito(org.mockito.Mockito) MemoryRecords(org.apache.kafka.common.record.MemoryRecords) List(java.util.List) Metrics(org.apache.kafka.common.metrics.Metrics) Assertions.assertTrue(org.junit.jupiter.api.Assertions.assertTrue) BeginQuorumEpochResponseData(org.apache.kafka.common.message.BeginQuorumEpochResponseData) Errors(org.apache.kafka.common.protocol.Errors) Optional(java.util.Optional) KafkaMetric(org.apache.kafka.common.metrics.KafkaMetric) Collections(java.util.Collections) VoteResponseData(org.apache.kafka.common.message.VoteResponseData) FetchResponseData(org.apache.kafka.common.message.FetchResponseData) MemoryRecords(org.apache.kafka.common.record.MemoryRecords) Test(org.junit.jupiter.api.Test)

Example 78 with MemoryRecords

use of org.apache.kafka.common.record.MemoryRecords in project kafka by apache.

the class KafkaRaftClientTest method testPurgatoryFetchTimeout.

@Test
public void testPurgatoryFetchTimeout() throws Exception {
    int localId = 0;
    int otherNodeId = 1;
    int epoch = 5;
    Set<Integer> voters = Utils.mkSet(localId, otherNodeId);
    RaftClientTestContext context = RaftClientTestContext.initializeAsLeader(localId, voters, epoch);
    // Follower sends a fetch which cannot be satisfied immediately
    int maxWaitTimeMs = 500;
    context.deliverRequest(context.fetchRequest(epoch, otherNodeId, 1L, epoch, maxWaitTimeMs));
    context.client.poll();
    assertEquals(0, context.channel.drainSendQueue().size());
    // After expiration of the max wait time, the fetch returns an empty record set
    context.time.sleep(maxWaitTimeMs);
    context.client.poll();
    MemoryRecords fetchedRecords = context.assertSentFetchPartitionResponse(Errors.NONE, epoch, OptionalInt.of(localId));
    assertEquals(0, fetchedRecords.sizeInBytes());
}
Also used : MemoryRecords(org.apache.kafka.common.record.MemoryRecords) Test(org.junit.jupiter.api.Test)

Example 79 with MemoryRecords

use of org.apache.kafka.common.record.MemoryRecords in project kafka by apache.

the class KafkaRaftClientTest method testPurgatoryFetchSatisfiedByWrite.

@Test
public void testPurgatoryFetchSatisfiedByWrite() throws Exception {
    int localId = 0;
    int otherNodeId = 1;
    int epoch = 5;
    Set<Integer> voters = Utils.mkSet(localId, otherNodeId);
    RaftClientTestContext context = RaftClientTestContext.initializeAsLeader(localId, voters, epoch);
    // Follower sends a fetch which cannot be satisfied immediately
    context.deliverRequest(context.fetchRequest(epoch, otherNodeId, 1L, epoch, 500));
    context.client.poll();
    assertEquals(0, context.channel.drainSendQueue().size());
    // Append some records that can fulfill the Fetch request
    String[] appendRecords = new String[] { "a", "b", "c" };
    context.client.scheduleAppend(epoch, Arrays.asList(appendRecords));
    context.client.poll();
    MemoryRecords fetchedRecords = context.assertSentFetchPartitionResponse(Errors.NONE, epoch, OptionalInt.of(localId));
    RaftClientTestContext.assertMatchingRecords(appendRecords, fetchedRecords);
}
Also used : MemoryRecords(org.apache.kafka.common.record.MemoryRecords) Test(org.junit.jupiter.api.Test)

Example 80 with MemoryRecords

use of org.apache.kafka.common.record.MemoryRecords in project kafka by apache.

the class RecordsBatchReaderTest method testReadFromFileRecords.

@ParameterizedTest
@EnumSource(CompressionType.class)
public void testReadFromFileRecords(CompressionType compressionType) throws Exception {
    long baseOffset = 57;
    List<TestBatch<String>> batches = RecordsIteratorTest.createBatches(baseOffset);
    MemoryRecords memRecords = RecordsIteratorTest.buildRecords(compressionType, batches);
    FileRecords fileRecords = FileRecords.open(tempFile());
    fileRecords.append(memRecords);
    testBatchReader(baseOffset, fileRecords, batches);
}
Also used : TestBatch(org.apache.kafka.raft.internals.RecordsIteratorTest.TestBatch) FileRecords(org.apache.kafka.common.record.FileRecords) MemoryRecords(org.apache.kafka.common.record.MemoryRecords) EnumSource(org.junit.jupiter.params.provider.EnumSource) ParameterizedTest(org.junit.jupiter.params.ParameterizedTest)

Aggregations

MemoryRecords (org.apache.kafka.common.record.MemoryRecords)108 TopicPartition (org.apache.kafka.common.TopicPartition)59 Test (org.junit.jupiter.api.Test)43 SimpleRecord (org.apache.kafka.common.record.SimpleRecord)40 ByteBuffer (java.nio.ByteBuffer)34 ArrayList (java.util.ArrayList)28 List (java.util.List)27 Test (org.junit.Test)27 HashMap (java.util.HashMap)26 LinkedHashMap (java.util.LinkedHashMap)23 MemoryRecordsBuilder (org.apache.kafka.common.record.MemoryRecordsBuilder)23 ConsumerRecord (org.apache.kafka.clients.consumer.ConsumerRecord)18 FetchResponseData (org.apache.kafka.common.message.FetchResponseData)16 Collections.singletonList (java.util.Collections.singletonList)15 Record (org.apache.kafka.common.record.Record)15 Arrays.asList (java.util.Arrays.asList)14 Collections.emptyList (java.util.Collections.emptyList)14 ByteArrayDeserializer (org.apache.kafka.common.serialization.ByteArrayDeserializer)14 Metrics (org.apache.kafka.common.metrics.Metrics)12 MutableRecordBatch (org.apache.kafka.common.record.MutableRecordBatch)11