推土机深度映射不起作用

发布于 2024-09-05 04:01:14 字数 1926 浏览 10 评论 0原文

我正在尝试使用 dozer 4.1 在类之间进行映射。我有一个如下所示的源类:

    public class initRequest{
     protected String id;
     protected String[] details
}

我有一个如下所示的目标类:

public class initResponse{
       protected String id;
       protected DetailsObject detObj;
}

public class DetailsObject{
 protected List<String>  details;
}

因此,本质上我希望将详细信息数组中的字符串填充到详细信息对象中的列表中。

我尝试过这样的映射:

<mapping wildcard="true" >
  <class-a>initRequest</class-a>
  <class-b>initResponse</class-b>   
  <field>
    <a is-accessible="true">details</a>
    <b is-accessible="true">detObj.details</b>
  </field>
</mapping>

但我收到此错误:

Exception in thread "main" net.sf.dozer.util.mapping.MappingException: java.lang.NoSuchFieldException: detObj.details
    at net.sf.dozer.util.mapping.util.MappingUtils.throwMappingException(MappingUtils.java:91)
    at net.sf.dozer.util.mapping.propertydescriptor.FieldPropertyDescriptor.<init>(FieldPropertyDescriptor.java:43)
    at net.sf.dozer.util.mapping.propertydescriptor.PropertyDescriptorFactory.getPropertyDescriptor(PropertyDescriptorFactory.java:53)
    at net.sf.dozer.util.mapping.fieldmap.FieldMap.getDestPropertyDescriptor(FieldMap.java:370)
    at net.sf.dozer.util.mapping.fieldmap.FieldMap.getDestFieldType(FieldMap.java:103)
    at net.sf.dozer.util.mapping.util.MappingsParser.processMappings(MappingsParser.java:95)
    at net.sf.dozer.util.mapping.util.CustomMappingsLoader.load(CustomMappingsLoader.java:77)
    at net.sf.dozer.util.mapping.DozerBeanMapper.loadCustomMappings(DozerBeanMapper.java:149)
    at net.sf.dozer.util.mapping.DozerBeanMapper.getMappingProcessor(DozerBeanMapper.java:132)
    at net.sf.dozer.util.mapping.DozerBeanMapper.map(DozerBeanMapper.java:94)

如何映射它才能正常工作?

I am trying to use dozer 4.1 to map between classes. I have a source class that looks like this:

    public class initRequest{
     protected String id;
     protected String[] details
}

I have a destination class that looks like this:

public class initResponse{
       protected String id;
       protected DetailsObject detObj;
}

public class DetailsObject{
 protected List<String>  details;
}

So essentially i want the string in the details array to be populated into the List in the Details object.

I have tried a mapping like this:

<mapping wildcard="true" >
  <class-a>initRequest</class-a>
  <class-b>initResponse</class-b>   
  <field>
    <a is-accessible="true">details</a>
    <b is-accessible="true">detObj.details</b>
  </field>
</mapping>

But I get this error:

Exception in thread "main" net.sf.dozer.util.mapping.MappingException: java.lang.NoSuchFieldException: detObj.details
    at net.sf.dozer.util.mapping.util.MappingUtils.throwMappingException(MappingUtils.java:91)
    at net.sf.dozer.util.mapping.propertydescriptor.FieldPropertyDescriptor.<init>(FieldPropertyDescriptor.java:43)
    at net.sf.dozer.util.mapping.propertydescriptor.PropertyDescriptorFactory.getPropertyDescriptor(PropertyDescriptorFactory.java:53)
    at net.sf.dozer.util.mapping.fieldmap.FieldMap.getDestPropertyDescriptor(FieldMap.java:370)
    at net.sf.dozer.util.mapping.fieldmap.FieldMap.getDestFieldType(FieldMap.java:103)
    at net.sf.dozer.util.mapping.util.MappingsParser.processMappings(MappingsParser.java:95)
    at net.sf.dozer.util.mapping.util.CustomMappingsLoader.load(CustomMappingsLoader.java:77)
    at net.sf.dozer.util.mapping.DozerBeanMapper.loadCustomMappings(DozerBeanMapper.java:149)
    at net.sf.dozer.util.mapping.DozerBeanMapper.getMappingProcessor(DozerBeanMapper.java:132)
    at net.sf.dozer.util.mapping.DozerBeanMapper.map(DozerBeanMapper.java:94)

How can i map this so that it works?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

短叹 2024-09-12 04:01:15

这对我有用。我使用的是 5.2.1 版本

 <mapping wildcard="true" >
      <class-a>initRequest</class-a>
      <class-b>initResponse</class-b>   
      <field>
        <a>details</a>
        <b is-accessible="true">detObj.details</b>
      </field>
    </mapping>

