-1

I was tried to get OSM data from my local overpass API. There are four steps to get OSM data.

  1. run the binary file /srv/osm3s/bin/osm3s_query
  2. once the osm3s_query is running, you'll see this messageencoding remark: Please enter your query and terminate it with CTRL+D.
  3. input your query <query type="node"><bbox-query n="51.0" s="50.9" w="6.9" e="7.0"/><has-kv k="amenity" v="pub"/></query><print/>
  4. press ctrl+D and get the OSM results

my code as below:

try
    {            
        Runtime rt = Runtime.getRuntime();
        Process proc = rt.exec("/srv/osm3s/bin/osm3s_query");
        InputStream stderr = proc.getErrorStream();
        InputStreamReader isr = new InputStreamReader(stderr);
        BufferedReader br = new BufferedReader(isr);
        String line = null;
        while ( (line = br.readLine()) != null)
            System.out.println(line);
        int exitVal = proc.waitFor();
        System.out.println("Process exitValue: " + exitVal);
    } catch (Throwable t)
      {
        t.printStackTrace();
      }

The process will hang on step 2 after shown the message encoding remark: Please enter your query and terminate it with CTRL+D.. I have no idea how to give the process the query string.

Anybody has some idea?

Kohei TAMURA
  • 4,970
  • 7
  • 25
  • 49
user2775128
  • 309
  • 1
  • 4
  • 14

2 Answers2

0
OutputStreamWriter output = proc.getOutputStream();
output.write(yourQuery);
output.write(4); // that's ctrl-d
output.flush();
jingx
  • 3,698
  • 3
  • 24
  • 40
0

Firstly -- this is a pretty fragile way to interact with the Overpass API. Since Overpass is an XML-over-HTTP API, and Java has lots of XML and HTTP libraries, there are plenty of ways to do it in native Java. OpenStreetMap provides examples - for example http://wiki.openstreetmap.org/wiki/Java_Access_Example

This is probably easier, and certainly more robust, than calling an external command.

There are also higher level Java libraries: http://wiki.openstreetmap.org/wiki/Frameworks


For the general case of running a process, writing to its stdin and reading from its stdout, since Java 1.5 it's best to use ProcessBuilder to create your Process.

Once you have a process, you can use getInputStream(), getOutputSteam() and getErrorStream() to get the relevant streams (in the builder, if you like, you can make stderr go to stdout).

It's possible to get into a deadlock when reading and writing these streams - in many situations you'll need to either use non-blocking IO classes or create separate threads for reading and writing.

slim
  • 40,215
  • 13
  • 94
  • 127
  • Thanks for your answer. Due to some special reasons, query via HTTP is not allow. I took your advice ` ProcessBuilder.start()` and `getOutputSteam()`. – user2775128 Jul 26 '17 at 02:57