Unmarshal отсутствует атрибут xml для необязательного объекта Java - PullRequest
0 голосов
/ 13 июня 2018

Я пытаюсь распаковать xml-файл, который имеет некоторые необязательные атрибуты (атрибут может быть включен в элемент, но иногда он отсутствует).Как я могу создать необязательные объекты Java из этих атрибутов?

XML:

...
<example a="s"
     b="2.0"
/>
<example a="z"
/>
...

Java:

@XmlRootElement(name = "example")
public class ExampleDTO {

  private String a;
  private Optional<Float> b;

  public String getA() {
    return a;
  }

  @XmlAttribute
  public void setA(String a) {
    this.a = a;
  }

  public Optional<Float> getB() {
    return b;
  }

  @XmlAttribute
  @XmlJavaTypeAdapter(FloatOptionalAdapter.class)
  public void setB(Optional<Float> b) {
    this.b= b;
  }

Адаптер:

public class FloatOptionalAdapter extends XmlAdapter<Float, Optional<Float>> {

  @Override
  public Optional<Float> unmarshal(Float v) throws Exception {
    return Optional.ofNullable(v);
  }

  @Override
  public Float marshal(Optional<Float> v) throws Exception {
    if (v == null || !v.isPresent()) {
      return null;
    } else {
      return v.get();
    }
  }
}

Когда я запускаю этот код, я получаю 2 объекта ExampleDTO.В первом я получаю необязательный объект со значением "2.0".Во втором значение b равно нулю.Как я могу сделать значение пустым Необязательным объектом?

1 Ответ

0 голосов
/ 13 июня 2018

Во-первых, никогда не оставляйте Optional<T> поля в состоянии null , поскольку это просто отрицает всю цель использования типа Optional<T>.

Убедитесь, что они имеютЗначение ненулевое перед тем, как позволить пользователям API получить к нему доступ и выполнять над ним операции, например, private Optional<Float> b; было бы гораздо лучше объявить как private Optional<Float> b = Optional.empty() (что на самом деле может решить вашу текущую проблему).

Кроме того, я не фанат использования в качестве параметров метода Optional ( см. Здесь ).

Тот факт, что ваш setB потребляет Optional<T>, означает, что любойможно присвоить любое значение полю b, а это значит, что можно даже сделать setB(null), упс ...

Как уже упоминалось, в идеале вам следует избегать использования необязательных в качестве параметров, но если вы хотите сохранить его какЗатем я бы предложил выполнить некоторую проверку, чтобы предотвратить передачу null методу setB(...), так как снова это отрицает цель использования Optional.

Наконец, значение по умолчанию b beOptional.empty() а также предотвращение null, передаваемый методу setB(...), означает, что b никогда не может быть null, что всегда должно иметь место, чтобы использовать тип Optional<T>.

...