geeViz.esriLib¶
ArcGIS / Esri REST services client for geeViz.
Bridges three Esri service types into the existing geeViz viewer with no
JavaScript changes required. The viewer already supports both
tileMapService (for raster tiles) and geoJSONVector (for vector
features) layer types.
Service type |
Mechanism |
|---|---|
Image Service |
|
Map Service (cached) |
|
Feature Service (≤ |
Fetch |
Feature Service (> |
|
Public API — 7 functions + 1 constant:
import geeViz.esriLib as el
# Discover data on any ArcGIS Portal
results = el.searchPortal("naip 2023") # IIPP (default)
results = el.searchPortal("naip 2023", portal="agol") # ArcGIS Online
results = el.searchPortal("naip 2023",
portal="https://myagency.gov/portal")
# Available portals
el.PORTALS.keys() # iipp, agol, usgs, noaa, usfs, nasa
# Inspect any service
meta = el.getServiceMetadata("https://.../ImageServer")
# Add to the geeViz map (auto-dispatches by service type)
el.addEsriService(result_or_url)
# Or call the typed helpers directly
el.addEsriImageService("https://.../ImageServer", name="NAIP 2023")
el.addEsriFeatureService("https://.../FeatureServer/0",
max_features=2000, where="STATE='UT'")
el.addEsriMapService("https://.../MapServer")
Token-gated portals:
# Obtain a token first:
# POST <portal>/sharing/rest/generateToken
# username=...&password=...&client=requestip&expiration=60&f=json
token = "..."
el.searchPortal("classified data", token=token)
el.addEsriFeatureService(url, token=token)
Copyright 2026 Ian Housman
Licensed under the Apache License, Version 2.0 (the “License”); you may not use this file except in compliance with the License. You may obtain a copy of the License at
Module Attributes
Module-level dict mapping short names to portal base URLs. |
Functions
|
Fetch and add an ArcGIS Feature Service layer as a GeoJSON vector layer. |
|
Add an ArcGIS Image Service as an XYZ tile layer to the geeViz map. |
|
Add a cached ArcGIS Map Service as an XYZ tile layer to the geeViz map. |
|
Auto-detect the Esri service type and call the appropriate add helper. |
|
Fetch and return the JSON metadata for any ArcGIS REST service. |
|
Search any ArcGIS Portal for hosted services. |
- geeViz.esriLib.PORTALS: dict[str, str] = {'agol': 'https://www.arcgis.com', 'iipp': 'https://imagery.geoplatform.gov/iipp', 'nasa': 'https://nasa.maps.arcgis.com', 'noaa': 'https://coastalatlas.noaa.gov', 'usfs': 'https://data.fs.usda.gov/geodata', 'usgs': 'https://www.sciencebase.gov/sciencebase'}¶
Module-level dict mapping short names to portal base URLs.
Add your own at runtime:
from geeViz.esriLib import PORTALS PORTALS["myagency"] = "https://gis.myagency.gov/portal"
- geeViz.esriLib.searchPortal(query: str, portal: str = 'iipp', limit: int = 20, data_only: bool = True, raw_q: str | None = None, token: str | None = None, **filters: Any) list[dict[str, Any]][source]¶
Search any ArcGIS Portal for hosted services.
Uses the standard
/sharing/rest/searchendpoint present on ArcGIS Online, IIPP, and any ArcGIS Enterprise install.- Parameters:
query (str) – Free-text search query (e.g.
"naip 2023","fire perimeter").portal (str, optional) – Either a short name from
PORTALS("iipp","agol","usgs","noaa","usfs","nasa") or a full portal base URL. Defaults to"iipp".limit (int, optional) – Maximum results to return (1–100). Defaults to 20.
data_only (bool, optional) – When
True(default), appends a bundled exclusion list that filters out non-data items (styles, web apps, dashboards, etc.) so results are datasets only. Set toFalseto search without restrictions.raw_q (str, optional) – If supplied, overrides the assembled query string entirely — ignores
query,data_only, andfilters. Use for portal query DSL power users.token (str, optional) – ArcGIS token for secured portals. Omit for public services. Obtain via
POST <portal>/sharing/rest/generateToken.**filters – Extra ArcGIS search filters forwarded verbatim as query params (e.g.
sortField="title",sortOrder="asc",bbox="-120,35,-110,42").
- Returns:
Parsed portal items. Each dict includes:
id(str): Item ID.title(str): Item title.type(str): Esri item type (e.g."Image Service","Feature Service").snippet(str): Short description.tags(list of str): Associated tags.url(str): Service endpoint URL (may be""if not set).owner(str): Portal username of the owner.created(int): Unix timestamp (ms) of item creation.modified(int): Unix timestamp (ms) of last modification.thumbnail(str or None): Thumbnail URL, orNoneif absent._raw(dict): Full raw portal item dict for advanced access.
- Return type:
list of dict
Example:
import geeViz.esriLib as el # Search IIPP for NAIP imagery (default portal) results = el.searchPortal("naip 2023", limit=10) for r in results: print(r["title"], r["type"], r["url"]) # ArcGIS Online results = el.searchPortal("wildfire perimeter", portal="agol") # Custom Enterprise portal results = el.searchPortal("hydrology", portal="https://gis.mystate.gov/portal") # Raw portal query DSL (bypasses data_only and filters) results = el.searchPortal("", raw_q='type:"Feature Service" owner:USGS')
- geeViz.esriLib.getServiceMetadata(url: str, token: str | None = None) dict[str, Any][source]¶
Fetch and return the JSON metadata for any ArcGIS REST service.
Appends
?f=jsonto the URL and returns the parsed response. Works for ImageServer, FeatureServer, MapServer, and any sub-layer URL (e.g./FeatureServer/0).- Parameters:
url (str) –
ArcGIS service endpoint, e.g.:
"https://naip.services.arcgis.com/.../ImageServer" "https://services.arcgis.com/.../FeatureServer/0" "https://server.arcgisonline.com/.../MapServer"
token (str, optional) – ArcGIS token for secured services.
- Returns:
Parsed service metadata. Common keys vary by service type:
name(str): Service name.type(str): Layer geometry type (Feature Services).fields(list): Schema fields (Feature Services).extent(dict): Spatial extent.spatialReference(dict): Spatial reference info.minScale,maxScale(int): Scale range.capabilities(str): Comma-separated capabilities string.
- Return type:
dict
- Raises:
ConnectionError – If the URL is unreachable.
ValueError – If the response is not valid JSON.
Example:
import geeViz.esriLib as el meta = el.getServiceMetadata("https://.../ImageServer") print(meta["name"]) print(meta["extent"]) # FeatureServer layer 0 meta = el.getServiceMetadata("https://.../FeatureServer/0") print([f["name"] for f in meta.get("fields", [])])
- geeViz.esriLib.addEsriImageService(url_or_result: str | dict, viz_params: dict | None = None, name: str | None = None, token: str | None = None) None[source]¶
Add an ArcGIS Image Service as an XYZ tile layer to the geeViz map.
Constructs the ArcGIS tile URL pattern
<service_url>/tile/{z}/{y}/{x}and callsgeeViz.geeView.Map.addTileLayer.Note
ArcGIS tile URLs use
{z}/{y}/{x}order (y before x), not the XYZ standard{z}/{x}/{y}. This function emits the correct ArcGIS order automatically.- Parameters:
url_or_result (str or dict) –
Either:
A bare service URL, e.g.
"https://naip.services.arcgis.com/.../ImageServer"A
searchPortal()result dict (the"url"key is used).
viz_params (dict, optional) – Forwarded to
addTileLayeras keyword arguments. Supported keys:opacity(float),visible(bool),max_zoom(int).name (str, optional) – Layer name shown in the geeViz layer list. Defaults to the last segment of the service URL.
token (str, optional) – ArcGIS token appended to tile requests as
?token=<>.
Example:
import geeViz.esriLib as el import geeViz.geeView as gv el.addEsriImageService( "https://naip.services.arcgis.com/.../ImageServer", name="NAIP 2022", viz_params={"opacity": 0.85}, ) gv.Map.centerObject(gv.ee.Geometry.Point([-111.89, 40.77]), 12) gv.Map.view()
- geeViz.esriLib.addEsriMapService(url_or_result: str | dict, name: str | None = None, token: str | None = None, viz_params: dict | None = None) None[source]¶
Add a cached ArcGIS Map Service as an XYZ tile layer to the geeViz map.
Cached Map Services expose the same
/tile/{z}/{y}/{x}tile endpoint as Image Services and are handled identically. Dynamic (non-cached) Map Services do not serve tiles this way; for those, useaddEsriFeatureService()on the individual sub-layer.- Parameters:
url_or_result (str or dict) – Service URL or
searchPortal()result dict.name (str, optional) – Layer name. Defaults to last URL segment.
token (str, optional) – ArcGIS token for secured services.
viz_params (dict, optional) –
opacity,visible,max_zoom.
Example:
import geeViz.esriLib as el el.addEsriMapService( "https://server.arcgisonline.com/ArcGIS/rest/services/" "World_Imagery/MapServer", name="ESRI World Imagery", )
- geeViz.esriLib.addEsriFeatureService(url_or_result: str | dict, viz_params: dict | None = None, name: str | None = None, max_features: int = 1000, where: str = '1=1', token: str | None = None) None[source]¶
Fetch and add an ArcGIS Feature Service layer as a GeoJSON vector layer.
Hits
<url>/query?f=geojson&where=<where>&outSR=4326and passes the returned GeoJSON directly togeeViz.geeView.Map.addLayer.Warning
Always performs a
returnCountOnly=truepre-flight before fetching geometry. If the result count exceeds max_features, aValueErroris raised with a concrete remediation message.- Parameters:
url_or_result (str or dict) – Feature Service or sub-layer URL (e.g.
".../FeatureServer/0"), or asearchPortal()result dict. If the URL points to the FeatureServer root rather than a specific layer,/0is appended automatically.viz_params (dict, optional) – Passed to
Map.addLayeras thevizdict. Supports all geeViz vector viz keys ("color","strokeColor","fillColor","opacity","strokeWidth","layerType", etc.).name (str, optional) – Layer name. Defaults to last URL segment.
max_features (int, optional) – Hard cap on feature count. If the service has more than this many features matching where, a
ValueErroris raised. Defaults to 1000. Increase with care — very large GeoJSON payloads can slow the viewer.where (str, optional) – SQL WHERE clause sent to the service for server-side filtering. Defaults to
"1=1"(all features). Example:where="STATE_FIPS='06'"(California only).token (str, optional) – ArcGIS token for secured services.
- Raises:
ValueError – If the feature count exceeds max_features.
ConnectionError – If the service URL is unreachable.
Example:
import geeViz.esriLib as el import geeViz.geeView as gv # Simple fetch — all features up to default cap el.addEsriFeatureService( "https://services.arcgis.com/.../FeatureServer/0", name="Wildfire Perimeters", ) # Filter server-side to stay under the cap el.addEsriFeatureService( "https://services.arcgis.com/.../FeatureServer/0", where="YEAR_=2023 AND GIS_ACRES > 10000", name="Large 2023 Fires", max_features=500, ) gv.Map.view()
- geeViz.esriLib.addEsriService(url_or_result: str | dict, viz_params: dict | None = None, name: str | None = None, token: str | None = None, max_features: int = 1000, where: str = '1=1') None[source]¶
Auto-detect the Esri service type and call the appropriate add helper.
Inspects the URL path (and falls back to the service metadata) to determine whether url_or_result is an Image Service, Feature Service, or Map Service, then delegates to
addEsriImageService(),addEsriFeatureService(), oraddEsriMapService().- Parameters:
url_or_result (str or dict) – Service URL or
searchPortal()result dict.viz_params (dict, optional) – Visualization parameters forwarded to the typed helper.
name (str, optional) – Layer name.
token (str, optional) – ArcGIS token.
max_features (int, optional) – Forwarded to
addEsriFeatureService().where (str, optional) – SQL WHERE clause forwarded to
addEsriFeatureService().
- Raises:
ValueError – If the service type cannot be determined.
Example:
import geeViz.esriLib as el results = el.searchPortal("naip 2023", limit=5) for r in results: el.addEsriService(r) # dispatches by type automatically