Polymorphic collections in SnakeYaml

我的未来我决定 提交于 2021-01-27 04:20:57

问题


My intention is to have polymorphic collections like the ones in JSON using jackson, maybe with the help of tags.

I can't seem to able to configure it properly tho.

My yaml file is:

!person
age: 27
job: dev
name: me
skills:
- !devSkill {
  description: 'software development',
  name: android,
  language: java, c++
  years: 7
}
- !softSkill {
  description: 'good person',
  name: <3,
  reason: lots of NGO work
}
- !sportsSkill {
  description: 'racing legend',
  name: vrooom,
  championships: - San Marino 2012
                 - San Marino 2015
}

Which in code would map to a hierarchy with an (abstract?) BaseSkill with description and name, and 3 children: dev, soft and sports.

My problem is, I don't understand SnakeYAML's documentation enough to allow this. My current options are:

Constructor constructor = new Constructor(Person.class);
TypeDescription carDescription = new TypeDescription(Person.class);
                carDescription.putListPropertyType("skills", SportsSkill.class);
                carDescription.putListPropertyType("skills", SoftSkill.class);
                carDescription.putListPropertyType("skills", DevSkill.class);
                // Apparently the last is the winner here because it overrides
                constructor.addTypeDescription(carDescription);

Representer representer = new Representer();
                representer.addClassTag(Person.class, new Tag("!person"));
                representer.addClassTag(SoftSkill.class, new Tag("!Softkill"));
                representer.addClassTag(DevSkill.class, new Tag("!devSkill"));
                representer.addClassTag(SportsSkill.class, new Tag("!portsSkill"));

DumperOptions options = new DumperOptions();
                options.setPrettyFlow(true);
Yaml yaml = new Yaml(constructor, representer, options);

The error is in the lines of

E/YAML﹕ Can't construct a java object for tag:yaml.org,2002:app.yamlmodel.Person; exception=Cannot create property=skills for JavaBean=Person(name=me, job=dev, age=27, skills=null); null; Can't construct a java object for !sportSkill; exception=Invalid tag: !sportSkill
    in "<reader>", line 1, column 1:
    name: me
    ^

回答1:


This thread is quit old but I found a solution for it, hope its still help someone. your mistake is that you should add the tags and type descriptor to the constructor and let SnakeYaml figure out the object structure. In you case:

Constructor constructor = new Constructor(Person.class);
constructor.addTypeDescription(new TypeDescription(SoftSkill.class, new Tag("!softkill"));
constructor.addTypeDescription(new TypeDescription(DevSkill.class, new Tag("!devkill"));
constructor.addTypeDescription(new TypeDescription(SportsSkill.class, new Tag("!sportskill"));

you didnt mention the SnakeYaml version you use but I am using 1.16



来源:https://stackoverflow.com/questions/28176025/polymorphic-collections-in-snakeyaml

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!