Skip to content

Support opening ArcGIS FeatureServer URLs directly (single layer + multi-layer discovery) #14225

@jatorre

Description

@jatorre

Context

The ESRIJSON driver currently requires users to manually construct /query URLs to read features from ArcGIS FeatureServer endpoints. For example:

# This works — but users have to know the query API
ogrinfo "https://example.com/.../FeatureServer/0/query?where=1%3D1&outFields=*&f=json"

# This does NOT work — returns no features (metadata JSON, not recognized)
ogrinfo "https://example.com/.../FeatureServer/0"

# This also does NOT work — multi-layer not supported
ogrinfo "https://example.com/.../FeatureServer"

This is a usability gap. ArcGIS FeatureServer is one of the most widely deployed vector data services, and users reasonably expect GDAL to handle these URLs directly — the same way WFS or OAPIF URLs work.

Related: #4613 (multi-layer support, reopened by @rouault as "a reasonable enhancement"), #12081 (pagination retry).

Current state

The ESRIJSON driver does have solid support for reading ESRI JSON responses, including:

  • Field type mapping (esriFieldType* → OGR types)
  • ESRI geometry parsing
  • Automatic pagination via exceededTransferLimit / resultOffset
  • GET/POST switching for long URLs

But the driver only activates for URLs containing f=json, f=pjson, or resultRecordCount= (see IsLikelyESRIJSONURL() in ogrgeojsonutils.cpp). A bare FeatureServer URL doesn't match any of these, so it's never claimed by the driver.

Proposal

I'd like to incrementally improve FeatureServer support. Before writing code, I want to check whether this approach makes sense to the maintainers.

Step 1 — Single-layer URL rewriting (small, extends ESRIJSON driver)

When opening a URL matching .../FeatureServer/<layer_id>:

  • Detect it in IsLikelyESRIJSONURL() / ESRIJSONDriverGetSourceType()
  • In OGRESRIJSONDriverOpen(), rewrite the URL to .../FeatureServer/<layer_id>/query?where=1%3D1&outFields=*&f=json
  • Preserve any existing query parameters (e.g. ?token=...)
  • The existing ESRI JSON parsing and pagination then handles the rest

This is ~50 lines of C++ in the existing driver, no new files.

Step 2 — Multi-layer discovery (medium, addresses #4613)

When opening .../FeatureServer (no layer ID):

  • Fetch the service metadata JSON (?f=json)
  • Parse the layers array to enumerate available layers
  • Expose each as a separate OGR layer, with reads routed through /query

This follows the same pattern as OAPIF (/collections → per-collection /items) and WFS (GetCapabilities → per-type GetFeature).

Step 3+ — Filters, auth, robustness (future)

Questions for maintainers

  1. Should this live in the ESRIJSON driver or become a new driver? Step 1 naturally extends ESRIJSON. Step 2 starts to look more like a service driver (similar to WFS/OAPIF/Carto). Is there a point where it should become ogr/ogrsf_frmts/arcgis/?

  2. Does Step 2 require an RFC? It adds multi-layer behavior to what's currently a single-layer driver. The code change is moderate (following existing patterns from OAPIF/WFS), but the architectural shift might warrant an RFC.

  3. Any concerns with Step 1 as a starting PR? It's minimal and non-breaking — URLs that already have /query are not affected.

I'm happy to start with Step 1 as a PR if the approach looks right, or adjust based on feedback.

Metadata

Metadata

Assignees

No one assigned

    Labels

    not for AI loversSee https://gdal.org/en/stable/community/ai_tool_policy.html

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions