我有以下课程:
class User {
public function setName($value) { ... }
public function setEmailAddress($value) { ... }
public function setUsername($value) { ... }
public function getName() { ... }
public function getEmailAddress() { ... }
public function getUsername() { ... }
public function isGroupAdministrator($groupId) { ... }
public function isMemberOfGroup($groupId) { ... }
public function isSiteAdministrator() { ... }
public function isRoot() { ... }
public function hasModulePermission($moduleId, $recordId, $permissionCode) { ... }
public function hasGroupPermission($groupId, $permissionCode) { ... }
public function hasContentPermission($recordId, $permissionCode) { ... }
public function hasModulePermission($moduleId, $recordId, $permissionCode) { ... }
public function canLogIn() { ... }
public function isLoggedIn() { ... }
public function setCanLogIn($canLogIn) { ... }
}
这会变成“神级吗?”
我不确定是否应该将这个课分开。这样做的问题是,该类的方法被其域用于确定是否在网页上显示给定的UI元素,因此该类中没有任何行为。
我想我可以将权限相关的方法放在一些Permission类中,使这些方法保持静态(例如。:: userIsGroupAdministrator(...),:: userIsMemberOfGroup(...):: userHasGroupPermission(...) ,:: userHasContentPermission(...))
关于这门课程如何更好的任何建议?
答案 0 :(得分:9)
如果您已经运行了代码,那么请以小块重构。如果不是,我会看以下内容:
class User {
String username
String name
String emailAddress
Boolean active
Integer permission # A bitmask of the statics in the Permission class
}
class Group {
String name
}
class UserGroupMapping {
User user
Group group
Boolean administrator
}
class Permission {
static IS_ROOT = 1
static IS_SITE_ADMIN = 2
}
class Session {
User user
Boolean logged_in
}
其余部分确实属于服务类:
class SecurityService {
static public function hasModulePermission($user, $module, $record, $permission) { ... }
static public function hasGroupPermission($user, $group, $permission) { ... }
static public function hasContentPermission($user, $record, $permission) { ... }
static public function hasModulePermission($user, $module, $record, $permission) { ... }
}
答案 1 :(得分:8)
是的,我认为你的用户类做得太多了。
将一些与组相关的函数拆分为Group类,并将与模块相关的函数拆分为Module类。或者可能将权限拆分为自己的一组类。
答案 2 :(得分:4)
很难从方法名称中分辨出来。我用来打破课堂的一种启发式方法是查看状态变量。是否存在易于一起使用的州?他们可以分成一个单独的班级吗?
答案 3 :(得分:1)
如果您可以描述User
对象的行为方式,与之交互的对象,环境等等,将会有所帮助。
我想我可以将权限相关的方法放在一些Permission类[...]
中
是的,您可以查看基于策略的设计。
我还建议您取出User
的固定状态,即电子邮件/姓名等,并将其放在单独的课程中。
答案 4 :(得分:1)
现在在您的应用程序中添加新功能或维护现有功能有多困难?如果你在这方面没有遇到问题,那么你可能可以保持现状(至少在一段时间内)。
是的,您的User类有一些重叠的职责,可能会被重构到Role-based access control系统中。
底线是:你真的是gonna need it吗?
答案 5 :(得分:0)
我会考虑创建一个Permissions类,并使其成为User类的成员。
答案 6 :(得分:0)
我会拆分该类的“用户”方面和“组”管理方面。
答案 7 :(得分:0)
我至少会删除setCanLogIn($canLogIn)
功能。这应该在类中内部确定,具体取决于用户是否提供了正确的凭据并且已经过身份验证。
根据此项目的大小,或者这是否是框架的一部分,将确定是否需要更多抽象。
答案 8 :(得分:0)
您似乎需要User对象中的单独ACL和Role对象 http://en.wikipedia.org/wiki/Role-based_access_control
您还可以看到how it's done in ZF。
为了便于阅读,您可以考虑使用__get()
and __set()
代替:
public function setName($value) { ... }
public function setEmailAddress($value) { ... }
public function setUsername($value) { ... }
public function getName() { ... }
public function getEmailAddress() { ... }
public function getUsername() { ... }
答案 9 :(得分:0)
看起来合情合理。当然,我不知道应用程序。我认为分解Permissions类是有意义的。
理想情况下,你会考虑拥有一个权限类意味着什么 - 它知道什么,它的实际行动是什么?此外,由于“权限”是复数,您可能想知道您是否真的想要一个单独的Permission对象的集合,但是如果它们实际上是一个可能过度的简单布尔值的访问者。
答案 10 :(得分:0)
只要类上的方法返回实例数据或仅修改内部状态,该类就没有错误。
但是,例如如果canLogIn()方法寻找一些外部服务(存储库,成员服务等),则存在简单性和可测试性的问题。如果是这种情况,您必须拥有一些服务类并在其上具有这些方法。像
new SomeFactory().GetUserService().canLogIn(user);
答案 11 :(得分:0)
这不是太糟糕,但我认为你的权限机制可以使用因子分解。这是一个明确要求聚合而不是继承的情况。如果有可能将非平凡的联系信息与用户相关联,您可能也想要将电子邮件地址分解出来,也可能转换为可以在需要时加载其他联系信息的身份。
一般来说,我可以建议将用户视为聚合和编写(不继承)功能子单元的中心点 - 这种方法在“实体系统”的标题下实现游戏开发中的流行语状态。
答案 12 :(得分:0)
离开这些......他们找到了IMO:
public function isLoggedIn() { ... }
public function getEmailAddress() { ... }
public function setEmailAddress() { ... }
建议您使用Get / Set Name函数替换它们,这些函数处理TUserName的实例:
public function getUsername() { ... }
public function setUsername($value) { ... }
public function getName() { ... }
public function setName($value) { ... }
TUserName会:
.FirstName
.LastName
.MiddleName
.UserName
建议您使用Get / Set Admin函数替换它们,这些函数处理TUserGroup的实例:
public function isGroupAdministrator($groupId) { ... }
public function isMemberOfGroup($groupId) { ... }
public function isSiteAdministrator() { ... }
public function isRoot() { ... }
TUserGroup会:
.MemberOfGroup(GroupID)
.AdminSite
.Root
.AdminGroup(GroupID)
建议你用Get / Set Permission函数替换它们,它们处理TUserPermissions的一个实例:
public function hasModulePermission($moduleId, $recordId, $permissionCode)
public function hasGroupPermission($groupId, $permissionCode)
public function hasContentPermission($recordId, $permissionCode)
public function hasModulePermission($moduleId, $recordId, $permissionCode)
public function canLogIn()
public function setCanLogIn($canLogIn)
TUserPermissions会有:
.ModulePermitted(ModuleID,RecordID,PermCode)
.GroupPermitted(GroupID,PermCode)
.ContentPermitted(RecordID,PermCode)
.ModulePermitted(ModuleID,RecordID,PermCode)
.CanLogIn