r/dotnet

▲ 16 r/dotnet

Does anyone actually build Rich Domain Models in real world DDD projects anymore

Hi everyone,
I’ve been working on a few different .NET projects lately that all claim to be using Domain-Driven Design, but I'm starting to notice a huge gap between the textbook theory and what we actually ship. Honestly, in my experience, a true "Rich Domain Model" is basically a myth. Whenever I look at our codebases, the entities are essentially just anemic property bags with public setters.
Instead of encapsulating behavior inside the domain, all the actual business logic, state changes, and orchestrations just live in the Application layer, usually shoved into command handlers. Even validation is completely outsourced. We just rely heavily on FluentValidation in Application before anything even gets a chance to touch the domain. And when it comes to Value Objects, we almost never build robust, encapsulated types. Most of the time, something that probably should be a Value Object just gets turned into a standard C# enum or left as a primitive .
It feels like the only parts of DDD we actually adopt are the structural concepts. We do split things into Bounded Contexts, we identify Aggregate Roots and Entities, and we strictly follow the rule of having one repository per AR to fetch the parent and its children as a single unit. But beyond that structural organization, the domain itself is completely hollow.
I really want to know what DDD looks like in the trenches for the rest of you. Is this combination of anemic models, application handlers, and FluentValidation basically the unspoken reality of .NET enterprise apps? If you are actually out there successfully enforcing invariants and behavior inside rich domain models, how do you manage complex validations or rules that cross multiple aggregates without turning your domain into a messy dependency nightmare? I'd love to hear how much of the DDD textbook actually makes it into your production codebases.

reddit.com
u/SaltedFesh — 3 hours ago
▲ 10 r/dotnet

How do you handle transactions with repository pattern ?

I’m using the repository pattern with an IRepositoryManager that aggregates multiple repositories and exposes a single SaveChangesAsync that calls DbContext.SaveChangesAsync.

Everything works fine until I need a transaction across multiple repositories.

Since they share the same DbContext it kind of acts like a unit of work, but I’m not sure how to properly handle explicit transactions.

Would you expose something like BeginTransactionAsync on the repository manager, or handle transactions at the service layer instead.

What approach do you usually follow in real projects.

reddit.com
u/Minimum-Ad7352 — 5 hours ago
▲ 10 r/dotnet

Why am I getting this error if there is a null check?

```

Argument type 'Domain.User.UserId?' is not assignable to parameter type 'Domain.User.UserId'

```

In TypeScript, I don’t get an error because there’s a null check, but here it seems the language design is flawed specifically in this case

u/Sensitive-Raccoon155 — 5 hours ago
▲ 39 r/dotnet

I built a multiplayer browser game entirely in .NET (Blazor WASM, Canvas 2D, SignalR, EF Core)

https://preview.redd.it/6dd8ojxbpltg1.png?width=1610&format=png&auto=webp&s=d1037ed05ae3a7ed27c2dfd387640492aca6d904

Hey everyone! I want to share a project I been working on. This one's a browser game inspired by Chocobo Hot & Cold minigame from Final Fantasy IX,built as a full multiplayer web game using only .NET stack. You can play it directly in the browser, no install needed. As for the stack:

- Blazor WASM for the frontend (running in browser at 60 fps)

