Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
242 views
in Technique[技术] by (71.8m points)

c# - How to write functionality using DDD / CQRS

I have a bank account domain as listed below. There can be SavingsAccount, LoanAccount, FixedAccount and so on. One user can have multiple accounts. I need to add a new functionality – get all accounts for a user. Where should be the function written and how?

It would be great if the solution follows SOLID principles( Open-Closed principle,…) and DDD.

Any refactoring that would make the code better is welcome.

Note: The AccountManipulator will be used by a website client over a web service.

namespace BankAccountBL
{
public class AccountManipulator
{
    //Whether it should beprivate or public?
    private IAccount acc;

    public AccountManipulator(int accountNumber)
    {
        acc = AccountFactory.GetAccount(accountNumber);
    }

    public void FreezeAccount()
    {
        acc.Freeze();
    }

}

public interface IAccount
{
    void Freeze();
}

public class AccountFactory
{
    public static IAccount GetAccount(int accountNumber)
    {
        return new SavingsAccount(accountNumber);
    }
}

public class SavingsAccount : IAccount
{
    public SavingsAccount(int accountNumber)
    {

    }

    public void Freeze()
    {

    }
}
}

READING:

  1. When to use the CQRS design pattern?

  2. In domain-driven design, would it be a violation of DDD to put calls to other objects' repostiories in a domain object?

  3. Refactoring domain logic that accesses repositories in a legacy system

  4. Which of these examples represent correct use of DDD?

  5. Good Domain Driven Design samples

  6. Advantage of creating a generic repository vs. specific repository for each object?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

if your AccountManipulator is a Fa?ade to your domain, I wouldn't put the account number in the constructor. I would refactor it this way:

public class AccountManipulator
{
    private  AccountFactory _factory;
    private UserRepository _users;

    public AccountManipulator(AccountFactory factory, UserRepository users)
    {
       _factory = factory;
       _users = users;
    }

    public void FreezeAccount(int accountNumber)
    {
       var acc = _factory.GetAccount(accountNumber);
       acc.Freeze();
    }

    public IEnumerable<IAccount> GetAccountsOf(User user) {
       return _users.GetAccountIds(user).Select(_factory.GetAccount);
    }
}

public interface UserRepository {
    IEnumerable<int> GetAccountIds(User user);
}

In order to state if your domain is SOLID, you should analyze it with the principle:

  • Single Responsibility: every object has is own responsibility (and only that one):
    • AccountFactory: creates IAccounts
    • SavingsAccount: implementation of IAccount that reads from/writes to (a database? a web service?)
    • AccountManipulator: provide a minimal and simple set of operations to do with domain objects.
  • Open/Closed: are you classes are open to extensions and closed to changes?
    • AccountFactory: well, no. If you write a new implementation of IAccount, in order to use it you have to change AccountFactory. Solution: abstract factory
    • SavingsAccount? It depends if it will use external dependencies. Need more code to say.
    • AccountManipulator: yes. If you need to do another operation with your domain objects, you can use directly the other services without change AccountManipulator. Or you can inherit from it
  • Liskov substitution: can you substitute any class with another implementation? Need more code to say. You have no other implementations of IAccount or IAccountFactory now
  • Dependency Inversion:
    • AccountManipulator should depend on abstractions: AccountFactory and UserRepository should be interfaces.

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...