Jackson JSON处理器在反序列化期间覆盖对象的属性

Jackson JSON处理器在反序列化期间覆盖对象的属性,json,properties,deserialization,jackson,overwrite,Json,Properties,Deserialization,Jackson,Overwrite,我有个有趣的问题。Jackson使用具有相同名称的“子”对象的属性值覆盖“父”对象的属性值。更准确地说,这是我的Java结构 public class Contact { ... String name; List<Email> emails; List<PhoneNumbers> phoneNumbers; Account account; ... } public class Account { ...

我有个有趣的问题。Jackson使用具有相同名称的“子”对象的属性值覆盖“父”对象的属性值。更准确地说,这是我的Java结构

public class Contact {
    ...
    String name;
    List<Email> emails;
    List<PhoneNumbers> phoneNumbers;
    Account account;
    ...
}

public class Account {
    ...
    String accountName;
    List<Email> emails;
    List<PhoneNumbers> phoneNumbers;
    Account account;
    ...
}
公共类联系人{
...
字符串名;
列出电子邮件;
列出电话号码;
账户;
...
}
公共类帐户{
...
字符串accountName;
列出电子邮件;
列出电话号码;
账户;
...
}
所以,当我形成Contact JSON对象并将其发送到服务器时,一切都会正常进行,直到BeanDeserializer进入Contact类的account属性。然后,它开始读取JSON中account部分的proeprities,这是可以的,但不会创建account实例来在contact上设置它——它将account属性的值写入到与contact实例同名的属性中


我很困惑,不知道从哪里开始寻找解决方法。

我无法重现任何类似于原始问题中描述的问题

下面的示例是根据原始问题中的描述创建的,按照预期工作,没有错误或不正确的反序列化

import java.util.LinkedList;
import java.util.List;

import org.codehaus.jackson.annotate.JsonAutoDetect.Visibility;
import org.codehaus.jackson.annotate.JsonCreator;
import org.codehaus.jackson.annotate.JsonProperty;
import org.codehaus.jackson.map.ObjectMapper;

public class JacksonFoo
{
  public static void main(String[] args) throws Exception
  {
    Account account1 = new Account();
    account1.accountName = "account 1";
    account1.emails = new LinkedList<Email>();
    account1.emails.add(new Email("email_11@google.com"));
    account1.emails.add(new Email("email_12@google.com"));
    account1.phoneNumbers = new LinkedList<PhoneNumbers>();
    account1.phoneNumbers.add(new PhoneNumbers(1111, 1112));
    account1.phoneNumbers.add(new PhoneNumbers(1113, 1114));

    Account account2 = new Account();
    account2.accountName = "account 2";
    account2.emails = new LinkedList<Email>();
    account2.emails.add(new Email("email_21@google.com"));
    account2.emails.add(new Email("email_22@google.com"));
    account2.phoneNumbers = new LinkedList<PhoneNumbers>();
    account2.phoneNumbers.add(new PhoneNumbers(2221, 2222));
    account2.phoneNumbers.add(new PhoneNumbers(2223, 2224));
    account2.account = account1;

    Contact contact = new Contact();
    contact.name = "contact";
    contact.emails = new LinkedList<Email>();
    contact.emails.add(new Email("email_31@google.com"));
    contact.emails.add(new Email("email_32@google.com"));
    contact.phoneNumbers = new LinkedList<PhoneNumbers>();
    contact.phoneNumbers.add(new PhoneNumbers(3331, 3332));
    contact.phoneNumbers.add(new PhoneNumbers(3333, 3334));
    contact.account = account2;

    ObjectMapper mapper = new ObjectMapper();
    mapper.setVisibilityChecker(  
        mapper.getVisibilityChecker()  
          .withFieldVisibility(Visibility.ANY));

    String account1Json = mapper.writeValueAsString(account1);
    String account2Json = mapper.writeValueAsString(account2);
    String contactJson = mapper.writeValueAsString(contact);

    System.out.println(account1Json); // {"accountName":"account 1","emails":[{"email":"email_11@google.com"},{"email":"email_12@google.com"}],"phoneNumbers":[{"phone1":1111,"phone2":1112},{"phone1":1113,"phone2":1114}],"account":null}
    System.out.println(account2Json); // {"accountName":"account 2","emails":[{"email":"email_21@google.com"},{"email":"email_22@google.com"}],"phoneNumbers":[{"phone1":2221,"phone2":2222},{"phone1":2223,"phone2":2224}],"account":{"accountName":"account 1","emails":[{"email":"email_11@google.com"},{"email":"email_12@google.com"}],"phoneNumbers":[{"phone1":1111,"phone2":1112},{"phone1":1113,"phone2":1114}],"account":null}}
    System.out.println(contactJson); // {"name":"contact","emails":[{"email":"email_31@google.com"},{"email":"email_32@google.com"}],"phoneNumbers":[{"phone1":3331,"phone2":3332},{"phone1":3333,"phone2":3334}],"account":{"accountName":"account 2","emails":[{"email":"email_21@google.com"},{"email":"email_22@google.com"}],"phoneNumbers":[{"phone1":2221,"phone2":2222},{"phone1":2223,"phone2":2224}],"account":{"accountName":"account 1","emails":[{"email":"email_11@google.com"},{"email":"email_12@google.com"}],"phoneNumbers":[{"phone1":1111,"phone2":1112},{"phone1":1113,"phone2":1114}],"account":null}}}

    Account account1Copy = mapper.readValue(account1Json, Account.class);
    Account account2Copy = mapper.readValue(account2Json, Account.class);
    Contact contactCopy = mapper.readValue(contactJson, Contact.class);

    System.out.println(account1.equals(account1Copy)); // true
    System.out.println(account2.equals(account2Copy)); // true
    System.out.println(contact.equals(contactCopy)); // true
  }
}

class Contact
{
  String name;
  List<Email> emails;
  List<PhoneNumbers> phoneNumbers;
  Account account;

  @Override
  public boolean equals(Object o)
  {
    Contact c = (Contact) o;
    if (name.equals(c.name))
      if (emails.containsAll(c.emails))
        if (c.emails.containsAll(emails))
          if (phoneNumbers.containsAll(c.phoneNumbers))
            if (c.phoneNumbers.containsAll(phoneNumbers))
              return account.equals(c.account);
    return false;
  }
}

class Account
{
  String accountName;
  List<Email> emails;
  List<PhoneNumbers> phoneNumbers;
  Account account;

  @Override
  public boolean equals(Object o)
  {
    Account a = (Account) o;
    if (accountName.equals(a.accountName))
      if (emails.containsAll(a.emails))
        if (a.emails.containsAll(emails))
          if (phoneNumbers.containsAll(a.phoneNumbers))
            if (a.phoneNumbers.containsAll(phoneNumbers))
              if (account != null && a.account != null)
                return account.equals(a.account);
              else if (account == null && a.account == null)
                return true;
    return false;
  }
}

class Email
{
  String email;

  @JsonCreator
  Email(@JsonProperty("email") String e) {email = e;}

  @Override
  public boolean equals(Object o)
  {
    Email e = (Email) o;
    return email.equals(e.email);
  }
}

class PhoneNumbers
{
  long phone1;
  long phone2;

  @JsonCreator
  PhoneNumbers(@JsonProperty("phone1") long p1, @JsonProperty("phone2")long p2) {phone1 = p1; phone2 = p2;}

  @Override
  public boolean equals(Object o)
  {
    PhoneNumbers p = (PhoneNumbers) o;
    return phone1 == p.phone1 && phone2 == p.phone2;
  }
}
import java.util.LinkedList;
导入java.util.List;
导入org.codehaus.jackson.annotate.JsonAutoDetect.Visibility;
导入org.codehaus.jackson.annotate.JsonCreator;
导入org.codehaus.jackson.annotate.JsonProperty;
导入org.codehaus.jackson.map.ObjectMapper;
公务舱杰克逊福
{
公共静态void main(字符串[]args)引发异常
{
账户1=新账户();
account1.accountName=“account1”;
account1.emails=新链接列表();
帐户1.电子邮件。添加(新电子邮件(“电子邮件”)_11@google.com"));
帐户1.电子邮件。添加(新电子邮件(“电子邮件”)_12@google.com"));
account1.phoneNumbers=新建LinkedList();
account1.phoneNumbers.add(新电话号码(1111112));
account1.phoneNumbers.add(新电话号码(11131114));
账户account2=新账户();
account2.accountName=“account2”;
account2.emails=新链接列表();
账户2.电子邮件。添加(新电子邮件(“电子邮件”)_21@google.com"));
账户2.电子邮件。添加(新电子邮件(“电子邮件”)_22@google.com"));
account2.phoneNumbers=新建LinkedList();
account2.phoneNumbers.add(新电话号码(22212222));
account2.phoneNumbers.add(新电话号码(2223224));
account2.account=account1;
触点=新触点();
contact.name=“contact”;
contact.emails=新建LinkedList();
contact.emails.add(新电子邮件(“电子邮件”)_31@google.com"));
contact.emails.add(新电子邮件(“电子邮件”)_32@google.com"));
contact.phoneNumbers=新建LinkedList();
contact.phoneNumbers.add(新电话号码(3331332));
联系人。电话号码。添加(新电话号码(3333334));
contact.account=account2;
ObjectMapper mapper=新的ObjectMapper();
mapper.setVisibilityChecker(
mapper.getVisibilityChecker()
.具有现场可视性(Visibility.ANY));
字符串account1Json=mapper.writeValueAsString(account1);
字符串account2Json=mapper.writeValueAsString(account2);
字符串contactJson=mapper.writeValueAsString(contact);
System.out.println(account1Json);//{“accountName”:“account1”,“email”:[{“email”:“email”_11@google.com},{“电子邮件”:“电子邮件”_12@google.com“}],“PhoneNumber”:[{“phone1”:1111,“phone2”:1112},{“phone1”:1113,“phone2”:1114}],“account”:null}
System.out.println(account2Json);//{“accountName”:“account2”,“email”:[{“email”:“email”_21@google.com},{“电子邮件”:“电子邮件”_22@google.com“}],“电话号码”:[{“电话1”:2221,“电话2”:2222},{“电话1”:2223,“电话2”:2224}],“帐户”:{“帐户名”:“帐户1”,“电子邮件”:[{“电子邮件”:“电子邮件”_11@google.com},{“电子邮件”:“电子邮件”_12@google.com“}],“电话号码”:[{“phone1”:1111,“phone2”:1112},{“phone1”:1113,“phone2”:1114}],“account”:null}
System.out.println(contactJson);//{“姓名”:“联系人”,“电子邮件”:[{“电子邮件”:“电子邮件”_31@google.com},{“电子邮件”:“电子邮件”_32@google.com“}],“电话号码”:[{“电话1”:3331,“电话2”:3332},{“电话1”:3333,“电话2”:3334}],“帐户”:{“帐户名”:“帐户2”,“电子邮件”:[{“电子邮件”:“电子邮件”_21@google.com},{“电子邮件”:“电子邮件”_22@google.com}],“电话号码”:[{“phone1”:2221电话2:2222},{“电话1:2223”,“电话2:2224}],“帐户”:{“帐户名”:“帐户1”,“电子邮件”:[{“电子邮件”:“电子邮件”_11@google.com},{“电子邮件”:“电子邮件”_12@google.com“}],“PhoneNumber”:[{“phone1”:1111,“phone2”:1112},{“phone1”:1113,“phone2”:1114}],“account”:null}
Account account1Copy=mapper.readValue(account1Json,Account.class);
Account account2Copy=mapper.readValue(account2Json,Account.class);
Contact-contactCopy=mapper.readValue(contactJson,Contact.class);
System.out.println(account1.equals(account1Copy));//true
System.out.println(account2.equals(account2Copy));//true
System.out.println(contact.equals(contactCopy));//true
}
}
班级联系
{
字符串名;
列出电子邮件;
列出电话号码;
账户;
@凌驾
公共布尔等于(对象o)
{
触点c=(触点)o;
if(name.equals(c.name))
如果(电子邮件,包含所有电子邮件)
如果(包括所有电子邮件)
if(phonenumber.containsAll(c.phonenumber))
if(c.phoneNumbers.containsAll(phoneNumbers))
返回账户。等于(c账户);
返回false;
}
}
类别帐户
{
字符串accountName;
列出电子邮件;
列出电话号码;
账户;
@凌驾
公共布尔等于(对象o)
{
账户a=(账户)o;
if(accountName.equals(a.accountName))
如果(电子邮件包含所有电子邮件)
如果(a.emails.containsAll(emails))
if(phoneNumbers.containsAll(a.phoneNumbers))
if(a.phoneNumbers.containsAll(phoneNumbers))
if(account!=null&&a.account!=null)
返回账户。等于(a账户);
else if(account==null&&a.account==null)
返回true;
返回fal