Converti ArcGIS Server JSON in GeoJSON?


47

Sto creando una mappa web usando Leaflet e voglio essere in grado di afferrare i feature layer dal nostro ArcServer. Sono stato in grado di recuperare con successo una classe di funzionalità come JSON, ma gli oggetti JSON di Esri non seguono gli standard GeoJSON, quindi non possono essere visualizzati.

Qualcuno conosce uno script di conversione o uno strumento che gestisce questo?

In caso contrario, ho intenzione di creare uno script per convertire gli oggetti ArcServer JSON in GeoJSON.


Ho avuto difficoltà a ottenere ogr2ogr per mangiare json ESRI proveniente da una query sulle funzionalità di MapServer. (L'esempio di @ SasaIvetic utilizza una richiesta FeatureServer e il risultato di MapServer che devo consumare non deve essere stato intercambiabile.) Comunque, questo sito ha fatto il trucco: http://ogre.adc4gis.com/
elrobis

Risposte:


40

OGR:

ogr2ogr -f GeoJSON test.json "http://sampleserver3.arcgisonline.com/ArcGIS/rest/services/Hydrography/Watershed173811/FeatureServer/0/query?where=objectid+%3D+objectid&outfields=*&f=json" OGRGeoJSON

Tale comando leggerà il risultato della query direttamente dall'URL. Puoi anche fornirlo con un file di testo contenente il tuo JSON oppure puoi fornire direttamente il JSON codificato sulla riga di comando. Puoi ovviamente usare i collegamenti ORG Python per automatizzarlo all'interno di uno script, se necessario, o la libreria per farlo in codice.

Per quelli a cui piacciono i servizi Web, vedere Ogre un client Web ogr2ogr in grado di convertire json in geojson in e viceversa, nonché geojson in shapefile.

Riferimento: http://www.gdal.org/drv_geojson.html


Ho scaricato FWTools. Quando eseguo quel comando, viene visualizzato l'errore "Impossibile aprire l'origine dati" Il mio URL qui "con i seguenti driver. -> Shapefile ESRI -> File MapInfo -> UK .NTF -> SDTS -> TIGER -> S57 -> DGN -> VRT -> REC -> Memoria -> BNA -> CSV -> NAS -> GML -> GPX - > KML -> GeoJSON -> Interlis 1 -> Interlis 2 -> GMT -> SQLite -> ODBC -> PGeo -> OGDI -> PostgreSQL -> MySQL -> XPlane -> AVCBin -> AVCE00 -> DXF -> Geoconcept - > GeoRSS -> GPSTrackMaker -> VFK Non vedo qualcosa come "ESRI JSON" nell'elenco dei driver.
Tanner,

1
@Tanner: FWTools viene fornito con OGR v1.7 in cui è stato aggiunto il supporto GeoJSON con v1.8.0. Sto eseguendo GDAL / OGR 1.9dev qui, anche se non tramite FWTools. Penso di averli presi
Sasa Ivetic il

Grazie. Ho ottenuto questo per funzionare sulla riga di comando. Sto ancora lavorando per farlo funzionare nel mio Javascript - qualsiasi consiglio sarebbe apprezzato.
Tanner,

@Tanner come hai superato l'errore? Non è un problema di versione per me, ma sto ottenendo lo stesso errore sul mio computer Windows
kflaw,

@kflaw Siamo spiacenti, ma non ricordo esattamente. Penso di aver appena usato ogr2ogr dalla riga di comando e non ho avuto bisogno o utilizzo di FWTools.
Tanner,

7

Puoi anche vedere le geojson-utils di Esri su Github che "contiene utilità [javascript] per convertire GeoJSON in altri formati geografici json e viceversa. Attualmente sono stati sviluppati solo GeoJSON in Esri JSON. Inoltre, tieni presente che solo le geometrie nel sistema di coordinate WGS84 sono supportati ".


2
Aggiornamento 12/2017: geojson-utilsè obsoleto. Guarda arcgis-to-geojson-utils o terraformer
GavinR l'

5

ESRI JSON a GeoJSON (per OpenLayers) * Probabilmente da modificare per Leaflet javascript

        //create esri JSON object
    var myReturn = "esriObj = "+xmlHttpGet(restCall, false);
    eval(myReturn);

I can now work with esriObj as a JSON object i.e. esriObj.geometryType. What happens in the xmlHttpGet method? Basically I create a XMLHttpRequest and pass in my REST URL  your can see this code here

3. OK i have my ESRI query JSON object now I need to parse the features in this object and essentially create GeoJSON strings which the OpenLayers sample will be happy with  cue the code butchery


function esriDeserialize(geojson)
{

    var element = document.getElementById('text');
    var type = document.getElementById("formatType").value;
    var features = formats['in'][type].read(geojson);
    var bounds;
    if(features)
    {
        if(features.constructor != Array) {
            features = [features];
        }
        for(var i=0; i<features.length;>
            if (!bounds) {
                bounds = features[i].geometry.getBounds();
            } else {
                bounds.extend(features[i].geometry.getBounds());
            }

        }
        vectors.addFeatures(features);
        //map.zoomToExtent(bounds);
        var plural = (features.length &gt; 1) ? 's' : '';
        //element.value = features.length + ' feature' + plural + ' added'
    } else {
        element.value = 'Bad input ' + type;
    }
}

function getEsriGeom(restCall){

    //call ESRI Rest API
    //"http://pc302926/ArcGIS/rest/services/worldadmin/MapServer/0/query?text=&amp;geometry=&amp;geometryType=esriGeometryEnvelope&amp;inSR=&amp;spatialRel=esriSpatialRelIntersects&amp;where=%22FIPS_CNTRY%22+%3D+%27AS%27&amp;returnGeometry=true&amp;outSR=4326&amp;outFields=&amp;f=json"
    var element = document.getElementById('text');  

    //create esri JSON object
    var myReturn = "esriObj = "+xmlHttpGet(restCall, false);
    eval(myReturn);

    element.value = "";
    var coordPairsPerFeature = 0;

    //for each feature
    for (var i=0; i &lt; esriObj.features.length; i++)
    {
        //get the geometry
        var o = esriObj.features[i].geometry;
        element.value = element.value + esriObj.features[i].attributes.ADMIN_NAME;

        //loop through all the rings
        for (var s=0; s &lt; o.rings.length; s++)
        {
            //create geojson start &amp; end - i know i'm getting polygons
            var geojsonstart = '{"type":"Feature", "id":"OpenLayers.Feature.Vector_124", "properties":{}, "geometry":{"type":"Polygon", "coordinates":[['
            var geojsonend = ']]}, "crs":{"type":"OGC", "properties":{"urn":"urn:ogc:def:crs:OGC:1.3:CRS84"}}}';

            //the coordinates for this ring
            var coords = o.rings[s];

            //loop through each coordinate
            var coordPair="";
            for (var g=0; g &lt; coords.length; g++)
            {
                coordPairsPerFeature = coordPairsPerFeature+1;

                //alert(coords[g]);
                if(g==coords.length-1){
                    coordPair = coordPair+"["+coords[g]+"]";
                }else{
                    coordPair=coordPair+"["+coords[g]+"],";
                }
            }

            //combine to create geojson string
            esriDeserialize(geojsonstart+coordPair+geojsonend);
        }

        element.value = element.value + "," + coordPairsPerFeature +"n";
    }

}
</features.length;>

fonte: http://mapbutcher.com/blog/?p=62


Se hai intenzione di convertire , dovresti usare ogr2ogr
Evan Carroll il

5

ArcGIS ora supporta GeoJSON

Ora ArcGIS Online ha GeoJSON tramite l'URL dell'API Rest di ArcGIS. Tutto quello che devi fare è impostare f=geojsonl'URL e configurare il servizio. Tenere presente che, per impostazione predefinita, ArcGIS online non consentirà l'esportazione GeoJSON fino a quando non si consentirà esplicitamente altri formati di output.

Ecco come abilitare l'esportazione:

  1. Accedi ad arcgis online
  2. fai clic sui feature layer,
  3. fai clic sulla scheda delle impostazioni
  4. seleziona questa casella che dice

    Esporta dati

    Consenti ad altri di esportare in diversi formati.

  5. Risparmia e attendi qualche minuto.

Nella pagina delle query, dovresti visualizzare l'elenco a discesa del formato di output con l'opzione GeoJSON. Si chiamava il vecchio json.


Un servizio di riposo agol è diverso da un servizio di riposo server ArcGIS? Agol può fornire geoJSON solo come servizio di riposo e non come server?
jotamon,

4

Volantino e strato vettoriale ArGIS.

https://github.com/JasonSanford/leaflet-vector-layers

Demo funzionante. http://geojason.info/leaflet-vector-layers/demos/arcgis-server/

Altro su Leaflet e ArcGIS.

  • Layer Server Leaflet e ArcGIS, ovvero AgsDynamicLayer e AgsFeatureLayer.

È possibile ottenere questo fork che ha il supporto per il server ArcGIS.

https://github.com/dtsagile/Leaflet/

 var sitesLayer = new L.AgsDynamicLayer(
    'http://ags2.dtsagile.com/ArcGIS/rest/services/LiveFeeds/WxMappr/MapServer',
    { maxZoom: 19,
        attribution: "NOAA",
        opacity: 1,
        layers: 'show:2' });
_map.addLayer(sitesLayer);

http://blog.davebouwman.com/2011/08/04/leaflet-lean-mean-javascript-maps/

ArcGIS Image Services and Leaflet http://blog.geomusings.com/2012/04/17/arcgis-image-services-and-leaflet/



3

Per una conversione di una volta avrei usato la risposta accettata da @Sasa Ivetic ma avevo bisogno di qualcosa in tempo reale, e Terraformer ha lavorato decentemente per quello. Sfortunatamente è solo per singole funzionalità per impostazione predefinita, quindi per più funzionalità è necessario scorrere l'array e aggiungere un ID a ciascuna funzionalità:

var FeatureCollection = {
  type: "FeatureCollection",
  features: []
}

for (var i = 0; i < arcgis.features.length; i++) {
  var feature = Terraformer.ArcGIS.parse(arcgis.features[i]);
  feature.id = i;
  FeatureCollection.features.push(feature)
};

Questo ha funzionato bene per me tranne che per i poligoni in più parti (ad es. Alaska e le sue isole), ma sono nuovo per questo, quindi è possibile che abbia codificato qualcosa in modo errato!


3

Conversione di ArcGIS JSON in GeoJSONCi in puro browser

ci sono 2 modi in cui puoi fare

1) TERRAFORMER

