Reformat whole codebase using Android Studio
This commit is contained in:
parent
d5322667d5
commit
c15913c1ab
161 changed files with 15124 additions and 18537 deletions
|
|
@ -3,6 +3,7 @@ package btools.server.request;
|
|||
import btools.router.RoutingContext;
|
||||
import btools.router.RoutingEngine;
|
||||
import btools.server.ServiceContext;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.BufferedWriter;
|
||||
import java.io.File;
|
||||
|
|
@ -15,8 +16,7 @@ import java.util.Map;
|
|||
/**
|
||||
* Custom profile uploads
|
||||
*/
|
||||
public class ProfileUploadHandler
|
||||
{
|
||||
public class ProfileUploadHandler {
|
||||
// maximum number of characters (file size limit for custom profiles)
|
||||
private static final int MAX_LENGTH = 100000;
|
||||
|
||||
|
|
@ -24,29 +24,25 @@ public class ProfileUploadHandler
|
|||
public static final String CUSTOM_PREFIX = "custom_";
|
||||
public static final String SHARED_PREFIX = "shared_";
|
||||
|
||||
private ServiceContext serviceContext;
|
||||
|
||||
public ProfileUploadHandler( ServiceContext serviceContext)
|
||||
{
|
||||
this.serviceContext = serviceContext;
|
||||
}
|
||||
private ServiceContext serviceContext;
|
||||
|
||||
public void handlePostRequest(String profileId, BufferedReader br, BufferedWriter response) throws IOException
|
||||
{
|
||||
public ProfileUploadHandler(ServiceContext serviceContext) {
|
||||
this.serviceContext = serviceContext;
|
||||
}
|
||||
|
||||
public void handlePostRequest(String profileId, BufferedReader br, BufferedWriter response) throws IOException {
|
||||
BufferedWriter fileWriter = null;
|
||||
|
||||
try
|
||||
{
|
||||
try {
|
||||
String id;
|
||||
if ( profileId != null )
|
||||
{
|
||||
if (profileId != null) {
|
||||
// update existing file when id appended
|
||||
id = profileId.substring( ProfileUploadHandler.CUSTOM_PREFIX.length() );
|
||||
id = profileId.substring(ProfileUploadHandler.CUSTOM_PREFIX.length());
|
||||
} else {
|
||||
id = "" + System.currentTimeMillis();
|
||||
}
|
||||
File file = new File( getOrCreateCustomProfileDir(), id + ".brf" );
|
||||
fileWriter = new BufferedWriter(new OutputStreamWriter(new FileOutputStream( file ) ) );
|
||||
File file = new File(getOrCreateCustomProfileDir(), id + ".brf");
|
||||
fileWriter = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(file)));
|
||||
//StringWriter sw = new StringWriter(); bw = new BufferedWriter(sw);
|
||||
|
||||
// only profile text as content
|
||||
|
|
@ -56,57 +52,56 @@ public class ProfileUploadHandler
|
|||
//System.out.println("data: |" + sw.toString() + "|");
|
||||
|
||||
Map<String, String> responseData = new HashMap<String, String>();
|
||||
responseData.put( "profileid", CUSTOM_PREFIX + id );
|
||||
responseData.put("profileid", CUSTOM_PREFIX + id);
|
||||
|
||||
validateProfile( id, responseData );
|
||||
validateProfile(id, responseData);
|
||||
|
||||
response.write( toJSON( responseData ) );
|
||||
}
|
||||
finally
|
||||
{
|
||||
if ( fileWriter != null ) try { fileWriter.close(); } catch( Exception e ) {}
|
||||
response.write(toJSON(responseData));
|
||||
} finally {
|
||||
if (fileWriter != null) try {
|
||||
fileWriter.close();
|
||||
} catch (Exception e) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private File getOrCreateCustomProfileDir()
|
||||
{
|
||||
private File getOrCreateCustomProfileDir() {
|
||||
// workaround: customProfileDir relative to profileDir, because RoutingEngine doesn't know custom profiles
|
||||
File customProfileDir = new File(serviceContext.profileDir, serviceContext.customProfileDir);
|
||||
if (!customProfileDir.exists())
|
||||
{
|
||||
if (!customProfileDir.exists()) {
|
||||
customProfileDir.mkdir();
|
||||
}
|
||||
return customProfileDir;
|
||||
}
|
||||
|
||||
// reads HTTP POST content from input into output stream/writer
|
||||
private static void readPostData( BufferedReader ir, BufferedWriter bw, String id ) throws IOException
|
||||
{
|
||||
private static void readPostData(BufferedReader ir, BufferedWriter bw, String id) throws IOException {
|
||||
// Content-Type: text/plain;charset=UTF-8
|
||||
|
||||
int numChars = 0;
|
||||
|
||||
// Content-Length header is in bytes (!= characters for UTF8),
|
||||
// but Reader reads characters, so don't know number of characters to read
|
||||
for(;;)
|
||||
{
|
||||
for (; ; ) {
|
||||
// read will block when false, occurs at end of stream rather than -1
|
||||
if (!ir.ready()) {
|
||||
try { Thread.sleep(1000); } catch( Exception e ) {}
|
||||
if ( !ir.ready() ) break;
|
||||
try {
|
||||
Thread.sleep(1000);
|
||||
} catch (Exception e) {
|
||||
}
|
||||
if (!ir.ready()) break;
|
||||
}
|
||||
int c = ir.read();
|
||||
if ( c == -1) break;
|
||||
bw.write( c );
|
||||
|
||||
if (c == -1) break;
|
||||
bw.write(c);
|
||||
|
||||
numChars++;
|
||||
if (numChars > MAX_LENGTH)
|
||||
throw new IOException("Maximum number of characters exceeded (" + MAX_LENGTH + ", " + id + ")");
|
||||
}
|
||||
}
|
||||
|
||||
private String toJSON( Map<String, String> data )
|
||||
{
|
||||
private String toJSON(Map<String, String> data) {
|
||||
boolean first = true;
|
||||
StringBuilder sb = new StringBuilder();
|
||||
sb.append("{");
|
||||
|
|
@ -123,29 +118,22 @@ public class ProfileUploadHandler
|
|||
return sb.toString();
|
||||
}
|
||||
|
||||
public void validateProfile(String id, Map<String, String> responseData)
|
||||
{
|
||||
public void validateProfile(String id, Map<String, String> responseData) {
|
||||
// validate by initializing RoutingEngine, where parsing is done, and catching exceptions
|
||||
// see https://github.com/abrensch/brouter/issues/14
|
||||
try
|
||||
{
|
||||
try {
|
||||
RoutingContext rc = new RoutingContext();
|
||||
rc.localFunction = serviceContext.customProfileDir + "/" + id;
|
||||
new RoutingEngine( null, null, null, null, rc );
|
||||
}
|
||||
catch ( Exception e )
|
||||
{
|
||||
rc.localFunction = serviceContext.customProfileDir + "/" + id;
|
||||
new RoutingEngine(null, null, null, null, rc);
|
||||
} catch (Exception e) {
|
||||
String msg = e.getMessage();
|
||||
if ( msg == null )
|
||||
{
|
||||
if (msg == null) {
|
||||
msg = "";
|
||||
}
|
||||
else if ( msg.indexOf( "does not contain expressions for context" ) >= 0 )
|
||||
{
|
||||
} else if (msg.indexOf("does not contain expressions for context") >= 0) {
|
||||
// remove absolute path in this specific exception, useful for server, but don't disclose to client
|
||||
msg = msg.substring( msg.indexOf( "does not contain expressions for context" ) );
|
||||
msg = msg.substring(msg.indexOf("does not contain expressions for context"));
|
||||
}
|
||||
responseData.put( "error", "Profile error: " + msg );
|
||||
responseData.put("error", "Profile error: " + msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,31 +1,29 @@
|
|||
package btools.server.request;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
|
||||
import btools.router.OsmNodeNamed;
|
||||
import btools.router.OsmTrack;
|
||||
import btools.router.RoutingContext;
|
||||
import btools.server.ServiceContext;
|
||||
|
||||
public abstract class RequestHandler
|
||||
{
|
||||
protected ServiceContext serviceContext;
|
||||
protected HashMap<String,String> params;
|
||||
|
||||
public RequestHandler( ServiceContext serviceContext, HashMap<String,String> params )
|
||||
{
|
||||
this.serviceContext = serviceContext;
|
||||
this.params = params;
|
||||
}
|
||||
|
||||
public abstract RoutingContext readRoutingContext();
|
||||
|
||||
public abstract List<OsmNodeNamed> readWayPointList();
|
||||
|
||||
public abstract String formatTrack(OsmTrack track);
|
||||
|
||||
public abstract String getMimeType();
|
||||
|
||||
public abstract String getFileName();
|
||||
}
|
||||
package btools.server.request;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
|
||||
import btools.router.OsmNodeNamed;
|
||||
import btools.router.OsmTrack;
|
||||
import btools.router.RoutingContext;
|
||||
import btools.server.ServiceContext;
|
||||
|
||||
public abstract class RequestHandler {
|
||||
protected ServiceContext serviceContext;
|
||||
protected HashMap<String, String> params;
|
||||
|
||||
public RequestHandler(ServiceContext serviceContext, HashMap<String, String> params) {
|
||||
this.serviceContext = serviceContext;
|
||||
this.params = params;
|
||||
}
|
||||
|
||||
public abstract RoutingContext readRoutingContext();
|
||||
|
||||
public abstract List<OsmNodeNamed> readWayPointList();
|
||||
|
||||
public abstract String formatTrack(OsmTrack track);
|
||||
|
||||
public abstract String getMimeType();
|
||||
|
||||
public abstract String getFileName();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,343 +1,293 @@
|
|||
package btools.server.request;
|
||||
|
||||
import btools.mapaccess.OsmNode;
|
||||
import btools.router.OsmNodeNamed;
|
||||
import btools.router.OsmNogoPolygon;
|
||||
import btools.router.OsmTrack;
|
||||
import btools.router.RoutingContext;
|
||||
import btools.server.ServiceContext;
|
||||
import java.io.BufferedWriter;
|
||||
import java.io.File;
|
||||
import java.io.StringWriter;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* URL query parameter handler for web and standalone server. Supports all
|
||||
* BRouter features without restrictions.
|
||||
*
|
||||
* Parameters:
|
||||
*
|
||||
* lonlats = lon,lat|... (unlimited list of lon,lat waypoints separated by |)
|
||||
* nogos = lon,lat,radius|... (optional, radius in meters)
|
||||
* profile = profile file name without .brf
|
||||
* alternativeidx = [0|1|2|3] (optional, default 0)
|
||||
* format = [kml|gpx|geojson] (optional, default gpx)
|
||||
* trackname = name used for filename and format specific trackname (optional, default brouter)
|
||||
* exportWaypoints = 1 to export them (optional, default is no export)
|
||||
* pois = lon,lat,name|... (optional)
|
||||
*
|
||||
* Example URLs:
|
||||
* {@code http://localhost:17777/brouter?lonlats=8.799297,49.565883|8.811764,49.563606&nogos=&profile=trekking&alternativeidx=0&format=gpx}
|
||||
* {@code http://localhost:17777/brouter?lonlats=1.1,1.2|2.1,2.2|3.1,3.2|4.1,4.2&nogos=-1.1,-1.2,1|-2.1,-2.2,2&profile=shortest&alternativeidx=1&format=kml&trackname=Ride&pois=1.1,2.1,Barner Bar}
|
||||
*
|
||||
*/
|
||||
public class ServerHandler extends RequestHandler {
|
||||
|
||||
private RoutingContext rc;
|
||||
|
||||
public ServerHandler( ServiceContext serviceContext, HashMap<String, String> params )
|
||||
{
|
||||
super( serviceContext, params );
|
||||
}
|
||||
|
||||
@Override
|
||||
public RoutingContext readRoutingContext()
|
||||
{
|
||||
rc = new RoutingContext();
|
||||
rc.memoryclass = 128;
|
||||
|
||||
String profile = params.get( "profile" );
|
||||
// when custom profile replace prefix with directory path
|
||||
if ( profile.startsWith( ProfileUploadHandler.CUSTOM_PREFIX ) )
|
||||
{
|
||||
String customProfile = profile.substring( ProfileUploadHandler.CUSTOM_PREFIX.length() );
|
||||
profile = new File( serviceContext.customProfileDir, customProfile ).getPath();
|
||||
}
|
||||
else if ( profile.startsWith( ProfileUploadHandler.SHARED_PREFIX ) )
|
||||
{
|
||||
String customProfile = profile.substring( ProfileUploadHandler.SHARED_PREFIX.length() );
|
||||
profile = new File( serviceContext.sharedProfileDir, customProfile ).getPath();
|
||||
}
|
||||
rc.localFunction = profile;
|
||||
|
||||
rc.setAlternativeIdx(Integer.parseInt(params.get( "alternativeidx" )));
|
||||
|
||||
List<OsmNodeNamed> poisList = readPoisList();
|
||||
rc.poipoints = poisList;
|
||||
|
||||
List<OsmNodeNamed> nogoList = readNogoList();
|
||||
List<OsmNodeNamed> nogoPolygonsList = readNogoPolygons();
|
||||
|
||||
if ( nogoList != null )
|
||||
{
|
||||
RoutingContext.prepareNogoPoints( nogoList );
|
||||
rc.nogopoints = nogoList;
|
||||
}
|
||||
|
||||
if (rc.nogopoints == null)
|
||||
{
|
||||
rc.nogopoints = nogoPolygonsList;
|
||||
}
|
||||
else if ( nogoPolygonsList != null )
|
||||
{
|
||||
rc.nogopoints.addAll(nogoPolygonsList);
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<OsmNodeNamed> readWayPointList()
|
||||
{
|
||||
// lon,lat|...
|
||||
String lonLats = params.get( "lonlats" );
|
||||
if (lonLats == null) throw new IllegalArgumentException( "lonlats parameter not set" );
|
||||
|
||||
String[] coords = lonLats.split("\\|");
|
||||
if (coords.length < 2)
|
||||
throw new IllegalArgumentException( "we need two lat/lon points at least!" );
|
||||
|
||||
List<OsmNodeNamed> wplist = new ArrayList<OsmNodeNamed>();
|
||||
for (int i = 0; i < coords.length; i++)
|
||||
{
|
||||
String[] lonLat = coords[i].split(",");
|
||||
if (lonLat.length < 2)
|
||||
throw new IllegalArgumentException( "we need two lat/lon points at least!" );
|
||||
wplist.add( readPosition( lonLat[0], lonLat[1], "via" + i ) );
|
||||
}
|
||||
|
||||
wplist.get(0).name = "from";
|
||||
wplist.get(wplist.size()-1).name = "to";
|
||||
|
||||
return wplist;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String formatTrack(OsmTrack track)
|
||||
{
|
||||
String result;
|
||||
// optional, may be null
|
||||
String format = params.get( "format" );
|
||||
String trackName = getTrackName();
|
||||
if (trackName != null) {
|
||||
track.name = trackName;
|
||||
}
|
||||
String exportWaypointsStr = params.get( "exportWaypoints" );
|
||||
if (exportWaypointsStr != null && Integer.parseInt(exportWaypointsStr) != 0) {
|
||||
track.exportWaypoints = true;
|
||||
}
|
||||
|
||||
if (format == null || "gpx".equals(format))
|
||||
{
|
||||
result = track.formatAsGpx();
|
||||
}
|
||||
else if ("kml".equals(format))
|
||||
{
|
||||
result = track.formatAsKml();
|
||||
}
|
||||
else if ("geojson".equals(format))
|
||||
{
|
||||
result = track.formatAsGeoJson();
|
||||
}
|
||||
else if ("csv".equals(format))
|
||||
{
|
||||
try
|
||||
{
|
||||
StringWriter sw = new StringWriter();
|
||||
BufferedWriter bw = new BufferedWriter(sw);
|
||||
track.writeMessages( bw, rc );
|
||||
return sw.toString();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return "Error: " + ex.getMessage();
|
||||
}
|
||||
}
|
||||
else {
|
||||
System.out.println("unknown track format '" + format + "', using default");
|
||||
result = track.formatAsGpx();
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMimeType()
|
||||
{
|
||||
// default
|
||||
String result = "text/plain";
|
||||
|
||||
// optional, may be null
|
||||
String format = params.get( "format" );
|
||||
if ( format != null )
|
||||
{
|
||||
if ( "gpx".equals( format ) )
|
||||
{
|
||||
result = "application/gpx+xml";
|
||||
}
|
||||
else if ( "kml".equals( format ) )
|
||||
{
|
||||
result = "application/vnd.google-earth.kml+xml";
|
||||
}
|
||||
else if ( "geojson".equals( format ) )
|
||||
{
|
||||
result = "application/vnd.geo+json";
|
||||
}
|
||||
else if ( "csv".equals( format ) )
|
||||
{
|
||||
result = "text/tab-separated-values";
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getFileName()
|
||||
{
|
||||
String fileName = null;
|
||||
String format = params.get( "format" );
|
||||
String trackName = getTrackName();
|
||||
|
||||
if ( format != null )
|
||||
{
|
||||
fileName = ( trackName == null ? "brouter" : trackName ) + "." + format;
|
||||
}
|
||||
|
||||
return fileName;
|
||||
}
|
||||
|
||||
private String getTrackName()
|
||||
{
|
||||
return params.get( "trackname" ) == null ? null : params.get( "trackname" ).replaceAll("[^a-zA-Z0-9 \\._\\-]+", "");
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readPosition( String vlon, String vlat, String name )
|
||||
{
|
||||
if ( vlon == null ) throw new IllegalArgumentException( "lon " + name + " not found in input" );
|
||||
if ( vlat == null ) throw new IllegalArgumentException( "lat " + name + " not found in input" );
|
||||
|
||||
return readPosition(Double.parseDouble( vlon ), Double.parseDouble( vlat ), name);
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readPosition( double lon, double lat, String name )
|
||||
{
|
||||
OsmNodeNamed n = new OsmNodeNamed();
|
||||
n.name = name;
|
||||
n.ilon = (int)( ( lon + 180. ) *1000000. + 0.5);
|
||||
n.ilat = (int)( ( lat + 90. ) *1000000. + 0.5);
|
||||
return n;
|
||||
}
|
||||
|
||||
private List<OsmNodeNamed> readPoisList()
|
||||
{
|
||||
// lon,lat,name|...
|
||||
String pois = params.get( "pois" );
|
||||
if ( pois == null ) return null;
|
||||
|
||||
String[] lonLatNameList = pois.split("\\|");
|
||||
|
||||
List<OsmNodeNamed> poisList = new ArrayList<OsmNodeNamed>();
|
||||
for (int i = 0; i < lonLatNameList.length; i++)
|
||||
{
|
||||
String[] lonLatName = lonLatNameList[i].split(",");
|
||||
|
||||
if (lonLatName.length != 3)
|
||||
continue;
|
||||
|
||||
OsmNodeNamed n = new OsmNodeNamed();
|
||||
n.ilon = (int)( ( Double.parseDouble(lonLatName[0]) + 180. ) *1000000. + 0.5);
|
||||
n.ilat = (int)( ( Double.parseDouble(lonLatName[1]) + 90. ) *1000000. + 0.5);
|
||||
n.name = lonLatName[2];
|
||||
poisList.add(n);
|
||||
}
|
||||
|
||||
return poisList;
|
||||
}
|
||||
|
||||
private List<OsmNodeNamed> readNogoList()
|
||||
{
|
||||
// lon,lat,radius|...
|
||||
String nogos = params.get( "nogos" );
|
||||
if ( nogos == null ) return null;
|
||||
|
||||
String[] lonLatRadList = nogos.split("\\|");
|
||||
|
||||
List<OsmNodeNamed> nogoList = new ArrayList<OsmNodeNamed>();
|
||||
for (int i = 0; i < lonLatRadList.length; i++)
|
||||
{
|
||||
String[] lonLatRad = lonLatRadList[i].split(",");
|
||||
String nogoWeight = "NaN";
|
||||
if (lonLatRad.length > 3) {
|
||||
nogoWeight = lonLatRad[3];
|
||||
}
|
||||
nogoList.add(readNogo(lonLatRad[0], lonLatRad[1], lonLatRad[2], nogoWeight));
|
||||
}
|
||||
|
||||
return nogoList;
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readNogo( String lon, String lat, String radius, String nogoWeight )
|
||||
{
|
||||
double weight = "undefined".equals( nogoWeight ) ? Double.NaN : Double.parseDouble( nogoWeight );
|
||||
return readNogo(Double.parseDouble( lon ), Double.parseDouble( lat ), Integer.parseInt( radius ), weight );
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readNogo( double lon, double lat, int radius, double nogoWeight )
|
||||
{
|
||||
OsmNodeNamed n = new OsmNodeNamed();
|
||||
n.name = "nogo" + radius;
|
||||
n.ilon = (int)( ( lon + 180. ) *1000000. + 0.5);
|
||||
n.ilat = (int)( ( lat + 90. ) *1000000. + 0.5);
|
||||
n.isNogo = true;
|
||||
n.nogoWeight = nogoWeight;
|
||||
return n;
|
||||
}
|
||||
|
||||
private List<OsmNodeNamed> readNogoPolygons()
|
||||
{
|
||||
List<OsmNodeNamed> result = new ArrayList<OsmNodeNamed>();
|
||||
parseNogoPolygons( params.get("polylines"), result, false );
|
||||
parseNogoPolygons( params.get("polygons"), result, true );
|
||||
return result.size() > 0 ? result : null;
|
||||
}
|
||||
|
||||
private static void parseNogoPolygons(String polygons, List<OsmNodeNamed> result, boolean closed )
|
||||
{
|
||||
if ( polygons != null )
|
||||
{
|
||||
String[] polygonList = polygons.split("\\|");
|
||||
for (int i = 0; i < polygonList.length; i++)
|
||||
{
|
||||
String[] lonLatList = polygonList[i].split(",");
|
||||
if ( lonLatList.length > 1 )
|
||||
{
|
||||
OsmNogoPolygon polygon = new OsmNogoPolygon(closed);
|
||||
int j;
|
||||
for (j = 0; j < 2 * (lonLatList.length / 2) - 1;)
|
||||
{
|
||||
String slon = lonLatList[j++];
|
||||
String slat = lonLatList[j++];
|
||||
int lon = (int)( ( Double.parseDouble(slon) + 180. ) *1000000. + 0.5);
|
||||
int lat = (int)( ( Double.parseDouble(slat) + 90. ) *1000000. + 0.5);
|
||||
polygon.addVertex(lon, lat);
|
||||
}
|
||||
|
||||
String nogoWeight = "NaN";
|
||||
if (j < lonLatList.length) {
|
||||
nogoWeight = lonLatList[j];
|
||||
}
|
||||
polygon.nogoWeight = Double.parseDouble( nogoWeight );
|
||||
|
||||
if ( polygon.points.size() > 0 )
|
||||
{
|
||||
polygon.calcBoundingCircle();
|
||||
result.add(polygon);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
package btools.server.request;
|
||||
|
||||
import btools.mapaccess.OsmNode;
|
||||
import btools.router.OsmNodeNamed;
|
||||
import btools.router.OsmNogoPolygon;
|
||||
import btools.router.OsmTrack;
|
||||
import btools.router.RoutingContext;
|
||||
import btools.server.ServiceContext;
|
||||
|
||||
import java.io.BufferedWriter;
|
||||
import java.io.File;
|
||||
import java.io.StringWriter;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* URL query parameter handler for web and standalone server. Supports all
|
||||
* BRouter features without restrictions.
|
||||
* <p>
|
||||
* Parameters:
|
||||
* <p>
|
||||
* lonlats = lon,lat|... (unlimited list of lon,lat waypoints separated by |)
|
||||
* nogos = lon,lat,radius|... (optional, radius in meters)
|
||||
* profile = profile file name without .brf
|
||||
* alternativeidx = [0|1|2|3] (optional, default 0)
|
||||
* format = [kml|gpx|geojson] (optional, default gpx)
|
||||
* trackname = name used for filename and format specific trackname (optional, default brouter)
|
||||
* exportWaypoints = 1 to export them (optional, default is no export)
|
||||
* pois = lon,lat,name|... (optional)
|
||||
* <p>
|
||||
* Example URLs:
|
||||
* {@code http://localhost:17777/brouter?lonlats=8.799297,49.565883|8.811764,49.563606&nogos=&profile=trekking&alternativeidx=0&format=gpx}
|
||||
* {@code http://localhost:17777/brouter?lonlats=1.1,1.2|2.1,2.2|3.1,3.2|4.1,4.2&nogos=-1.1,-1.2,1|-2.1,-2.2,2&profile=shortest&alternativeidx=1&format=kml&trackname=Ride&pois=1.1,2.1,Barner Bar}
|
||||
*/
|
||||
public class ServerHandler extends RequestHandler {
|
||||
|
||||
private RoutingContext rc;
|
||||
|
||||
public ServerHandler(ServiceContext serviceContext, HashMap<String, String> params) {
|
||||
super(serviceContext, params);
|
||||
}
|
||||
|
||||
@Override
|
||||
public RoutingContext readRoutingContext() {
|
||||
rc = new RoutingContext();
|
||||
rc.memoryclass = 128;
|
||||
|
||||
String profile = params.get("profile");
|
||||
// when custom profile replace prefix with directory path
|
||||
if (profile.startsWith(ProfileUploadHandler.CUSTOM_PREFIX)) {
|
||||
String customProfile = profile.substring(ProfileUploadHandler.CUSTOM_PREFIX.length());
|
||||
profile = new File(serviceContext.customProfileDir, customProfile).getPath();
|
||||
} else if (profile.startsWith(ProfileUploadHandler.SHARED_PREFIX)) {
|
||||
String customProfile = profile.substring(ProfileUploadHandler.SHARED_PREFIX.length());
|
||||
profile = new File(serviceContext.sharedProfileDir, customProfile).getPath();
|
||||
}
|
||||
rc.localFunction = profile;
|
||||
|
||||
rc.setAlternativeIdx(Integer.parseInt(params.get("alternativeidx")));
|
||||
|
||||
List<OsmNodeNamed> poisList = readPoisList();
|
||||
rc.poipoints = poisList;
|
||||
|
||||
List<OsmNodeNamed> nogoList = readNogoList();
|
||||
List<OsmNodeNamed> nogoPolygonsList = readNogoPolygons();
|
||||
|
||||
if (nogoList != null) {
|
||||
RoutingContext.prepareNogoPoints(nogoList);
|
||||
rc.nogopoints = nogoList;
|
||||
}
|
||||
|
||||
if (rc.nogopoints == null) {
|
||||
rc.nogopoints = nogoPolygonsList;
|
||||
} else if (nogoPolygonsList != null) {
|
||||
rc.nogopoints.addAll(nogoPolygonsList);
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<OsmNodeNamed> readWayPointList() {
|
||||
// lon,lat|...
|
||||
String lonLats = params.get("lonlats");
|
||||
if (lonLats == null) throw new IllegalArgumentException("lonlats parameter not set");
|
||||
|
||||
String[] coords = lonLats.split("\\|");
|
||||
if (coords.length < 2)
|
||||
throw new IllegalArgumentException("we need two lat/lon points at least!");
|
||||
|
||||
List<OsmNodeNamed> wplist = new ArrayList<OsmNodeNamed>();
|
||||
for (int i = 0; i < coords.length; i++) {
|
||||
String[] lonLat = coords[i].split(",");
|
||||
if (lonLat.length < 2)
|
||||
throw new IllegalArgumentException("we need two lat/lon points at least!");
|
||||
wplist.add(readPosition(lonLat[0], lonLat[1], "via" + i));
|
||||
}
|
||||
|
||||
wplist.get(0).name = "from";
|
||||
wplist.get(wplist.size() - 1).name = "to";
|
||||
|
||||
return wplist;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String formatTrack(OsmTrack track) {
|
||||
String result;
|
||||
// optional, may be null
|
||||
String format = params.get("format");
|
||||
String trackName = getTrackName();
|
||||
if (trackName != null) {
|
||||
track.name = trackName;
|
||||
}
|
||||
String exportWaypointsStr = params.get("exportWaypoints");
|
||||
if (exportWaypointsStr != null && Integer.parseInt(exportWaypointsStr) != 0) {
|
||||
track.exportWaypoints = true;
|
||||
}
|
||||
|
||||
if (format == null || "gpx".equals(format)) {
|
||||
result = track.formatAsGpx();
|
||||
} else if ("kml".equals(format)) {
|
||||
result = track.formatAsKml();
|
||||
} else if ("geojson".equals(format)) {
|
||||
result = track.formatAsGeoJson();
|
||||
} else if ("csv".equals(format)) {
|
||||
try {
|
||||
StringWriter sw = new StringWriter();
|
||||
BufferedWriter bw = new BufferedWriter(sw);
|
||||
track.writeMessages(bw, rc);
|
||||
return sw.toString();
|
||||
} catch (Exception ex) {
|
||||
return "Error: " + ex.getMessage();
|
||||
}
|
||||
} else {
|
||||
System.out.println("unknown track format '" + format + "', using default");
|
||||
result = track.formatAsGpx();
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMimeType() {
|
||||
// default
|
||||
String result = "text/plain";
|
||||
|
||||
// optional, may be null
|
||||
String format = params.get("format");
|
||||
if (format != null) {
|
||||
if ("gpx".equals(format)) {
|
||||
result = "application/gpx+xml";
|
||||
} else if ("kml".equals(format)) {
|
||||
result = "application/vnd.google-earth.kml+xml";
|
||||
} else if ("geojson".equals(format)) {
|
||||
result = "application/vnd.geo+json";
|
||||
} else if ("csv".equals(format)) {
|
||||
result = "text/tab-separated-values";
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getFileName() {
|
||||
String fileName = null;
|
||||
String format = params.get("format");
|
||||
String trackName = getTrackName();
|
||||
|
||||
if (format != null) {
|
||||
fileName = (trackName == null ? "brouter" : trackName) + "." + format;
|
||||
}
|
||||
|
||||
return fileName;
|
||||
}
|
||||
|
||||
private String getTrackName() {
|
||||
return params.get("trackname") == null ? null : params.get("trackname").replaceAll("[^a-zA-Z0-9 \\._\\-]+", "");
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readPosition(String vlon, String vlat, String name) {
|
||||
if (vlon == null) throw new IllegalArgumentException("lon " + name + " not found in input");
|
||||
if (vlat == null) throw new IllegalArgumentException("lat " + name + " not found in input");
|
||||
|
||||
return readPosition(Double.parseDouble(vlon), Double.parseDouble(vlat), name);
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readPosition(double lon, double lat, String name) {
|
||||
OsmNodeNamed n = new OsmNodeNamed();
|
||||
n.name = name;
|
||||
n.ilon = (int) ((lon + 180.) * 1000000. + 0.5);
|
||||
n.ilat = (int) ((lat + 90.) * 1000000. + 0.5);
|
||||
return n;
|
||||
}
|
||||
|
||||
private List<OsmNodeNamed> readPoisList() {
|
||||
// lon,lat,name|...
|
||||
String pois = params.get("pois");
|
||||
if (pois == null) return null;
|
||||
|
||||
String[] lonLatNameList = pois.split("\\|");
|
||||
|
||||
List<OsmNodeNamed> poisList = new ArrayList<OsmNodeNamed>();
|
||||
for (int i = 0; i < lonLatNameList.length; i++) {
|
||||
String[] lonLatName = lonLatNameList[i].split(",");
|
||||
|
||||
if (lonLatName.length != 3)
|
||||
continue;
|
||||
|
||||
OsmNodeNamed n = new OsmNodeNamed();
|
||||
n.ilon = (int) ((Double.parseDouble(lonLatName[0]) + 180.) * 1000000. + 0.5);
|
||||
n.ilat = (int) ((Double.parseDouble(lonLatName[1]) + 90.) * 1000000. + 0.5);
|
||||
n.name = lonLatName[2];
|
||||
poisList.add(n);
|
||||
}
|
||||
|
||||
return poisList;
|
||||
}
|
||||
|
||||
private List<OsmNodeNamed> readNogoList() {
|
||||
// lon,lat,radius|...
|
||||
String nogos = params.get("nogos");
|
||||
if (nogos == null) return null;
|
||||
|
||||
String[] lonLatRadList = nogos.split("\\|");
|
||||
|
||||
List<OsmNodeNamed> nogoList = new ArrayList<OsmNodeNamed>();
|
||||
for (int i = 0; i < lonLatRadList.length; i++) {
|
||||
String[] lonLatRad = lonLatRadList[i].split(",");
|
||||
String nogoWeight = "NaN";
|
||||
if (lonLatRad.length > 3) {
|
||||
nogoWeight = lonLatRad[3];
|
||||
}
|
||||
nogoList.add(readNogo(lonLatRad[0], lonLatRad[1], lonLatRad[2], nogoWeight));
|
||||
}
|
||||
|
||||
return nogoList;
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readNogo(String lon, String lat, String radius, String nogoWeight) {
|
||||
double weight = "undefined".equals(nogoWeight) ? Double.NaN : Double.parseDouble(nogoWeight);
|
||||
return readNogo(Double.parseDouble(lon), Double.parseDouble(lat), Integer.parseInt(radius), weight);
|
||||
}
|
||||
|
||||
private static OsmNodeNamed readNogo(double lon, double lat, int radius, double nogoWeight) {
|
||||
OsmNodeNamed n = new OsmNodeNamed();
|
||||
n.name = "nogo" + radius;
|
||||
n.ilon = (int) ((lon + 180.) * 1000000. + 0.5);
|
||||
n.ilat = (int) ((lat + 90.) * 1000000. + 0.5);
|
||||
n.isNogo = true;
|
||||
n.nogoWeight = nogoWeight;
|
||||
return n;
|
||||
}
|
||||
|
||||
private List<OsmNodeNamed> readNogoPolygons() {
|
||||
List<OsmNodeNamed> result = new ArrayList<OsmNodeNamed>();
|
||||
parseNogoPolygons(params.get("polylines"), result, false);
|
||||
parseNogoPolygons(params.get("polygons"), result, true);
|
||||
return result.size() > 0 ? result : null;
|
||||
}
|
||||
|
||||
private static void parseNogoPolygons(String polygons, List<OsmNodeNamed> result, boolean closed) {
|
||||
if (polygons != null) {
|
||||
String[] polygonList = polygons.split("\\|");
|
||||
for (int i = 0; i < polygonList.length; i++) {
|
||||
String[] lonLatList = polygonList[i].split(",");
|
||||
if (lonLatList.length > 1) {
|
||||
OsmNogoPolygon polygon = new OsmNogoPolygon(closed);
|
||||
int j;
|
||||
for (j = 0; j < 2 * (lonLatList.length / 2) - 1; ) {
|
||||
String slon = lonLatList[j++];
|
||||
String slat = lonLatList[j++];
|
||||
int lon = (int) ((Double.parseDouble(slon) + 180.) * 1000000. + 0.5);
|
||||
int lat = (int) ((Double.parseDouble(slat) + 90.) * 1000000. + 0.5);
|
||||
polygon.addVertex(lon, lat);
|
||||
}
|
||||
|
||||
String nogoWeight = "NaN";
|
||||
if (j < lonLatList.length) {
|
||||
nogoWeight = lonLatList[j];
|
||||
}
|
||||
polygon.nogoWeight = Double.parseDouble(nogoWeight);
|
||||
|
||||
if (polygon.points.size() > 0) {
|
||||
polygon.calcBoundingCircle();
|
||||
result.add(polygon);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue