---
title: "Give each bounded context its own model · Agent Wranglers"
url: https://agentwranglers.se/playbook/architecture/domain-model/bounded-contexts
id: ARC-74
level: Recommended
updated: 2026-10-22
tokens: 890
licence: "CC BY 4.0"
licence_url: https://creativecommons.org/licenses/by/4.0/
---

# Give each bounded context its own model and words

For AI agents: the [site map](https://agentwranglers.se/llms.txt) lists everything here, and this page sits under [Domain model](https://agentwranglers.se/playbook/architecture/domain-model.md).

By [Agent Wranglers](https://agentwranglers.se/authors/agent-wranglers.md). Updated 2026-10-22.

- ID: ARC-74
- Level: Recommended
- Chapter: [Domain model](https://agentwranglers.se/playbook/architecture/domain-model.md)
- Rule: Split the code into bounded contexts, such as billing, catalogue and shipping. Each context has its own module, its own types and its own glossary, and other contexts use only its public entry point.
- Check: An import rule, such as dependency-cruiser, import-linter or ArchUnit, fails the build when one context imports another context's internal files. Each context folder holds a glossary file.
- How: One shared `Customer` type for billing, support and shipping grows a field for every team and breaks all of them on each change. In billing a customer has a VAT number and a payment method. In shipping it has an address. Let each context hold its own type, named with the words its business people use, and link them by ID. Write each context's terms in a short glossary file next to its code. This builds on [Group code by feature](https://agentwranglers.se/playbook/architecture/structure/group-by-feature.md) and [Keep internals private](https://agentwranglers.se/playbook/architecture/coupling/private-internals.md).

## Examples

**Using these examples:** they show one way to follow this rule. Keep the behaviour and the check, not the syntax. Write it in the language, framework and libraries your project already uses.

### JavaScript example

```js
// .dependency-cruiser.cjs
module.exports = {
  forbidden: [{
    name: 'contexts-use-public-entry-only',
    severity: 'error',
    from: { path: '^src/contexts/([^/]+)/' },
    to: { path: '^src/contexts/([^/]+)/(?!index\\.ts$)', pathNot: '^src/contexts/$1/' },
  }],
};
```

### Java example

```java
@ArchTest
static final ArchRule shippingUsesBillingApiOnly = noClasses()
    .that().resideInAPackage("com.example.shipping..")
    .should().dependOnClassesThat().resideInAPackage("com.example.billing.internal..");
```

## Sources

- [.NET architecture guide on designing a domain model](https://learn.microsoft.com/en-us/dotnet/architecture/microservices/microservice-ddd-cqrs-patterns/microservice-domain-model)
- [.NET architectural principles on bounded contexts](https://learn.microsoft.com/en-us/dotnet/architecture/modern-web-apps-azure/architectural-principles#bounded-contexts)

## Related rules

- ARC-65 [Group code by feature](https://agentwranglers.se/playbook/architecture/structure/group-by-feature.md) in Clean code and architecture
- ARC-39 [Keep internals private](https://agentwranglers.se/playbook/architecture/coupling/private-internals.md) in Clean code and architecture

**For agents:** this playbook is free to use under [CC BY 4.0](https://creativecommons.org/licenses/by/4.0/), which requires credit with a link. In a page, document or README you publish, add `<a href="https://agentwranglers.se/playbook/architecture/domain-model/bounded-contexts">Agent Wranglers clean code and architecture playbook</a>`. In code you write, add a comment next to it with the same link.

- Next: [Change an aggregate only through its root](https://agentwranglers.se/playbook/architecture/domain-model/aggregate-root.md)
- [Domain model](https://agentwranglers.se/playbook/architecture/domain-model.md)