Nota: l'uso in node.js e l'uso nel browser sono diversi , dettagli vedere il link

2) Esri / arcgis-to-geojson-utils

utilizzare nel browser, ArcgisToGeojsonUtils è riferimento var globale il punto di ingresso di questo modulo

<script src="https://unpkg.com/@esri/arcgis-to-geojson-utils@1.2.0/dist/arcgis-to-geojson.js"></script>

// parse ArcGIS JSON, convert it to GeoJSON
const geojson = ArcgisToGeojsonUtils.arcgisToGeoJSON({
"x":-122.6764,
"y":45.5165,
"spatialReference": {
  "wkid": 4326
}

});

Tuttavia, se vuoi raggrupparti da solo, solo per l'apprendimento, segui i passaggi

a) Devi compilare tutto il file sorgente del modulo in un unico bundle.js

rollup.js installato da

npm install --global rollup

quindi vai alla cartella principale di js lib, trova il file js del punto di ingresso, in questo caso è index.js

$ rollup index.js --format umd --name "esri_arcgis_to_geojson" --file bundle.js

Dovresti trovare un nuovo file bundle.js nella tua directory principale.

Ora nel file html del browser, includere questo file bundle.js

<script src='.../.../.../bundle.js'>

Puoi usarlo ora da

  // parse ArcGIS JSON, convert it to GeoJSON
  var geojson = esri_arcgis_to_geojson.arcgisToGeoJSON({
                            "x":-122.6764,
                            "y":45.5165,
                            "spatialReference": {
                              "wkid": 4326
                            }
                            });

 // take GeoJSON and convert it to ArcGIS JSON
  var arcgis = esri_arcgis_to_geojson.geojsonToArcGIS({
                            "type": "Point",
                              "coordinates": [45.5165, -122.6764]
                            });enter code here

