> For the complete documentation index, see [llms.txt](https://tingreavinash.gitbook.io/the-tech-toolbox/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://tingreavinash.gitbook.io/the-tech-toolbox/notes/apache-kafka/partitions.md).

# Partitions

In Kafka, a partition is a unit of parallelism and scalability. A partition is a logical division of a Kafka topic. A topic can have multiple partitions. Each partition is an ordered, immutable sequence of records.

Partitions are useful for several reasons:

* Scalability: A topic with many partitions can be spread across multiple brokers, allowing for better parallelism and higher throughput.
* Fault tolerance: If a broker fails, Kafka can continue to function if there are other brokers with replicas of the partitions.
* Order guarantee: While records within a partition are ordered, records in different partitions are not guaranteed to be in any specific order. However, Kafka provides a way to assign a key to each record, which can be used to ensure that records with the same key are always in the same partition, preserving order within a key.

Overall, partitions are a key feature of Kafka that enable it to provide high throughput, fault tolerance, and ordered processing.

### Configuration

#### Producer

To send a message to a specific partition using Spring Boot Kafka, you need to create a `ProducerRecord` object with the topic name, partition number, and message to be sent. Here is an example code snippet that demonstrates how to send a message to a specific partition using Spring Boot Kafka:

```java
@Autowired
private KafkaTemplate<String, String> kafkaTemplate;

public void sendMessageToPartition(String topicName, int partitionNumber, String message) {
    ProducerRecord<String, String> record = new ProducerRecord<>(topicName, partitionNumber, null, message);
    kafkaTemplate.send(record);
}
```

In the code snippet above, the `KafkaTemplate` is used to send the message. The `ProducerRecord` object is created with the topic name, partition number, and message to be sent. The `null` argument represents the key of the message. Finally, the `send()` method of the `KafkaTemplate` is used to send the message to the specified partition.

Note that you should make sure that the partition number is within the range of the available partitions for the specified topic.

#### Consumer

In Spring Boot, you can handle Kafka partitions using the `@KafkaListener` annotation. The `@KafkaListener` annotation is used to indicate that a method should be invoked to process messages from a Kafka topic.

To handle Kafka partitions, you can specify the partition number or a partition key in the `@KafkaListener` annotation. Here's an example:

```java
@KafkaListener(topics = "my-topic", partitions = "0")
public void listenToPartition(@Payload String message) {
    // process the message
}

@KafkaListener(topicPartitions = {
        @TopicPartition(topic = "my-topic", partitions = {"0", "1"}),
        @TopicPartition(topic = "another-topic", partitions = "0", partitionOffsets = @PartitionOffset(partition = "0", initialOffset = "0"))
})
public void listenToTopicPartition(@Payload String message) {
    // process the message
}

@KafkaListener(topics = "my-topic", groupId = "my-group-id",
        containerFactory = "myContainerFactory")
public void listenToTopicWithCustomFactory(@Payload String message) {
    // process the message
}
```

In the first example, the `listenToPartition` method listens to partition 0 of the "my-topic" topic. In the second example, the `listenToTopicPartition` method listens to partitions 0 and 1 of the "my-topic" topic, as well as partition 0 of the "another-topic" topic. The `groupId` attribute specifies the consumer group ID to use. The `containerFactory` attribute specifies the name of the `KafkaListenerContainerFactory` bean to use.

You can also specify a `ConcurrentKafkaListenerContainerFactory` bean to configure the concurrency of the listener container. Here's an example:

```java
@Bean
public ConcurrentKafkaListenerContainerFactory<String, String> kafkaListenerContainerFactory() {
    ConcurrentKafkaListenerContainerFactory<String, String> factory =
            new ConcurrentKafkaListenerContainerFactory<>();
    factory.setConsumerFactory(consumerFactory());
    factory.setConcurrency(3); // set the concurrency to 3
    return factory;
}
```

In this example, the `kafkaListenerContainerFactory` method returns a `ConcurrentKafkaListenerContainerFactory` bean with a concurrency of 3. The `setConsumerFactory` method sets the `ConsumerFactory` to use.

By setting the concurrency of the listener container, you can process multiple Kafka messages concurrently. This can improve the throughput of your application.
