3

I have a problem importing an kml 2.1 file generated with geotools 17.1 into qgis 2.8.

Qgis refuses to import, google earth imports it and if I save it in google earth qgis is willing to import it.

ogrinfo says:

 ogrinfo test.kml 
 ERROR 4: ERROR Parseing kml test.kml :Invalid root element
 ERROR 4: ERROR Parseing kml test.kml :Invalid root element

after saving it with google earth:

 ogrinfo test-ge.kml 
 INFO: Open of `test-ge.kml'
       using driver `LIBKML' successful.
 1: test-ge

This is the kml generated by geottols

 <kml:kml xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:kml="http://earth.google.com/kml/2.1">
      <kml:Document id="featureCollection">
          <kml:Placemark id="guuid.27bed6fb-02ba-4536-8710-914fac29e236">
              <kml:name>"Grünliches etwas"</kml:name>
              <kml:description>DE-BB-Onlineeingabe null 2017-06-07
              </kml:description>
              <kml:Point>
                  <kml:coordinates>10.000000001438014,52.99999999818237
                  </kml:coordinates>
              </kml:Point>
          </kml:Placemark>            
      </kml:Document>
  </kml:kml>

This is the kml after saving it in google-eart:

 <?xml version="1.0" encoding="UTF-8"?>
 <kml xmlns="http://www.opengis.net/kml/2.2" xmlns:gx="http://www.google.com/kml/ext/2.2" xmlns:kml="http://www.opengis.net/kml/2.2" xmlns:atom="http://www.w3.org/2005/Atom">
 <Document id="featureCollection">
         <name>test.kml</name>
         <Placemark id="guuid.27bed6fb-02ba-4536-8710-914fac29e236">
                 <name>&quot;Grünliches etwas&quot;</name>
                 <description>DE-BB-Onlineeingabe null 2017-06-07</description>
                 <Point>
                         <coordinates>10.00000000143801,52.99999999818237,0</coordinates>
                 </Point>
         </Placemark>
 </Document>
 </kml> 

If I remove the namespace from the getools variant ogrinfo and qgis excepts it.

Is the namespace really invalid in kml? Or is gdal/orginfo/qgis to strict?

EDIT

here is the code used:

@Override
public void export(Collection<Occurrence> occurrences, OutputStream os)
{
  SimpleFeatureCollection features = createSampleFeatures(occurrences, false);
  Encoder encoder = new Encoder(new KMLConfiguration());
  encoder.setIndenting(true);
  try
  {
 encoder.encode(features, KML.kml, os);
  }
  catch (IOException e)
  {
 String message = "Failure to encode KMLConfiguration.";
 throw new FloradbException(FloradbError.INTERNAL_ERROR, message + e);
  }
}

protected SimpleFeatureCollection createSampleFeatures(
 Collection<Occurrence> occurrences, boolean withLink)
{
  SimpleFeatureTypeBuilder typeBuilder = new SimpleFeatureTypeBuilder();
  typeBuilder.setName("occurrences");
  typeBuilder.add("geometry", Geometry.class, DefaultGeographicCRS.WGS84);
  typeBuilder.add("name", String.class);
  typeBuilder.add("description", Object.class);
  SimpleFeatureType type = typeBuilder.buildFeatureType();

  SimpleFeatureBuilder featureBuilder = new SimpleFeatureBuilder(type);
  List<SimpleFeature> simpleFeatures = new ArrayList<>();
  CoordinateTransformerFactory factory = new CoordinateTransformerFactory();

  Iterator<Occurrence> iterator = occurrences.iterator();
  while (iterator.hasNext())
  {
 Occurrence occurrence = iterator.next();
 String wkt;
 if (occurrence.getSample().getPosition().getWktEpsg() == 4326)
 {
    wkt = occurrence.getSample().getPosition().getWkt();
 }
 else
 {
    CoordinateTransformer transformer = factory
      .getCoordinateTransformer(
        occurrence.getSample().getPosition().getWktEpsg(),
        4326);
    wkt = transformer
      .convert(occurrence.getSample().getPosition().getWkt());
 }

 WKTReader wktReader = new WKTReader();
 try
 {
    Geometry geom = wktReader.read(wkt);
    featureBuilder.add(geom);
 }
 catch (ParseException e)
 {
    String message = "Failure to convert wkt to Geometrie.";
    throw new FloradbException(FloradbError.INTERNAL_ERROR,
      message + e);
 }
 featureBuilder.add(occurrence.getTaxon().getName());
 String link;
 if(withLink)
 {
    link = "<a href=\"http://" + homeUrl + "/#!quellendetails//"
         + occurrence.getSample().getSurvey().getId() + "\">"
         + occurrence.getSample().getSurvey().getTitle() + "</a>";
 }
 else
 {
    link = occurrence.getSample().getSurvey().getTitle();
 }
 featureBuilder
       .add(link + " "
         + StringFormatter.getNullSafeStringRepresentation(
           occurrence.getSample().getSurvey().getAvailability())
         + " " + occurrence.getSample().getDate() + " Fund-UUID: "
         + occurrence.getUuid());
 simpleFeatures.add(featureBuilder
       .buildFeature("uuid." + occurrence.getUuid().toString()));
  }

  return DataUtilities.collection(simpleFeatures);
}
  • What happens if you delete the double quotas around the kml:name in the GeoTools variant? – user30184 Jul 5 '17 at 9:40
  • @user30184 the same error - i've also removed the german umlaut – dve Jul 5 '17 at 9:43
  • can you add the code you used to write it? – Ian Turton Jul 5 '17 at 13:03
  • This is weird as both GDAL/OGR and GoogleEarth are using the same LIbKML (in theory) – Ian Turton Jul 5 '17 at 13:37
  • I can also confirm that the other KML driver can't read files with a kml: namespace either – Ian Turton Jul 5 '17 at 13:39
1

This seems to be a bug in the OGR KML drivers - I've raised a bug.

UPDATE This is fixed in GDAL 2.2.2

In the meantime a temporary work around is to remove the kml: from the output.

SimpleFeatureCollection featureCollection = DataUtilities.collection(list);

Encoder encoder = new Encoder(new KMLConfiguration());
encoder.setIndenting(true);
ByteArrayOutputStream os = new ByteArrayOutputStream();
try {
  encoder.encode(featureCollection, KML.kml, os );
  String out = os.toString().replaceAll("kml:", "");
  System.out.println(out);
} catch (Exception e) {
  // TODO Auto-generated catch block
  e.printStackTrace();
} 

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.