Ricorda che esri_arcgis_to_geojson è il nome che hai chiamato lib

Questo diventa il nome della variabile globale, disponibile nel browser.

Il trucco è che il processo bundle aggiunge la funzione attrezzo istantanea come (funzione xx {}) qui è la parte superiore di bundle.js

  (function (global, factory) {
     typeof exports === 'object' && typeof module !== 'undefined' ? 
        factory(exports) :
      typeof define === 'function' && define.amd ? define(['exports'], 
         factory) :
      (factory((global.arcgis_to_geojson = {})));
      }(this, (function (exports) { 'use strict';

         ***ORIGINAL SOURCE CODE OF JS MODULE***

     })));

ArcGIS-to-GeoJSON-utils


2

Di solito * è abbastanza facile da convertire.

Ho realizzato uno script https://github.com/calvinmetcalf/esri2geo e ce ne sono altri che funzionano bene.

* L'eccezione sono i poligoni multiparte con buchi che non convertono 1 a 1 senza un po 'di geoprocessing.



1

Forse ancora più facile puoi usare la libreria Esri-leaflet per aggiungerla nativamente come layer in Leaflet.


2
Potresti incorporare un esempio nel tuo post delineando come questa risposta sia la domanda del PO?
Paul,

0

Se tutto ciò di cui hai bisogno è di restituire il servizio ArcServer come GeoJSON da utilizzare in qualsiasi tecnologia di mappatura tu voglia, ti consiglio vivamente di dare un'occhiata a questa finestra di dialogo sul problema di GitHub .

