Changeset 36294 in osm for applications/editors


Ignore:
Timestamp:
2024-07-18T14:19:53+02:00 (4 months ago)
Author:
taylor.smock
Message:

Replace uses of javax.json with jakarta.json

This also fixes some lint issues.

This additionally updates the minimum JOSM version to r19044 since it has Jakarta
JSON and it is Java 11+.

Location:
applications/editors/josm/plugins/SaudiNationalAddress
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • applications/editors/josm/plugins/SaudiNationalAddress/build.xml

    r35351 r36294  
    44    <!-- enter the SVN commit message -->
    55    <property name="commit.message" value="Initial version."/>
    6     <property name="plugin.main.version" value="10580"/>
     6    <property name="plugin.main.version" value="19044"/>
    77    <property name="plugin.author" value="Mouath Ibrahim"/>
    88    <property name="plugin.class"
  • applications/editors/josm/plugins/SaudiNationalAddress/pom.xml

    r36282 r36294  
    1717    <properties>
    1818        <plugin.src.dir>src</plugin.src.dir>
    19         <plugin.main.version>10580</plugin.main.version>
     19        <plugin.main.version>19044</plugin.main.version>
    2020        <plugin.author>Mouath Ibrahim</plugin.author>
    2121        <plugin.class>org.openstreetmap.josm.plugins.saudinationaladdress.SaudiNationalAddressPlugin</plugin.class>
  • applications/editors/josm/plugins/SaudiNationalAddress/src/org/openstreetmap/josm/plugins/saudinationaladdress/SaudiNationalAddressAction.java

    r35359 r36294  
     1// License: GPL. For details, see LICENSE file.
    12package org.openstreetmap.josm.plugins.saudinationaladdress;
    23
     4import jakarta.json.Json;
     5import jakarta.json.JsonArray;
     6import jakarta.json.JsonObject;
     7import jakarta.json.JsonReader;
    38import org.openstreetmap.josm.actions.JosmAction;
    49import org.openstreetmap.josm.command.ChangeCommand;
     
    611import org.openstreetmap.josm.command.SequenceCommand;
    712import org.openstreetmap.josm.data.UndoRedoHandler;
     13import org.openstreetmap.josm.data.coor.ILatLon;
    814import org.openstreetmap.josm.data.coor.LatLon;
    915import org.openstreetmap.josm.data.coor.conversion.DecimalDegreesCoordinateFormat;
     
    1723import org.openstreetmap.josm.tools.HttpClient;
    1824import org.openstreetmap.josm.tools.ImageProvider;
     25import org.openstreetmap.josm.tools.Logging;
    1926import org.openstreetmap.josm.tools.Shortcut;
    2027
    21 import javax.json.Json;
    22 import javax.json.JsonArray;
    23 import javax.json.JsonObject;
    24 import javax.json.JsonReader;
    25 import javax.swing.*;
    2628import java.awt.event.ActionEvent;
    2729import java.awt.event.KeyEvent;
    2830import java.io.BufferedReader;
    2931import java.io.IOException;
    30 import java.io.UnsupportedEncodingException;
    3132import java.net.MalformedURLException;
     33import java.net.URI;
     34import java.net.URISyntaxException;
    3235import java.net.URL;
    3336import java.net.URLEncoder;
     37import java.nio.charset.StandardCharsets;
    3438import java.util.ArrayList;
    3539import java.util.Collection;
    3640import java.util.List;
    3741
     42import static org.openstreetmap.josm.tools.I18n.marktr;
    3843import static org.openstreetmap.josm.tools.I18n.tr;
    3944import static org.openstreetmap.josm.tools.I18n.trn;
    4045
     46import javax.swing.JOptionPane;
     47
    4148/**
    42  * Created by tom on 02/08/15. (originaly for AustriaAddressHelper plugin)
    43  * Mouath Ibrahim 05/03/20
     49 * Created by tom on 02/08/15. (originally for AustriaAddressHelper plugin)
     50 * @author Mouath Ibrahim 05/03/20
    4451 */
    4552public class SaudiNationalAddressAction extends JosmAction {
    4653    static final String baseUrl = "https://apina.address.gov.sa/NationalAddress/v3.1/Address/address-geocode";
    47 
     54    private static final String GET_ADDRESS = marktr("Get Address");
     55
     56    /**
     57     * Create a new action for getting Saudi addresses
     58     */
    4859    public SaudiNationalAddressAction() {
    49         super(tr("Get Address"), new ImageProvider("icon.png"), tr("Get Address"),
    50                 Shortcut.registerShortcut("Get Address", tr("Get Address"),
     60        super(tr(GET_ADDRESS), new ImageProvider("icon.png"), tr(GET_ADDRESS),
     61                Shortcut.registerShortcut("Get Address", tr(GET_ADDRESS),
    5162                        KeyEvent.VK_G, Shortcut.CTRL), true, "getAddress",
    5263                true);
    5364    }
    5465
     66    /**
     67     * Load an address for an object
     68     * @param selectedObject The object to get the address for
     69     * @return The address if available, {@code null} otherwise
     70     */
    5571    public static OsmPrimitive loadAddress(OsmPrimitive selectedObject) {
    56         final String API_KEY = Config.getPref().get(SaudiNationalAddressPreference.API_KEY);
    57 
    58         if (!API_KEY.isEmpty()) {
     72        final String apiKey = Config.getPref().get(SaudiNationalAddressPreference.API_KEY);
     73
     74        if (!apiKey.isEmpty()) {
    5975            LatLon center = selectedObject.getBBox().getCenter();
    6076            // https://apina.address.gov.sa/NationalAddress/v3.1/Address/address-geocode?lat=25.36919&long=49.55076&language=E&format=json&encode=utf8
    61             URL url = null;
    62             try {
    63                 url = new URL(baseUrl
    64                         + "?lat=" + URLEncoder.encode(DecimalDegreesCoordinateFormat.INSTANCE.latToString(center), "UTF-8")
    65                         + "&long=" + URLEncoder.encode(DecimalDegreesCoordinateFormat.INSTANCE.lonToString(center), "UTF-8")
    66                         + "&language=A" // A for Arabic, E for English
    67                         + "&format=json"
    68                         + "&encode=utf8"
    69                 );
    70             } catch (MalformedURLException | UnsupportedEncodingException e) {
    71                 notification(e.getMessage(), JOptionPane.ERROR_MESSAGE);
    72             }
    73 
    74             JsonObject json = null;
    75             try (BufferedReader in = HttpClient.create(url)
    76                     .setReasonForRequest("JOSM Plugin Saudi National Address")
    77                     .setHeader("api_key", API_KEY)
    78                     .connect()
    79                     .getContentReader();
    80                  JsonReader reader = Json.createReader(in)) {
    81                 json = reader.readObject();
    82             } catch (IOException e) {
    83                 notification(e.getMessage(), JOptionPane.ERROR_MESSAGE);
    84 
    85             }
    86 
     77            URL url = generateUrl(center);
     78
     79            JsonObject json = getJson(apiKey, url);
    8780            // The api is not consistent in what it returns for error messages, hence this smart AI.
    8881            try {
    8982                if (json != null) {
    9083                    if (json.containsKey("statusCode")) {
    91                         if (!(json.getInt("statusCode") == 200)) {
     84                        if (json.getInt("statusCode") != 200) {
    9285                            notification(json.getString("message"), JOptionPane.ERROR_MESSAGE); // message: auth, rate limit errors
    9386                        }
     
    9588                        notification(tr("No address was found for this object."), JOptionPane.WARNING_MESSAGE);
    9689                    } else {
    97                         final JsonArray addressItems = json.getJsonArray("Addresses");
    98                         final JsonObject firstAddress = addressItems.getJsonObject(0);
    99 
    100                         String country = "SA";
    101                         //                    String province = firstAddress.getString("RegionName");
    102                         String district = firstAddress.getString("District");
    103                         String postcode = firstAddress.getString("PostCode") + "-" + firstAddress.getString("AdditionalNumber");
    104                         String city = firstAddress.getString("City");
    105                         String buildingNumber = firstAddress.getString("BuildingNumber");
    106                         String street = firstAddress.getString("Street");
    107 
    108                         final OsmPrimitive newObject = selectedObject instanceof Node
    109                                 ? new Node(((Node) selectedObject))
    110                                 : selectedObject instanceof Way
    111                                 ? new Way((Way) selectedObject)
    112                                 : selectedObject instanceof Relation
    113                                 ? new Relation((Relation) selectedObject)
    114                                 : null;
    115 
    116 
    117                         // seperate arabic and english
    118                         String[] districtArray = district.split(",");
    119                         String[] cityArray = city.split(",");
    120 
    121                         //                newObject.put("addr:country", country); // can be determined from boundary relations
    122                         //                newObject.put("addr:province", province); // can be determined from boundary relations
    123                         newObject.put("addr:postcode", postcode);
    124                         newObject.put("addr:city", cityArray[1]);
    125                         newObject.put("addr:city:en", cityArray[0]);
    126                         newObject.put("addr:district", districtArray[1]); // Arabic and common version
    127                         newObject.put("addr:district:en", districtArray[0]);
    128                         newObject.put("addr:housenumber", buildingNumber);
    129                         if (!street.isEmpty()) {
    130                             newObject.put("addr:street", street);
    131                         } // the api is still missing street names in some areas
    132 
    133                         String msg = tr("Successfully added address to selected object:") + "<br />"
    134                                 + encodeHTML(street) + " "
    135                                 + encodeHTML(buildingNumber) + ", "
    136                                 + encodeHTML(postcode) + " "
    137                                 + encodeHTML(district) + " ("
    138                                 + encodeHTML(country) + ")<br/>";
    139                         notification(msg, JOptionPane.INFORMATION_MESSAGE);
    140 
    141                         return newObject;
     90                        return createAddress(selectedObject, json);
    14291                    }
    14392                }
    14493            } catch (NullPointerException e) {
     94                Logging.error(e);
    14595                notification(tr("Unknown Error: ") + e.getMessage(), JOptionPane.ERROR_MESSAGE);
    14696            }
    14797        } else {
    14898            notification(tr("Please set your API key in the preference window!"), JOptionPane.ERROR_MESSAGE);
    149             return null;
    15099        }
    151100        return null;
    152101    }
    153102
     103    private static URL generateUrl(ILatLon center) {
     104        try {
     105            return new URI(baseUrl
     106                    + "?lat=" + URLEncoder.encode(DecimalDegreesCoordinateFormat.INSTANCE.latToString(center), StandardCharsets.UTF_8)
     107                    + "&long=" + URLEncoder.encode(DecimalDegreesCoordinateFormat.INSTANCE.lonToString(center), StandardCharsets.UTF_8)
     108                    + "&language=A" // A for Arabic, E for English
     109                    + "&format=json"
     110                    + "&encode=utf8"
     111            ).toURL();
     112        } catch (URISyntaxException | MalformedURLException e) {
     113            Logging.trace(e);
     114            notification(e.getMessage(), JOptionPane.ERROR_MESSAGE);
     115        }
     116        return null;
     117    }
     118
     119    private static OsmPrimitive createAddress(OsmPrimitive selectedObject, JsonObject json) {
     120        final JsonArray addressItems = json.getJsonArray("Addresses");
     121        final JsonObject firstAddress = addressItems.getJsonObject(0);
     122
     123        String country = "SA";
     124        // String province = firstAddress.getString("RegionName");
     125        String district = firstAddress.getString("District");
     126        String postcode = firstAddress.getString("PostCode") + "-" + firstAddress.getString("AdditionalNumber");
     127        String city = firstAddress.getString("City");
     128        String buildingNumber = firstAddress.getString("BuildingNumber");
     129        String street = firstAddress.getString("Street");
     130
     131        final OsmPrimitive newObject = createPrimitive(selectedObject);
     132
     133        // separate arabic and english
     134        String[] districtArray = district.split(",");
     135        String[] cityArray = city.split(",");
     136
     137        //                newObject.put("addr:country", country); // can be determined from boundary relations
     138        //                newObject.put("addr:province", province); // can be determined from boundary relations
     139        newObject.put("addr:postcode", postcode);
     140        newObject.put("addr:city", cityArray[1]);
     141        newObject.put("addr:city:en", cityArray[0]);
     142        newObject.put("addr:district", districtArray[1]); // Arabic and common version
     143        newObject.put("addr:district:en", districtArray[0]);
     144        newObject.put("addr:housenumber", buildingNumber);
     145        if (!street.isEmpty()) {
     146            newObject.put("addr:street", street);
     147        } // the api is still missing street names in some areas
     148
     149        String msg = tr("Successfully added address to selected object:") + "<br />"
     150                + encodeHTML(street) + " "
     151                + encodeHTML(buildingNumber) + ", "
     152                + encodeHTML(postcode) + " "
     153                + encodeHTML(district) + " ("
     154                + encodeHTML(country) + ")<br/>";
     155        notification(msg, JOptionPane.INFORMATION_MESSAGE);
     156
     157        return newObject;
     158    }
     159
     160    private static JsonObject getJson(String apiKey, URL url) {
     161        try (BufferedReader in = HttpClient.create(url)
     162                .setReasonForRequest("JOSM Plugin Saudi National Address")
     163                .setHeader("api_key", apiKey)
     164                .connect()
     165                .getContentReader();
     166             JsonReader reader = Json.createReader(in)) {
     167            return reader.readObject();
     168        } catch (IOException e) {
     169            Logging.trace(e);
     170            notification(e.getMessage(), JOptionPane.ERROR_MESSAGE);
     171        }
     172        return null;
     173    }
     174
     175    private static OsmPrimitive createPrimitive(OsmPrimitive selectedObject) {
     176        if (selectedObject instanceof Node) {
     177            return new Node((Node) selectedObject);
     178        }
     179        if (selectedObject instanceof Way) {
     180            return new Way((Way) selectedObject);
     181        }
     182        if (selectedObject instanceof Relation) {
     183            return new Relation((Relation) selectedObject);
     184        }
     185        throw new IllegalStateException("Unknown object type: " + selectedObject.getClass().getName());
     186    }
     187
    154188    private static String encodeHTML(String s) {
    155         StringBuffer out = new StringBuffer();
     189        StringBuilder out = new StringBuilder(s.length());
    156190        for (int i = 0; i < s.length(); i++) {
    157191            char c = s.charAt(i);
    158192            if (c > 127 || c == '"' || c == '<' || c == '>') {
    159                 out.append("&#" + (int) c + ";");
     193                out.append("&#").append((int) c).append(';');
    160194            } else {
    161195                out.append(c);
Note: See TracChangeset for help on using the changeset viewer.