用xstream解析谷歌地理编码

时间:2009-05-25 14:03:38

标签: java geocoding xstream

我正在使用Java和XStream通过http解析谷歌地理编码请求。我的想法是拥有一个带有所有地理编码attr的地址类(即lat / long,city,provice / state等),但是我在使用xstream解析xml时遇到了问题。

Google的回复与此相似:

<?xml version="1.0" encoding="UTF-8" ?>
<kml xmlns="http://earth.google.com/kml/2.0"><Response>
  <name>98 St. Patrick St, Toronto</name>
  <Status>
    <code>200</code>
    <request>geocode</request>
  </Status>
  <Placemark id="p1">
    <address>98 St Patrick St, Toronto, ON, Canada</address>
    <AddressDetails Accuracy="8" xmlns="urn:oasis:names:tc:ciq:xsdschema:xAL:2.0"> <Country><CountryNameCode>CA</CountryNameCode><CountryName>Canada</CountryName><AdministrativeArea><AdministrativeAreaName>ON</AdministrativeAreaName><Locality><LocalityName>Toronto</LocalityName><Thoroughfare><ThoroughfareName>98 St Patrick St</ThoroughfareName></Thoroughfare><PostalCode><PostalCodeNumber>M5T</PostalCodeNumber></PostalCode></Locality></AdministrativeArea></Country></AddressDetails>
    <ExtendedData>
      <LatLonBox north="43.6560378" south="43.6497426" east="-79.3864912" west="-79.3927864" />
    </ExtendedData>
    <Point><coordinates>-79.3896388,43.6528902,0</coordinates></Point>
  </Placemark>
</Response></kml>

这不会很好地显示,但代码的内容在AddressDetails标记中。

无论如何,我是Java和XStream的新手,所以API术语对我来说有点混乱。我只需要能够编写一些映射器,将所有这些标签(即CountryName)映射到我的Address对象中的属性,(即。address.country = blah)地址对象将非常简单,主要是国家的字符串名称等,并为lat / long浮动。

文档和示例只显示直接映射,其中每个xml标记直接映射到对象的同名属性。然而,在我的情况下,标签的名称与对象attr的不同。我正在寻找正确方向的快速点。

5 个答案:

答案 0 :(得分:2)

我在几个项目中使用过XStream。不幸的是,你的问题并不是XStream旨在解决的问题。您可以使用其转换器机制来实现您的直接目标,但您将遇到限制。简而言之,XStream不是为了将树结构A转换为树结构B而设计的 - 它的目的是将Java域模型转换为一些合理的XML。当您不太关心所生成的XML的细节时,XStream是一个很好的工具。如果您更关心XML而不是Java对象,请查看XMLBeans - Java很难看,但它非常符合模式。

对于您的项目,我将通过XML bean运行Google XML架构,生成一些Java,这将为您提供一种更有文化的手动编码转换器的方法。您可以使用原始DOM树,但是您的代码类似于myAddress.setStreet(root.getFirstChild()。getAttribute(“addr1”)))。对于XML bean,你会说像myAddress.setStreet(googleResult.getAddress()。getStreetName();

我忽略了JAXB,因为它试图将接口与实现分开会增加不必要的复杂性。 Castor可能也是一个很好的考虑因素,但我多年没有使用它了。

简而言之,没有很多好的Object-to-Object或XML-to-Object转换器可以很好地处理结构转换。在那些我已经看过尝试声明性解决方案的人中,所有这些解决方案看起来都比使用XStream / XmlBeans以及手工编码的结构转换要复杂得多(并且不再可维护)。

答案 1 :(得分:0)

是否可以定义一个专门用于处理XStream映射的单独类?然后,您可以通过从另一个对象中查询值来简单地填充AddressDetails对象。

答案 2 :(得分:0)

我最终只是使用xpath并手动填充我自己的地址对象。似乎工作正常。

答案 3 :(得分:0)

你试过json格式吗?它应该是相同的,但你需要设置一个com.thoughtworks.xstream.io.json.JettisonMappedXmlDriver作为XStream的驱动程序

答案 4 :(得分:0)

您可以使用EclipseLink JAXB (MOXy)执行此操作:

package com.example;

import javax.xml.bind.annotation.XmlRootElement;
import org.eclipse.persistence.oxm.annotations.XmlPath;

@XmlRootElement(name="kml")
public class Address {

    private String country;

    @XmlPath("Response/Placemark/ns:AddressDetails/ns:Country/ns:CountryName/text()")
    public String getCountry() {
        return country;
    }

    public void setCountry(String country) {
        this.country = country;
    }

}

@javax.xml.bind.annotation.XmlSchema( 
   namespace = "http://earth.google.com/kml/2.0",
   xmlns = { 
      @javax.xml.bind.annotation.XmlNs(
         prefix = "ns", namespaceURI ="urn:oasis:names:tc:ciq:xsdschema:xAL:2.0")
   },
   elementFormDefault = javax.xml.bind.annotation.XmlNsForm.QUALIFIED) 
package com.example; 

这里有一个完整的例子: