大型企业应用模块化:Repository/Unit of Work模式仓储数量及性能问询
Hey there, great question—this is a super common challenge when modernizing legacy enterprise applications stuck on outdated tech stacks. Let’s unpack this clearly:
First: Does a Unit of Work with 50+ Repositories Cause Performance Issues?
Short answer: No, not directly—but there are critical caveats to watch for.
Here’s why:
- A Repository is essentially just a wrapper around a
DbSet(or similar data access abstraction) within your Unit of Work (tied to a singleDbContext). The number of Repositories you expose doesn’t add overhead to theDbContextitself. TheDbContext’s performance is driven by things like:- How many entities it’s tracking at once (long-lived
DbContextinstances holding hundreds/thousands of tracked entities will slow down change detection) - The efficiency of your queries (N+1 problems, unoptimized joins, missing database indexes)
- Whether you’re using
AsNoTracking()for read-only operations (reduces tracking overhead drastically)
- How many entities it’s tracking at once (long-lived
- The bigger issue with 50+ Repositories is maintainability, not performance. It’s easy to end up with duplicate code, inconsistent query patterns, or a bloated codebase that’s hard for new team members to navigate.
Second: Should You Split DbContexts by Schema? Tradeoffs to Consider
Splitting DbContexts per schema is a valid way to reduce complexity, but it comes with significant tradeoffs you need to weigh:
Pros of Schema-Based DbContext Splitting
- Clearer separation of concerns: Each
DbContextonly handles entities from one schema, making the codebase more modular and easier to reason about. - Better database-level isolation: You can apply schema-specific permissions, backup strategies, or even scale schemas independently if needed.
- Smaller
DbContextfootprints: EachDbContexthas fewer entity configurations, which can speed up initial setup (though this is usually negligible for most apps).
Cons of Schema-Based DbContext Splitting
- Distributed transaction complexity: If your business logic requires operations across multiple schemas (e.g., updating an order in the
salesschema and a customer in thecrmschema), you’ll need to handle distributed transactions (which add overhead and complexity) or implement saga patterns to manage consistency without transactions. - Code duplication: You’ll likely end up repeating configuration code (like connection strings, logging, or interceptor setup) across multiple
DbContexts unless you build a shared base class. - Cross-schema query headaches: Joining entities from different
DbContexts isn’t straightforward—you’ll either have to write raw SQL or handle data fetching manually across contexts, which can get messy fast. - Increased cognitive load: Your team will need to manage multiple
DbContexts, understand which Repositories belong to which context, and avoid accidental cross-context operations.
Practical Compromises to Try Before Full Splitting
If you want to avoid the complexity of splitting DbContexts but improve maintainability with 50+ Repos, try these steps:
- Group Repositories by domain, not schema: Organize your Repositories into logical folders/namespaces (e.g.,
SalesRepos,CustomerRepos,InventoryRepos) even if they share the sameDbContext. This makes the codebase easier to navigate without splitting the data layer. - Use generic base Repositories: Create a
BaseRepository<T>that handles common CRUD operations, then have your specific Repositories inherit from it. This reduces code duplication and cuts down on the number of distinct Repository classes you need to maintain. - Optimize
DbContextusage:- Keep
DbContextinstances short-lived (e.g., scoped per request in web apps) to avoid excessive entity tracking. - Use
AsNoTracking()for all read-only queries to reduce overhead. - Enable
SplitQueryfor complex joins to avoid large result sets and Cartesian product issues.
- Keep
- Gradual schema splitting: Instead of splitting all schemas at once, start with the most independent ones (e.g., a
loggingschema orconfigschema that doesn’t interact with core business entities). This lets you test the waters without disrupting the entire application.
Final Takeaway
A Unit of Work with 50+ Repositories won’t hurt performance, but it will hurt maintainability over time. Splitting DbContexts per schema solves the maintainability problem but introduces significant complexity—especially if your app has cross-schema business logic. Start with optimizing your existing Repository/DbContext design first, then consider gradual splitting only if the maintainability pain becomes unbearable.
内容的提问来源于stack exchange,提问作者Nathan Kamenar

