2

I have a CSV file where in a column there are some KML geometries. These geometries can be points, lines, polygons etc. I would like to validate them and check if they are correctly written.

I'm reading the CSV with Pandas

import pandas as pd

csv = read_csv('file.csv')

#Let's take into account just the first location
coordinates = csv.['location'].loc[0] 

coordinates would be:

<Point><coordinates>2.34880,48.85341</coordinates></Point>

I tried to proceed with fastKML, but it searches for a complete KML file to check and not just the string I got.

So I'm wondering, is there any possibility of validating directly the sting?

2
  • 2
    Perhaps wrap it into a complete KML string for a simple placemark, then parse it with fastkml from_string
    – user2856
    Commented Feb 17, 2022 at 12:14
  • A quick web search returned this Python KML library that claimss to validate KML files. pythonhosted.org/pykml.
    – GBG
    Commented Feb 17, 2022 at 16:54

3 Answers 3

4

Perhaps wrap it into a complete KML string for a simple placemark, then parse it with fastkml from_string:

e.g.

import pandas as pd
csv = read_csv('file.csv')

#Let's take into account just the first location
coordinates = csv.['location'].loc[0] 

kml_template = """
<?xml version="1.0" encoding="UTF-8"?>
<kml xmlns="http://www.opengis.net/kml/2.2">
  <Placemark>
    <name></name>
    <description></description>
    {}
  </Placemark>
</kml>
"""

k = kml.KML()
k.from_string(kml_template.format(coordinates))
0

This is possible with fastkml >= 1.1

>>> from fastkml import Point
>>> p = Point.from_string('<Point><coordinates>2.34880,48.85341</coordinates></Point>')
>>> p
fastkml.geometry.Point(ns='{http://www.opengis.net/kml/2.2}', name_spaces={'kml': '{http://www.opengis.net/kml/2.2}', 'atom': '{http://www.w3.org/2005/Atom}', 'gx': '{http://www.google.com/kml/ext/2.2}'}, id='', target_id='', extrude=None, altitude_mode=None, kml_coordinates=fastkml.geometry.Coordinates(ns='', name_spaces={'kml': '{http://www.opengis.net/kml/2.2}', 'atom': '{http://www.w3.org/2005/Atom}', 'gx': '{http://www.google.com/kml/ext/2.2}'}, coords=[(2.3488, 48.85341)], **{},), **{},)
>>> p.geometry
Point(2.3488, 48.85341)
>>> print(p)
<kml:Point xmlns:kml="http://www.opengis.net/kml/2.2">
  <coordinates>2.3488,48.85341</coordinates>
</kml:Point>

Fastkml 1.0.0 needs the namespace to be declared, e.g:

from fastkml import Point
p='<Point xmlns="http://www.opengis.net/kml/2.2"><coordinates>2.34880,48.85341</coordinates></Point>'
Point.from_string(p)
Point.from_string(p).validate()

or you can wrap it into a Placemark with the namespace:

from fastkml import Placemark
p="<Point><coordinates>2.34880,48.85341</coordinates></Point>"
pm=f'<Placemark xmlns="http://www.opengis.net/kml/2.2">{p}</Placemark>'
Placemark.from_string(pm)
Placemark.from_string(pm).validate()
0

@ehi answered their own question.

With the tip from @user2856 I manage to check the geometry.

kml_start = "<kml xmlns='http://www.opengis.net/kml/2.2'><Placemark><name>Simple placemark</name><description>Test.</description>'"
kml_end = "</Placemark></kml>"
kml_test = kml_start+str(coordinates)+kml_end

try:
    k = kml.KML()
    k.from_string(kml_test)
    print("geometry")
except:
    errors += 1
    print("Error, no Geometry")

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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