K.EntityFrameworkCore Logo

Build Status NuGet Version NuGet Downloads License: MIT Documentation GitHub Release

Kafka that actually feels like Entity Framework

Use Kafka with the same patterns you already know. No complexity, no surprises.

What you're doing now 😤

// Multiple configuration files, scattered setup
var config = new ProducerConfig
{
    BootstrapServers = "localhost:9092",
    ClientId = "my-app",
    // ... 20+ more properties
};

var producer = new ProducerBuilder<string, string>(config).Build();

// Manual transaction management
dbContext.Orders.Add(order);
await dbContext.SaveChangesAsync();
    
// Separate Kafka operation - consistency risk!
await producer.ProduceAsync("order-events", message);

With K.EntityFrameworkCore ✨

dbContext.Orders.Add(new Order { Id = 123 });
dbContext.OrderEvents.Produce(new OrderCreated { OrderId = 123 });

await dbContext.SaveChangesAsync(); // 🎉 Both computed!

🏗️ Topic<T> works like DbSet<T>

Configure Kafka topics the same way you configure entities. Your team already knows how to use this.

Note

No new concepts to learn. If you can write modelBuilder.Entity<Order>(), you can write modelBuilder.Topic<OrderEvent>().


Quick Start: From Zero to Kafka in 3 Steps

1️⃣ Define Your DbContext

public class OrderContext(DbContextOptions options) : DbContext(options)
{
    // Your regular entities
    public DbSet<Order> Orders { get; set; }
    
    // Kafka topics - just like DbSets!
    public Topic<OrderEvent> OrderEvents { get; set; }
    
    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        // Configure your topic like you would any entity
        modelBuilder.Topic<OrderEvent>(topic =>
        {
            topic.HasName("order-events");
            topic.HasProducer(p => p.HasOutbox()); // Built-in outbox!
            topic.HasConsumer(c => c.HasInbox());  // Built-in deduplication!
        });
    }
}

2️⃣ Configure Services

builder.Services.AddDbContext<OrderContext>(options => options
    .UseSqlServer("your-connection-string")
    .UseKafkaExtensibility("localhost:9092"));

3️⃣ Produce & Consume

// Producing is just like adding entities
dbContext.Orders.Add(new Order { Id = 123 });
dbContext.OrderEvents.Produce(new OrderCreated { OrderId = 123 });
await dbContext.SaveChangesAsync(); // Both saved atomically! 🎉

// Consuming feels natural too
await foreach (var orderEvent in dbContext.OrderEvents)
{
    // Process your message
    await ProcessOrder(orderEvent.Value);
    
    // Commit to mark as processed
    await dbContext.SaveChangesAsync();
}

Ready to stop fighting Kafka?

Get Started in Under 5 Minutes

Install it now and start using Kafka the way it should have worked from the beginning.

Installation
dotnet add package K.EntityFrameworkCore