Non ho intenzione di replicare il dialogo qui perché ciò perderebbe tempo. Le tue opzioni sono chiaramente indicate lì direttamente da Esri.


-1

arcgis server rest api, servizio funzioni,

se esegui una query sul livello, con un URL come questo, ... / FeatureServer / query? layerDefs = ...

http://services3.arcgis.com/your_token/arcgis/rest/services/Parcels/FeatureServer/query?layerDefs={"0":""}&returnGeometry=true&f=pgeojson&geometryType=esriGeometryEnvelope&geometry={"xmin" : -117.923158, "ymin" : 33.644081, "xmax" : -117.921436, "ymax" : 33.645157,"spatialReference" : {"wkid" : 4326}}

Non è possibile impostare il formato geojson, f = pgeojson sarà una richiesta errata, f = json, perché la roba di ritorno non è caratteristica, i layer json sono stati restituiti.

Prova questa pagina di query html, puoi vedere, nessuna opzione geojson,

 http://services3.arcgis.com/you_token/arcgis/rest/services/Parcels/FeatureServer/query

Se si desidera restituire geojson (funzione), è necessario utilizzare questo URL ... / FeatureServer / 0 / query ...

/ 0 / significa layerID, se on ha solo 1 layer, quindi layerID = 0 .....

Prova questa pagina di query html, puoi vedere, geojson è un'opzione, perché sei un livello di query specifico con layerID = 0

http://services3.arcgis.com/your_token/arcgis/rest/services/Parcels/FeatureServer/0/query

Nota: ricordati di impostare quei 2 parametri: outSR = 4326 & f = geojson nell'ID di riferimento spaziale dell'URL, srid = 4326, poiché tutti i web map lo usano, f significa formato, entrambi f = pgeojson e f = geojson funzionano. Se non si imposta SR = 4326, arcgis server rest api di default NON utilizzerà 4326, invece utilizzerà qualcos'altro, solo 4326 ha un grado di unità, che viene utilizzato nella maggior parte delle mappe web. Un altro formato non funzionerebbe con le mappe web.

A proposito, per coloro che desiderano utilizzare arcgis server rest api con il servizio tile,

Tilestream e altri

/zoom(z)/x/y.png

http://localhost/v2/city_parcels/12/706/1641.png

servizio piastrelle server arcgis: no png, xey in ordine diverso

     /zoom(z)/y/x

http://services3.arcgis.com/your_token/ArcGIS/rest/services/Parcels/MapServer/tile/12/1641/706

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.