Java DTO上作为标记接口的用户角色

Java DTO上作为标记接口的用户角色,java,oop,design-patterns,Java,Oop,Design Patterns,我有类似的东西 //A marker Interface public interface User { } //2 DTO Classes public class Administrator implements User{ //getters and setters } public class OperativeUser implements User{ //getters and setters } //A generic interface public interface U

我有类似的东西

//A marker Interface
public interface User {
}

//2 DTO Classes
public class Administrator implements User{
//getters and setters
}

public class OperativeUser implements User{
//getters and setters
}

//A generic interface
public interface UserService<T extends User>{
    public void createUser(T user);    
}
//Two concrete clases
public class AdministratorService implements UserService<Administrator>{
    public void createUser(Administrator user){
       //specific stuff for an administrator
    }    
}
public class OperativeUserService implements UserService<OperativeUser>{
    public void createUser(OperativeUser user){
       //specific stuff for an operative user
    }    
}
new AdministratorService().createUser(new Administrator());
//标记接口
公共界面用户{
}
//2个DTO类
公共类管理员实现用户{
//接球手和接球手
}
公共类用户实现用户{
//接球手和接球手
}
//通用接口
公共接口用户服务{
公共用户(T用户);
}
//两层混凝土
公共类管理员服务实现用户服务


多谢各位

管理员与其他用户之间实际上是角色/权限的问题。在一个成熟的系统中,你可能不止有两个

我建议您首先添加“角色”&一个方便的
isAdministrator()
检查:

public class User {
    public String getName();

    public Set<String> getRoles();
    public boolean isAdministrator();
}
公共类用户{
公共字符串getName();
公共设置getRoles();
公共布尔值isAdministrator();
}
我提议担任
Set';这将便于使用字符串常量检查角色。(备选方案可以是
Set`)

这提供了一种检查管理员角色的简洁方法,使用户成为一个具体的类,不再需要为“普通”用户和管理员提供单独的类型,并使您的角色系统在将来得到完善和扩展


比这更大的系统进一步采用角色结构:它们为“权限”建模,并允许灵活分配用户->角色和角色->权限。然而,这种复杂程度超出了你当前的问题。

这个问题是基于观点的

我正在分享我的观点

您拥有的是一个稍微修改过的版本。这里真正的问题是,你需要这些吗

如果
Administrator
OperativeUser
是值对象(如您的问题所示),并且将具有不同的属性,为什么还要为它们创建超级类型(
User
)?无论如何,您将在代码中的某个地方执行
实例的
检查。在本例中,您的
UserService
被简化为类似的内容(是的,简单的旧方法重载!)

另一方面,如果您的
管理员
操作用户
确实有常用方法,那么它们应该在
用户
界面中声明,该界面现在不再是标记界面

来回答你的问题

1.-有一种更好的方法来实现这种没有继承(扩展)的层次结构,如果是,你能给我一些指导吗

答:除非需要,否则不要使用继承

2.-标记接口的良好使用是我的做法还是我的误解

答:我觉得这个用法不正确。我这样说的原因是,为了根据您的代码示例创建,比方说和
Administrator
,我必须这样写

//A marker Interface
public interface User {
}

//2 DTO Classes
public class Administrator implements User{
//getters and setters
}

public class OperativeUser implements User{
//getters and setters
}

//A generic interface
public interface UserService<T extends User>{
    public void createUser(T user);    
}
//Two concrete clases
public class AdministratorService implements UserService<Administrator>{
    public void createUser(Administrator user){
       //specific stuff for an administrator
    }    
}
public class OperativeUserService implements UserService<OperativeUser>{
    public void createUser(OperativeUser user){
       //specific stuff for an operative user
    }    
}
new AdministratorService().createUser(new Administrator());
如果您只需像我上面解释的那样用更少的代码和更少的层次结构重载方法,也可以实现同样的效果


更多关于为什么标记接口的信息。

嗨,Pravin,关于类型user的事情是因为这样我就可以做以下
@Inject@user(type=“Administrator”)user-Administrator
@Inject@User(Type=“OperativeUser”)用户操作因此,如果新用户未添加任何已经具有relase的内容,则需要对其进行编辑并违反“打开-关闭”Principle@jjam但是,您是否能够在其他地方使用
用户
作为
管理员
,而无需强制转换?。这不是为了方便实例化/注入,而是为了能够多态地使用
用户
实例。此外,我不确定我是否理解这是如何违反开/关原则的。是的,你是对的,我没有意识到我的代码在我的特殊情况下可以正常工作,但在我项目的其他部分,当我需要使用特定用户时,我需要检查该特定对象是否是您前面提到的x对象的实例,它将以我一开始试图避免的意大利面代码结束,这就解决了我的具体问题,回答了我的具体问题,非常感谢,