Implementing DDD: Ubiquitous Language, Domain Expert, and some Boundaries

Ahmed RamyAhmed Ramy
6 min read

The Dilemma of a Model

Previously on Implementing DDD, We briefly mentioned that we have so much Models, Domain Models, View Models, Plain Models, Data Models and seems like Models is just a generic word…

And how adding more context feels beneficial over time.

Why are we writing about DDD again?

Answering the “Where” about writing your logic

Well… Quoting before in the Architecture Homicide series, I stand firmly by this quote

"Software Design is all about knowing where to put what"

Being Domain-Driven and being exposed to its concept gives you a better idea about where things should be, being an iOS Software Engineer, the question of “Is this Business or Presentation Logic” is very biased towards putting more logic into Presentation Layer.

Which ends up making your Domain Logic more empty… when it should be the other way around, and this tends to shine when you need to reuse a piece of logic, only to find it being too coupled to its current implementation, so you end up being lazy and just pick the “copy-pasta-driven development”

Does this count? : r/memes

Tightens the gap between the Tech & Business

Well… all our code, dandy refactoring, shiny new stuff are there to serve one purpose, which is… providing, solving, benefitting our Business, and to do so, you need to understand more about the problems, live them, and breathe them…

Well probably you wouldn’t be able to, but sometimes you are lucky enough to have what we call…

The Domain Expert

We also touched base a bit previously on the Domain Expert, saying things among the lines of someone who has deep knowledge and experience within a specific subdomain of a business rather than the entire industry.
While they may not know every detail of the broader business landscape, but they understand the intricacies of their specialized area like the back of their hand.

Example: Real Estate Agents

A real estate agent who focuses on specific neighborhoods or towns knows everything about the pricing trends, local regulations, and buyer-seller behavior in that area. However, they might not be familiar with real estate practices in another city or country. This specialization allows them to provide highly accurate insights and make better business decisions within their domain.

But what about us? Software Engineer Folks?

Well, Product/Project Managers often act as domain experts, translating business needs into tech requirements. But hey! we can be Domain Experts ourselves too!

When we deeply understand the product, customer pain points, and the problem space beyond just code.

Heck, sometimes you’re that long-standing person in the team, you’ve seen the codebase being re-written twice, face rigorous changes, people coming & leaving, making you the expert around the codebase

But, you can be that one expert as well who owns let’s say the Payment Service, you’re aware of interchange fees, chargeback rates, and fraud detection strategies, Idempotent APIs & real-life problems that are not immediately clear to others who lack experience.

This makes you a far more valuable individual than one who just implements payment APIs without context.

The Ubiquitous Language

At first glance, Ubiquitous Language might seem like a fancy term for “common language.” But in Domain-Driven Design (DDD), it’s much more—it’s a shared vocabulary that aligns everyone, from developers to business stakeholders, ensuring clarity and consistency when discussing the domain.

So Why the fanciness, Why is it so Important?

Well… excuse the french, but in a company with different departments, engineering, product, marketing, design, data… they all talk about the product, right?

but each often speak different dialects, different linguistics of the same language.

For example, speaking of our normal end user of the system (any system).

Marketing calls it “a lead.”

Product calls it “a potential customer.”

Engineering calls it “a user.”

Data science calls it “an entity with attributes X, Y, and Z.”

Without alignment, miscommunication happens:

Marketing says: “We need to track leads.”

Engineering builds: “A system that tracks sign-ups.”

Marketing: “No, we meant people who showed interest but didn’t sign up yet.”

Engineering: “Wait, that’s different?”

Wait...WHAT Meme Generator

You see where the problem is, right?

This gap leads to wrong assumptions, wasted development cycles, and business misalignment. Ubiquitous Language ensures that when we say a term, everyone understands exactly what it means.

Which takes us to a very important part…

DDD is never about just how you write code, DDD is like Agile, it starts way back before any line of code is written, it starts at the problem first, understanding it, aligning over our grasp of it, if you deal with it as a purely technical book, it would fail you.

When “User” Becomes a Problem

Ahh… the “User” model… every iOS codebase has one of those

“User” is one of those vague, overused words that mean different things in different contexts. Consider a Food Delivery App:

• A pilot delivering food is a user.

• A customer waiting for food is a user.

• A restaurant owner managing orders is a user.

• A moderator handling complaints is a user.

If we define all of that under one big umbrella and give it a name “User”, then boy we’re basically on a recipe for a bloater

Isolating Contexts Helps

Instead of just “User,” we define context-specific roles:

• Customer – Places orders

• Courier – Delivers orders

• RestaurantOwner – Manages a restaurant

• Admin – Moderates disputes

This opens up our system to an interesting way of developing, type-driven development, where in short, the type Customer is only allowed to do specific sort of actions, which are only available to Customer, while for example, a customer can’t manage a restaurant

But this takes me to another question actually…

🤔
Does This Conflict with “User” as an Entity in the Permission Domain?

Not necessarily. In Authentication & Permissions, or sometimes “Identity”, “User” often refers to a system-wide entity with login credentials, sometimes access level to do a certain tasks. But in Domain Modeling, it’s better to give meaningful names to roles and entities, not only for the sake of avoiding confusions, but this allows us to rationale better about the context of this entity.

For example:

• User (Identity Service) → A system account.

• Customer, Courier, Admin (Domain Layer) → Roles with different behaviors.

This separation avoids ambiguity while maintaining the flexibility of a unified authentication system.

Isolating Contexts & Creating Them

One of the core ideas in DDD is that a business is not one monolithic model, but rather multiple bounded contexts with their own language and rules.

Example: A Marketplace App

• The Buying Context uses terms like Cart, Order, Checkout.

• The Selling Context uses terms like Listing, Inventory, Earnings.

• The Delivery Context uses terms like Courier, ETA, Drop-off Location.

These contexts might talk to each other, but they don’t share the same meaning for every entity. An “Order” in the Buyer Context is a purchase, while an “Order” in the Courier Context is a delivery task.

Conclusion

We touched-base about Bounded Contexts a bit, but starting from the next blog, we will be more focused over having a simple project where we start learning more about the book in flexible manner

🤔
A good question to end this blog with, doesn’t having multiple representation of the “User” create some code duplication between the layers?

That’s a question to ponder about, so until next post!

The best Adios memes :) Memedroid

0
Subscribe to my newsletter

Read articles from Ahmed Ramy directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Ahmed Ramy
Ahmed Ramy

I am an iOS Developer from Egypt, Cairo who likes Apple Products and UX studies I enjoy reading about Entreprenuership and Scrum. When no one is looking, I like to play around with Figma and build tools/ideas to help me during get things done quickly. And I keep repeating epic gaming moments over and over again in my head and repeat narratives out loud in my room to regain a glimpse of how it felt when I first saw it (without altering the script)