- HTML5 Canvas 2D for rendering through JS interop (no WebGL, no Unity, just canvas draw calls from C#)

- ASP.NET Core backend API (leaderboard, SignalR for multiplayer battles)

- PostgreSQL with EF Core

- Google and Discord OAuth for login (this was not actually as bad as I thought, though I hit some issues from time to time)

So, long story short, this game started as a bootcamp project when I've started coding. Just a Console App based on SFML. Kept working on that for a while, playing with inmutable ECS pattern (yeah this was an overkill but wanted to better understand it). The entire game state is a single record called World that gets replaced every frame, never mutated. All systems are static pure functions so they take a World in and return a new World out.

I've captured side effects like audio as data (Effect records) and executed after all systems run.

The game uses a Frame carrier pattern that threads (World, ImmutableList<Effect>) through the system pipeline, and a Pipe pattern for composing state transforms:

var result = new MotionState(pos, scale, accel)
  .Pipe(ctx, Horizontal)
  .Pipe(ctx, Vertical)
  .Pipe(ctx, Perspective);

The game engine lives in a shared library (ChocoboDig.Core) with no dependency on any rendering framework, so same logic that ran on the desktop SFML version now runs in WASM without changes.

As for WASM, the Canvas rendering is all through IJSRuntime interop. C# dictates what to draw, JS does the actual canvas calls. Pixel art with imageSmoothingEnabled = false, screen shake, some particle effects, floating text, etc.

I was honestly impressed about Blazor WASM. It can absolutely handle a real-time game loop, the performance was better than I expected. Initial load time is probably what I still need to nail but everything else looks pretty good.

JS interop for Canvas is not as slow as people think if you batch your calls

As for SignalR: it just works great for this kind of real-time sync, but I'd like to see multiple battles at the same time to see if it actually blows up or not lol.

If anyone want to see how a specific part works I can share code snippets in the comments, just ask!

reddit.com
u/leandroecorrea — 16 hours ago
▲ 31 r/dotnet+1 crossposts

Serilog sink that writes log events to self-contained interactive HTML files

I built a Serilog sink that outputs logs as clean HTML so they’re actually readable, searchable, and filterable by level.

.WriteTo.HtmlFile("logs-{date}.html")
github.com
u/Capital-Victory-1478 — 24 hours ago
▲ 9 r/dotnet

Entity Framework randomly adding max-length to columns in migrations?

How do I tell EF that I don't want a max length?

In some configurations, I'll have something like this with two identical string columns:

builder
    .Property(x =&gt; x.Name)
    .IsRequired();

builder
    .Property(x =&gt; x.Description)
    .IsRequired(false);

However when I create the migration, it'll add 450 max-length to some columns, but not others:

...
Name = table.Column&lt;string&gt;(type: "nvarchar(450", nullable: false), // Why 450???
Description = table.Column&lt;string&gt;(type: "nvarchar(max)", nullable: true),
...

Why is this happening, and how can I fix this?

reddit.com
u/Tuckertcs — 17 hours ago
▲ 2 r/dotnet

Is there need for cross-platform obfuscation tools?

I decide to maintain ConfuserEx and make it cross-platform, but I'm curious what's the current state of OSS cross-platform obfuscator tools? I assume that for Avalonia desktop applications there need for this even now, or NativeAOT is "obfuscation" technique?

reddit.com
u/kant2002 — 17 hours ago
▲ 0 r/dotnet+1 crossposts

How to use Dapper and hot chocolate instead of EF Core + DbContext?

Okay for Dapper you dont need a DbContext. Just a connectionstring. I let my program know I have a connectionstring like this:

builder.Services.AddTransient&lt;MawaddaDbContext&gt;(_
    =&gt; new MawaddaDbContext(new NpgsqlConnectionFactory(builder.Configuration)));

builder.Services
    .AddGraphQLServer()
    .AddQueryType&lt;Query&gt;();

Here is "MawaddaDbContext" just a class where I just the connection to create tables in my Postgresql database when they dont exist by writing queries using Dapper.

Then I make a Query class so I can fetch data using graphql Hot chocolate library because its just better than REST. However I get an internal error when I try to fetch my schema.

I have searched all of the internet but i cannot find a tutorial how to properly do this stuff with Dapper instead of EF core.

Here is my Query class:

    public class Query
    {
        public async Task&lt;Experience&gt; GetExperienceByIdAsync(string id,               MawaddaDbContext context)
        {
            var conn = await context.ConnectionFactory.CreateConnection();
            Experience experience = await conn.QueryFirstAsync&lt;Experience&gt;(@"SELECT * FROM experiences WHERE Id == ?", id);
            return experience;
        }
    } 
reddit.com
u/CodMore3394 — 23 hours ago
▲ 0 r/dotnet

.NET Performance in Betfair Trading: Integrating with Faster Languages

Recently, I ran a quick benchmark comparing Python and F# for a Betfair trading task. The results were clear: my F# code finished in 3 seconds, while the Python version took 10 seconds for the same operation. This lines up with what many developers observe statically typed, compiled languages like F# or C# often outperform dynamic, interpreted ones like Python, especially for property access and json operations.

But I’m curious: what’s your experience with .NET language performance in trading or other latency-sensitive domains? Have you found .NET fast enough for your needs, or have you hit bottlenecks?

Integrating .NET with Faster Languages

Sometimes, even .NET isn’t fast enough for the most performance-critical parts. In those cases, what’s the best way to bring in the raw speed of C, C++, or even Rust?

Here are a few integration patterns I’ve considered:

  • P/Invoke (Platform Invocation Services): Directly call C functions from .NET using DllImport. This works well for simple, stable APIs, but can get tricky with complex data structures or memory management.
  • C++/CLI: Write a managed C++/CLI wrapper that bridges native C++ and .NET. This is powerful but adds build complexity and is Windows-only.
  • gRPC or REST Servers: Run a high-performance service (in C, C++, or Rust) as a separate process, and have your .NET app communicate with it over gRPC or HTTP. This decouples the systems and works cross-platform, but adds some latency and deployment overhead.

Personally, I’m interested in the gRPC approach: exposing Rust or C++ operations as a service, with .NET as a client. This seems to offer the best of both worlds—.NET’s productivity and ecosystem, plus the raw speed of lower-level languages.

What’s Worked for You?

  • Have you integrated .NET with C, C++, or Rust for performance?
  • What patterns or tools have you found most reliable?
  • Any pitfalls or lessons learned?

Let’s share experiences and help each other build faster, more robust trading systems!

reddit.com
u/Optimal-Task-923 — 16 hours ago
Week