[8684] | 1 | // License: GPL. For details, see LICENSE file.
|
---|
[8744] | 2 | package org.openstreetmap.josm.tools;
|
---|
[8684] | 3 |
|
---|
| 4 | import java.io.IOException;
|
---|
| 5 | import java.io.Reader;
|
---|
| 6 |
|
---|
[8685] | 7 | import javax.script.Invocable;
|
---|
| 8 | import javax.script.ScriptEngine;
|
---|
| 9 | import javax.script.ScriptException;
|
---|
| 10 |
|
---|
[9856] | 11 | import org.openstreetmap.josm.io.CachedFile;
|
---|
[9717] | 12 |
|
---|
[8684] | 13 | /**
|
---|
[9704] | 14 | * Uses <a href="https://github.com/tyrasd/overpass-wizard/">Overpass Turbo query wizard</a> code (MIT Licensed)
|
---|
[8684] | 15 | * to build an Overpass QL from a {@link org.openstreetmap.josm.actions.search.SearchAction} like query.
|
---|
| 16 | *
|
---|
| 17 | * Requires a JavaScript {@link ScriptEngine}.
|
---|
[8744] | 18 | * @since 8744
|
---|
[8684] | 19 | */
|
---|
[8685] | 20 | public final class OverpassTurboQueryWizard {
|
---|
[8684] | 21 |
|
---|
| 22 | private static OverpassTurboQueryWizard instance;
|
---|
[13331] | 23 | private final ScriptEngine engine = Utils.getJavaScriptEngine();
|
---|
[8684] | 24 |
|
---|
| 25 | /**
|
---|
| 26 | * Replies the unique instance of this class.
|
---|
| 27 | *
|
---|
| 28 | * @return the unique instance of this class
|
---|
| 29 | */
|
---|
| 30 | public static synchronized OverpassTurboQueryWizard getInstance() {
|
---|
| 31 | if (instance == null) {
|
---|
| 32 | instance = new OverpassTurboQueryWizard();
|
---|
| 33 | }
|
---|
| 34 | return instance;
|
---|
| 35 | }
|
---|
| 36 |
|
---|
| 37 | private OverpassTurboQueryWizard() {
|
---|
[10733] | 38 | try (CachedFile file = new CachedFile("resource://data/overpass-wizard.js");
|
---|
| 39 | Reader reader = file.getContentReader()) {
|
---|
[13331] | 40 | if (engine != null) {
|
---|
| 41 | engine.eval("var console = {error: " + Logging.class.getCanonicalName() + ".warn};");
|
---|
| 42 | engine.eval("var global = {};");
|
---|
| 43 | engine.eval(reader);
|
---|
| 44 | engine.eval("var overpassWizard = function(query) {" +
|
---|
| 45 | " return global.overpassWizard(query, {" +
|
---|
| 46 | " comment: false," +
|
---|
| 47 | " outputFormat: 'xml'," +
|
---|
| 48 | " outputMode: 'recursive_meta'" +
|
---|
| 49 | " });" +
|
---|
| 50 | "}");
|
---|
| 51 | }
|
---|
[8684] | 52 | } catch (ScriptException | IOException ex) {
|
---|
[10235] | 53 | throw new IllegalStateException("Failed to initialize OverpassTurboQueryWizard", ex);
|
---|
[8684] | 54 | }
|
---|
| 55 | }
|
---|
| 56 |
|
---|
| 57 | /**
|
---|
| 58 | * Builds an Overpass QL from a {@link org.openstreetmap.josm.actions.search.SearchAction} like query.
|
---|
| 59 | * @param search the {@link org.openstreetmap.josm.actions.search.SearchAction} like query
|
---|
| 60 | * @return an Overpass QL query
|
---|
[9385] | 61 | * @throws UncheckedParseException when the parsing fails
|
---|
[8684] | 62 | */
|
---|
[10101] | 63 | public String constructQuery(String search) {
|
---|
[13331] | 64 | if (engine == null) {
|
---|
| 65 | throw new IllegalStateException("Failed to retrieve JavaScript engine");
|
---|
| 66 | }
|
---|
[8684] | 67 | try {
|
---|
[9856] | 68 | final Object result = ((Invocable) engine).invokeFunction("overpassWizard", search);
|
---|
[9850] | 69 | if (Boolean.FALSE.equals(result)) {
|
---|
[9385] | 70 | throw new UncheckedParseException();
|
---|
[8684] | 71 | }
|
---|
[11003] | 72 | return (String) result;
|
---|
[8684] | 73 | } catch (NoSuchMethodException e) {
|
---|
[9997] | 74 | throw new IllegalStateException(e);
|
---|
[8684] | 75 | } catch (ScriptException e) {
|
---|
[10101] | 76 | throw new UncheckedParseException("Failed to execute OverpassTurboQueryWizard", e);
|
---|
[8684] | 77 | }
|
---|
| 78 | }
|
---|
| 79 | }
|
---|