Juan Diego Juan Diego - 23 days ago 5
Java Question

Parsing dates with SAX Java

I am having trouble parsing dates of a gpx file with SAX. Somehow it fails to get the

<time>
tag of some nodes correctly. Most of the nodes are ok, and it doesn't seem have any problem with other tags.

I am testing on different gpx files and it always fails on the same nodes on the same files and there are no special characters or anything. And it is cyclical.

enter image description here

I am printing the node number next to the error. And the 3th column is the difference between the current error and the last error

enter image description here

It usually starts around the 800 to 1000 the first error. As you can see the dates are not being picked properly, for some reason they are trimmed.

This is my handler

package ec.com.mapachedev.webmapper.gpx;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.List;

import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

public class SAXFileHandler extends DefaultHandler {
private String reading;
private List<SAXTrack> tracks;
private List<SAXWayPoint> waypoints;
private List<SAXTrackPoint> trackpoints;
private SAXTrack track;
private SAXTrackPoint trackPoint;
private SAXWayPoint wayPoint;
private LocalDateTime fechaExtraido;
private LocalDateTime fechaIni;
private LocalDateTime fechaFin;
private DateTimeFormatter parser = DateTimeFormatter
.ofPattern("[yyyy-MM-dd'T'HH:mm:ss.SSS'Z']" + "[yyyy-MM-dd'T'HH:mm:ss'Z']");
private boolean isWaypoint = false;
private boolean isTrackPoint = false;
private int cont = 0;

public SAXFileHandler() {
super();
}

@Override
public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {
try {
if (qName.equals("trkpt")) {
trackPoint = new SAXTrackPoint();
isWaypoint = false;
isTrackPoint = true;
try {
trackPoint.setLat(Double.parseDouble(attributes.getValue("lat")));
trackPoint.setLon(Double.parseDouble(attributes.getValue("lon")));
} catch (Exception e) {
System.out.println("Error " + e.getMessage());
}

} /*
* else if (qName.equals("trkseg")) {
*
* }
*/else if (qName.equals("trk")) {
track = new SAXTrack();
isWaypoint = false;
isTrackPoint = false;
} else if (qName.equals("wpt")) {
isWaypoint = true;
isTrackPoint = false;
wayPoint = new SAXWayPoint();
try {
wayPoint.setLat(Double.parseDouble(attributes.getValue("lat")));
wayPoint.setLon(Double.parseDouble(attributes.getValue("lon")));
} catch (Exception e) {
System.out.println("Error " + e.getMessage());
}
} else if (qName.equals("gpx")) {
tracks = new ArrayList<SAXTrack>();
waypoints = new ArrayList<SAXWayPoint>();

isWaypoint = false;
isTrackPoint = false;
}
} finally {
// no matter the node, we empty the StringBuilder accumulator when
// we start
// a new node.
reading=null;
}
}

@Override
public void endElement(String uri, String localName, String qName) throws SAXException {

if (qName.equals("trkpt")) {
track.getPuntos().add(trackPoint);
} else if (qName.equals("speed")) {
try {
trackPoint.setVelocidad(Double.parseDouble(reading));
} catch (Exception e) {
System.out.println("Error " + e.getMessage());
}
} else if (qName.equals("time") && isTrackPoint) {
System.out.println("Time Track " + reading + " "
+ cont++);/*
* try { cont++;
* //System.out.println("Time Track " + reading
* + " "+cont++);
* trackPoint.setFecha(LocalDateTime.parse(
* reading, parser)); // Siempre guardamos la
* ultima fecha y si es la primer vez que //
* grabamos fechas tambien ponemos fechaInicial
* fechaFin = trackPoint.getFecha(); if
* (fechaIni == null) fechaIni =
* trackPoint.getFecha(); } catch (Exception e)
* { System.out.println("Error " +
* e.getMessage()+" " +cont); }
*/
} else if (qName.equals("ele") && isTrackPoint) {
try {
trackPoint.setEle(Double.parseDouble(reading));
} catch (Exception e) {
System.out.println("Error " + e.getMessage());
}
} else if (qName.equals("name") && isTrackPoint) {
// System.out.println("Nombre: "+reading);
trackPoint.setNombre(reading);
} else if (qName.equals("desc") && !isWaypoint && !isTrackPoint) {
track.setDesc(reading);
} else if (qName.equals("name") && !isWaypoint && !isTrackPoint) {
track.setName(reading);
} else if (qName.equals("desc") && isWaypoint) {
wayPoint.setDesc(reading);
} else if (qName.equals("cmt") && isWaypoint) {
wayPoint.setCmt(reading);
} else if (qName.equals("name") && isWaypoint) {
wayPoint.setCmt(reading);
} else if (qName.equals("time") && isWaypoint) {
System.out.println("Time WP " + reading);
wayPoint.setFecha(LocalDateTime.parse(reading, parser));
} else if (qName.equals("ele") && isWaypoint) {
try {
wayPoint.setEle(Double.parseDouble(reading));
} catch (Exception e) {
System.out.println("Error " + e.getMessage());
}
} else if (qName.equals("trk")) {
tracks.add(track);
} else if (qName.equals("time") && tracks.size() == 0) {
System.out.println("Time GPX " + reading);
fechaExtraido = LocalDateTime.parse(reading, parser);
}

}

@Override
public void characters(char[] ch, int start, int length) throws SAXException {
reading = new String(ch, start, length);
}

public List<SAXTrack> getTracks() {
return tracks;
}

public void setTracks(List<SAXTrack> tracks) {
this.tracks = tracks;
}

public List<SAXWayPoint> getWaypoints() {
return waypoints;
}

public void setWaypoints(List<SAXWayPoint> waypoints) {
this.waypoints = waypoints;
}

public List<SAXTrackPoint> getTrackpoints() {
return trackpoints;
}

public void setTrackpoints(List<SAXTrackPoint> trackpoints) {
this.trackpoints = trackpoints;
}

public SAXTrack getTrack() {
return track;
}

public void setTrack(SAXTrack track) {
this.track = track;
}

public SAXTrackPoint getTrackPoint() {
return trackPoint;
}

public void setTrackPoint(SAXTrackPoint trackPoint) {
this.trackPoint = trackPoint;
}

public SAXWayPoint getWayPoint() {
return wayPoint;
}

public void setWayPoint(SAXWayPoint wayPoint) {
this.wayPoint = wayPoint;
}

public LocalDateTime getFechaExtraido() {
return fechaExtraido;
}

public void setFechaExtraido(LocalDateTime fechaExtraido) {
this.fechaExtraido = fechaExtraido;
}

public LocalDateTime getFechaIni() {
return fechaIni;
}

public void setFechaIni(LocalDateTime fechaIni) {
this.fechaIni = fechaIni;
}

public LocalDateTime getFechaFin() {
return fechaFin;
}

public void setFechaFin(LocalDateTime fechaFin) {
this.fechaFin = fechaFin;
}

public DateTimeFormatter getParser() {
return parser;
}

public void setParser(DateTimeFormatter parser) {
this.parser = parser;
}

}

Answer

I changed my to code to use this. https://mappingdev.wordpress.com/2011/09/22/parsing-gpxxml-files-with-sax/

Just changed localName to name in the code and everything worked