{"id":12502,"date":"2015-09-06T15:52:00","date_gmt":"2015-09-06T14:52:00","guid":{"rendered":"https:\/\/touk.pl\/blog\/?guid=39d6c3dc9e2e74a2650ac74d0ebb3efe"},"modified":"2022-08-01T09:02:25","modified_gmt":"2022-08-01T07:02:25","slug":"writing-jaxb-in-groovy","status":"publish","type":"post","link":"https:\/\/touk.pl\/blog\/2015\/09\/06\/writing-jaxb-in-groovy\/","title":{"rendered":"Writing JAXB in Groovy"},"content":{"rendered":"<p>Suppose you want write a jaxb class in groovy. Why? Because you do not have to write these all getters, setters and other methods. You only have to write your fields down.<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"groovy\">@XmlRootElement \r\n@HashCodeAndEquals \r\n@ToString \r\nclass Person {\r\n    String firstName String lastName Integer age\r\n}<\/pre>\n<p>&nbsp;<\/p>\n<p>Lets check if we could unmarshal xml to Person class:<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"groovy\">def 'should unmarshall person xml to object'(){\r\n    given:\r\n        JAXBContext jc = JAXBContext.newInstance(Person)\r\n        String xml = 'JohnSmith20' \r\n    expect:\r\n        jc.createUnmarshaller().unmarshal(new StringReader(xml)) == new Person(firstName: 'John', lastName: 'Smith', age: 20)\r\n}<\/pre>\n<p>&nbsp;<\/p>\n<p>When we try this, then we obtain an eception:<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"generic\">com.sun.xml.internal.bind.v2.runtime.IllegalAnnotationsException: 1 counts of IllegalAnnotationExceptions\r\ngroovy.lang.MetaClass is an interface, and JAXB can't handle interfaces.\r\n this problem is related to the following location:\r\n  at groovy.lang.MetaClass\r\n  at public groovy.lang.MetaClass com.blogspot.przybyszd.jaxbingroovy.Person.getMetaClass()\r\n  at com.blogspot.przybyszd.jaxbingroovy.Person\r\n\r\n at com.sun.xml.internal.bind.v2.runtime.IllegalAnnotationsException$Builder.check(IllegalAnnotationsException.java:91)\r\n at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl.getTypeInfoSet(JAXBContextImpl.java:445)\r\n at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl.(JAXBContextImpl.java:277)\r\n at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl.(JAXBContextImpl.java:124)\r\n at com.sun.xml.internal.bind.v2.runtime.JAXBContextImpl$JAXBContextBuilder.build(JAXBContextImpl.java:1123)\r\n at com.sun.xml.internal.bind.v2.ContextFactory.createContext(ContextFactory.java:147)\r\n at javax.xml.bind.ContextFinder.newInstance(ContextFinder.java:247)\r\n at javax.xml.bind.ContextFinder.newInstance(ContextFinder.java:234)\r\n at javax.xml.bind.ContextFinder.find(ContextFinder.java:462)\r\n at javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:641)\r\n at javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:584)\r\n at com.blogspot.przybyszd.jaxbingroovy.PersonJaxbTest.should unmarshall person xml to object(PersonJaxbTest.groovy:10)\r\n\r\n<\/pre>\n<p>It is because groovy defines getMetaClass method for us. Marshaller and Unmarshaller use by default<\/p>\n<p><a href=\"http:\/\/docs.oracle.com\/javaee\/7\/api\/javax\/xml\/bind\/annotation\/XmlAccessType.html#PUBLIC_MEMBER\">XmlAccessType.PUBLIC_MEMBER<\/a> what means that public getters and setters should be used during marshalling\/unmarshalling. To solve this just add <a href=\"http:\/\/docs.oracle.com\/javaee\/7\/api\/javax\/xml\/bind\/annotation\/XmlAccessorType.html\">XmlAccessorType<\/a> annotatnio with <a href=\"http:\/\/docs.oracle.com\/javaee\/7\/api\/javax\/xml\/bind\/annotation\/XmlAccessType.html#FIELD\">XmlAccessType.FIELD<\/a> on jaxb class:<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"groovy\">@XmlRootElement @EqualsAndHashCode @XmlAccessorType(XmlAccessType.FIELD) class Person {\r\n    String firstName String lastName Integer age\r\n}<\/pre>\n<p>&nbsp;<\/p>\n<p>Of course if you want to apply this rule for each jaxb class in package, then you could put XmlAccessorType in pacakge-info.java file.<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"java\">@XmlAccessorType(XmlAccessType.FIELD) package com.blogspot.przybyszd.jaxbingroovy;\r\nimport javax.xml.bind.annotation.XmlAccessType;\r\nimport javax.xml.bind.annotation.XmlAccessorType;<\/pre>\n<p>&nbsp;<\/p>\n<p>Great, it works. Now let&#8217;s check out marshaller:<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"groovy\">def 'should marshall person'() {\r\n    given:\r\n        JAXBContext jc = JAXBContext.newInstance(Person)\r\n        Person p = new Person(firstName: 'John', lastName: 'Smith', age: 20)\r\n        StringWriter sw = new StringWriter()\r\n    when:\r\n        jc.createMarshaller().marshal(p, sw)\r\n    then:\r\n        String xml = sw.toString()\r\n        GPathResult gPathResult = new XmlSlurper().parseText(xml)\r\n        gPathResult.name() == 'person'\r\n        gPathResult.firstName == 'John'\r\n        gPathResult.lastName == 'Smith'\r\n        gPathResult.age == '20'\r\n}<\/pre>\n<p>&nbsp;<\/p>\n<p>And it also works. Source is available <a href=\"https:\/\/github.com\/alien11689\/JaxbInGroovy\">here<\/a>.<\/p>\n","protected":false},"excerpt":{"rendered":"Suppose you want write a jaxb class in groovy. Why? Because you do not have to write these all getters, setters and other methods. You only have to write your fields down.@XmlRootElement@HashCodeAndEquals@ToStringclass Person { String firstName String &#8230;\n","protected":false},"author":54,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[11],"tags":[50,68,107],"class_list":{"0":"post-12502","1":"post","2":"type-post","3":"status-publish","4":"format-standard","6":"category-development-design","7":"tag-groovy","8":"tag-java","9":"tag-xml"},"_links":{"self":[{"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/posts\/12502","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/users\/54"}],"replies":[{"embeddable":true,"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/comments?post=12502"}],"version-history":[{"count":11,"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/posts\/12502\/revisions"}],"predecessor-version":[{"id":14725,"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/posts\/12502\/revisions\/14725"}],"wp:attachment":[{"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/media?parent=12502"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/categories?post=12502"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/touk.pl\/blog\/wp-json\/wp\/v2\/tags?post=12502"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}