java - 模型和 DTO 之间映射对象时出现的问题

标签 java model dto

我正在以下模型之间进行映射:

@Entity
@Table(name="account_type")
@NamedQuery(name="AccountType.findAll", query="SELECT a FROM AccountType a")
public class AccountType implements Serializable {
    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue
    @Column(name="account_type_id")
    private Integer accountTypeId;

    @Column(name="account_type_code")
    private String accountTypeCode;

    @OneToMany(mappedBy="accountType")
    private Set<Account> accounts;

其中有一组帐户:

@Entity
@NamedQuery(name="Account.findAll", query="SELECT a FROM Account a")
public class Account implements Serializable {
    private static final long serialVersionUID = 1L;

@Id
@GeneratedValue
@Column(name="account_id")
private Integer accountId;

@Column(name="account_number")
private String accountNumber;

@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="account_type_id_fk")
private AccountType accountType;

以及他们的DTO

我在映射诸如 Account 之类的复杂类型时遇到问题:

public static Account getAccount(AccountDTO dto) {
        Account model = new Account();
        
        model.setAccountId(dto.getAccountId());
        model.setAccountNumber(dto.getAccountNumber());
        
        model.setAccountType(dto.getAccountType());
        // Error: can't convert from AccountypeDTO to AccountType

        return model;
    }

出现错误,无法从 AccountypeDTO 转换为 AccountType

所以我做了以下事情:

model.setAccountType(getAccountType(dto.getAccountType()));

其中 getAccountType 方法是:

public static AccountType getAccountType(AccountTypeDTO dto) {
        
        AccountType model = new AccountType();

        model.setAccountTypeId(dto.getAccountTypeId());
        model.setAccountTypeCode(dto.getAccountTypeCode());

        model.setAccounts(dto.getAccounts());
        // Now here again a similar error
    }

我认为这是一个深度递归?怎么解决这个问题?

我的问题是如何有效地转换它们。

附件

<小时/>

acountTypeDTO的代码:

@Component
@Scope(value="session", proxyMode=ScopedProxyMode.TARGET_CLASS)
public class AccountTypeDTO implements Serializable {
    private static final long serialVersionUID = 1L;

    @NotNull
    @NotEmpty
    private Integer accountTypeId;

    @NotNull
    @NotEmpty
    private String accountTypeCode;

    private Set<AccountDTO> accounts;

AccountDTO的代码:

@Component
@Scope(value="session", proxyMode=ScopedProxyMode.TARGET_CLASS)
public class AccountDTO implements Serializable {
    private static final long serialVersionUID = 1L;

    @NotNull
    @NotEmpty
    private Integer accountId;

    @NotNull
    @NotEmpty
    private String accountNumber;

    private AccountTypeDTO accountType;

最佳答案

我想到了两种替代方法,但它们需要一些改变。我将在序言中说,我还没有遇到转换为 DTO(即使我正在进行深度递归转换)成为瓶颈的情况。即使您的性能要求或规模如此之大,以至于在某种程度上确实成为了瓶颈,那么我个人建议在我开始担心具体级别的性能之前将工作划分到多个服务器上。另外,它可能看起来效率低下,但性能很少是直观的,您是否确认此转换是瓶颈?

第一个替代方案是不使用单独的类作为 DTO。有些方法使用与 DTO 和底层实体相同的类,有些方法使用 DTO 作为父类,将实体类作为子类。这将使您不必进行任何类型的 DTO<->Entity 转换。但也有缺点,因为这几乎总是最终将两个职责合并到一个类中,并且会使您的代码更加复杂且可读性较差。

第二种选择是不返回帐户本身,而是将它们转换为 ID。在这种方法中,您的 AccountTypeDTO 将具有 Set<Integer> accountIds而不是Set<AccountDTO> accounts 。但是,只有当您的客户并不总是需要对每个帐户进行操作时,这才有效。

关于java - 模型和 DTO 之间映射对象时出现的问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29994916/

相关文章:

java - Spring mvc表单预填充: list with preferences

javascript - 如何在 TypeScript 中将 api 数据转换为 DTO(数据传输对象)

java - 从 if-then 语句设置整数

java - 从 Windows 命令提示符运行带有 Access 数据库的 Java 应用程序

java - 在 URL 对象中设置自定义 HTTP 请求 header 不起作用

database - 多属性模型EAV数据库设计(其他模型)

java - 有没有办法提供 EObject (EMF) 的只读表示?

java - 为什么我不断收到这个该死的 SQL*Plus 无效标识符错误?

java - 不理解 ComboBox 的这个 NullPointerException

java - GWT错误: The response could not be deserialized