Some uncertainty with implementing the 3 structure Model (Domain object, data mapper and service)

末鹿安然 提交于 2019-12-04 10:51:31

I am going through the same thing you are right now (funny enough, for this exact problem - user registration/authorization).

One piece of advice that I have is that you should not restrict your model to just 3 layers (in this case, 3 classes). A model should be as many classes as needed in order to get the job done while maintaining SRP (single responsibility principle) integrity.

For example, you might also want to use a UserTableGateway class to compliment the UserDataMapper, and a UserCollection class to allow for potential pagination functionality or general lists of users. All of those things could be part of your model and UserService layer.

To answer your question about the logic specific to the registration process, yes, the most appropriate place for it is in the register methods of the UserService class.

All that said, you might want to think about your domain structure here. Is a UserService the most appropriate place for registration (and by extension, login, recover password, change password etc)?

Perhaps those things could be part of a totally different model related to Accounts. A service class could be something like this:

class Account 
{
    // Think of this as AccountService, it will have a number of collaborators,
    // including an Authenticator class for loggin in, a Session class for managing the session
    // and of course various persistence classes for storing the user, session and credentials


    public function register(UserInterface $user) {}
    public function login($email, $password) {}
    public function logout(UserInterface $user, $session_id) {}
    public function changePassword($user_id, $old_password, $new_password) {}
    public function recoverPassword($user_id, $email) {}
}

Given there are potentially dozens of other things a UserService could be responsible for, it makes sense for you to keep everything related to the user's account in its own service class.

Conceptually, an account is different from a user anyway, and if it's conceptually different, it deserves its own class.

Now, as far as getting the Account service class the dependencies it needs, that's beyond me at this stage in my understanding of complex system design.

This is an interesting question. I suppose your user Data Mapper has methods for finding & loading users based on some criteria (like username). Therefore, in this case I would do the check inside UserService::register by trying to find a user having the provided username (if it exists):


if ($mapper->findUserByUsername($username)) { 
    // username is already taken, handle this special case
}

By the way, I don't know if you read this, but a very good guide is Martin's Fowler book - Patterns of Enterprise Application Architecture. You will find good answers for many of your questions.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!