请注意,“is-accessable”对于 .希望有帮助

This works for me. I am using 5.2.1 version

 <mapping wildcard="true" >
      <class-a>initRequest</class-a>
      <class-b>initResponse</class-b>   
      <field>
        <a>details</a>
        <b is-accessible="true">detObj.details</b>
      </field>
    </mapping>

Note that "is-accessable" is not required for . Hope it helps

云淡风轻 2024-09-12 04:01:15

问题已解决...

  • is-accessible 允许更新对象,无论访问修饰符和 getter/setter 是否存在(对于使用 JAXB 生成的对象至关重要)

  • 深度映射的“点”表示法可用于访问嵌套对象

将两者结合起来是一个在 Dozer 中不起作用(也许在较新版本中起作用)

解决方案的功能...
修改 xsd,以便不需要深度映射。这不是我理想的解决方案,但它比为每个对象编写自定义转换器更好

Problem solved...

  • is-accesible allows an object to be updated regardless of access modifier and presence of getters/setters (essential for objects generated using JAXB)

  • "dot" notation for deep mapping works to access nested objects

Combining the two is a feature that does not work in Dozer (maybe it does in a newer version)

solution...
modify the xsd such that the deep mapping is not required. This is not my ideal solution but its better than writing a custom converter for every object

错爱 2024-09-12 04:01:15

对于 JaxB,用户可以下载并使用插件来生成 setter。有关更多详细信息,请参阅此链接,https://jaxb2-commons.dev。 java.net/collection-setter-injector/

In case of JaxB, use can download and use the plugin for generating the setters. Refer to this link for more details, https://jaxb2-commons.dev.java.net/collection-setter-injector/

雨的味道风的声音 2024-09-12 04:01:15

我猜想缺少访问器(getter / setter)。
顺便说一句,我认为您还需要为 DetailsObject 提供一个空的构造函数,以便推土机可以实例化它。

I would guess that accessors (getter / setter) are missing.
By the way I think that you'll also need to provide an empty constructor for DetailsObject so dozer can instanciate it.

霞映澄塘 2024-09-12 04:01:15
<b is-accessible="true">detObj.details</b>

应替换为

<b is-accessible="true">DetailsObject.details</b>
<b is-accessible="true">detObj.details</b>

Should be replaced with

<b is-accessible="true">DetailsObject.details</b>
逆夏时光 2024-09-12 04:01:15

虽然您似乎无法同时使用“可访问”和点表示法,但另一种方法是将深度映射分解为更小的映射。

我们在使用 JAX-WS 生成的代码时遇到了这种情况。您的列表没有 setter 方法,并且在我们的例子中是深度嵌套的。我们通过简单地将大型深度映射分解为较小的映射来找到我们的解决方案,这些映射“走”到了我们想要的地方。我试图在我的博客中解释这一点:

http:// /btarlton.blogspot.com/2014/08/dozer-deep-nestinga- Different-approach.html

但诀窍是通过较小的映射遍历对象树,并在必要时使用 is-accessible="true"无需设置器即可访问列表,并使用“this”作为属性名称来继续传递源。

希望这有帮助!

While it does seem you cannnot use the "is-accessible" and dot notation together another approach is to break your deep mapping into smaller mappings.

We ran into this situation with JAX-WS generated code. You have lists that have no setter methods and in our case were deeply nested. We found our solution by simply breaking the large deep mapping into smaller mappings that "walked" our way to what we wanted. I tried to explain this in my blog here:

http://btarlton.blogspot.com/2014/08/dozer-deep-nestinga-different-approach.html

But the trick is just walking the object tree by smaller mappings and using is-accessible="true" when necessary to access the list with no setter and using "this" as the property name to keep passing the source along.

Hope this helps!

别低头,皇冠会掉 2024-09-12 04:01:15

总结一下,这个问题有以下几种选择
1) 使用 JaxB 插件来启用 setter,如 Naveen 所讨论的
2)对此类属性使用 is-accessible

我相信使用第一种方法不必要地公开集合/列表的设置器,因为您可能有将它们设置为 null 的风险。

我们决定为这些字段(而不是整个类)启用 is-accessible 以避免任何副作用。

我已经在Dozer Mapping Class level is-accessible

To summarize there are following options for this issue
1) Use JaxB pluggin to enable setters as discussed by Naveen
2) Use is-accessible for such properties

I believe using first approach unnecessarily exposes setters for collections/lists as you can risk of setting them with null.

We decided to enable is-accessible for such fields (and not to entire class) to avoid any side effects.

I have discussed the solution at Dozer Mapping Class level is-accessible

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文