关于 arcgis-rest-services
arcgis-rest-services 是面向开发者的技能,介绍如何通过 @arcgis/core/rest 模块调用 ArcGIS Server REST 端点。内容覆盖空间查询,以及路径规划、地理编码、地点搜索、地理处理和地图打印等服务。
主要功能
- 01直接与动态 ESM 导入
- 02路径规划和服务区分析
- 03地理编码与地点搜索
- 04要素查询与识别
- 05地理处理和几何操作
- 06服务端地图导出
适用场景
- 01查找多个停靠点之间的路线
- 02对地址进行地理编码或搜索附近地点
- 03查询要素并识别地图位置
- 04运行地理处理任务或导出地图
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ saschabrunnerch/ arcgis-maps-sdk-js-ai-context --skill arcgis-rest-services安装后在 Claude Code 中输入/arcgis-rest-services确认已加载。
详细介绍
ArcGIS REST 服务
通过 @arcgis/core/rest/* 命名空间调用 ArcGIS Server REST 端点时使用此技能。涵盖路径规划、地理编码、空间查询、地理处理、打印、地点搜索及其他服务器端操作。
导入模式
直接 ESM 导入
import * as route from "@arcgis/core/rest/route.js";
import * as locator from "@arcgis/core/rest/locator.js";
import * as query from "@arcgis/core/rest/query.js";
import RouteParameters from "@arcgis/core/rest/support/RouteParameters.js";
import FeatureSet from "@arcgis/core/rest/support/FeatureSet.js";
import Query from "@arcgis/core/rest/support/Query.js";
动态导入(CDN)
const route = await $arcgis.import("@arcgis/core/rest/route.js");
const locator = await $arcgis.import("@arcgis/core/rest/locator.js");
const [query, Query] = await $arcgis.import([
"@arcgis/core/rest/query.js",
"@arcgis/core/rest/support/Query.js",
]);
所有 REST 服务函数都将服务 URL 作为第一个参数,并将参数对象作为第二个参数:
const result = await serviceName.methodName(serviceUrl, params);
路径规划
规划途经多个停靠点的路径,并可选择设置障碍物和路线指引。
import * as route from "@arcgis/core/rest/route.js";
import RouteParameters from "@arcgis/core/rest/support/RouteParameters.js";
import FeatureSet from "@arcgis/core/rest/support/FeatureSet.js";
import Graphic from "@arcgis/core/Graphic.js";
const stops = new FeatureSet({
features: [
new Graphic({
geometry: { type: "point", longitude: -117.195, latitude: 34.057 },
attributes: { Name: "Start" },
}),
new Graphic({
geometry: { type: "point", longitude: -117.918, latitude: 33.812 },
attributes: { Name: "End" },
}),
],
});
const routeParams = new RouteParameters({
stops,
outSpatialReference: { wkid: 4326 },
returnDirections: true,
returnRoutes: true,
directionsLanguage: "en",
});
const routeUrl =
"https://route-api.arcgis.com/arcgis/rest/services/World/Route/NAServer/Route_World";
const result = await route.solve(routeUrl, routeParams);
const routeResult = result.routeResults[0];
const routeGeometry = routeResult.route.geometry;
// Display directions
routeResult.directions.features.forEach((feature) => {
console.log(
feature.attributes.text,
feature.attributes.length.toFixed(2),
"miles",
);
});
带障碍物的路径规划
const pointBarriers = new FeatureSet({
features: [
new Graphic({
geometry: { type: "point", longitude: -117.5, latitude: 33.9 },
}),
],
});
const routeParams = new RouteParameters({
stops,
pointBarriers,
outSpatialReference: { wkid: 4326 },
returnDirections: true,
});
const result = await route.solve(routeUrl, routeParams);
最近设施
查找距离一组事件点最近的设施。
import * as closestFacility from "@arcgis/core/rest/closestFacility.js";
import ClosestFacilityParameters from "@arcgis/core/rest/support/ClosestFacilityParameters.js";
import FeatureSet from "@arcgis/core/rest/support/FeatureSet.js";
const facilities = new FeatureSet({
features: [
new Graphic({
geometry: { type: "point", longitude: -117.2, latitude: 34.06 },
}),
new Graphic({
geometry: { type: "point", longitude: -117.3, latitude: 34.1 },
}),
],
});
const incidents = new FeatureSet({
features: [
new Graphic({
geometry: { type: "point", longitude: -117.19, latitude: 34.05 },
}),
],
});
const params = new ClosestFacilityParameters({
facilities,
incidents,
defaultTargetFacilityCount: 1,
returnRoutes: true,
returnDirections: true,
outSpatialReference: { wkid: 4326 },
});
const cfUrl =
"https://route-api.arcgis.com/arcgis/rest/services/World/ClosestFacility/NAServer/ClosestFacility_World";
const result = await closestFacility.solve(cfUrl, params);
const closestRoute = result.routes[0];
console.log("Distance:", closestRoute.attributes.Total_Kilometers, "km");
服务区
根据行驶时间或距离,生成设施周围的服务区多边形。
import * as serviceArea from "@arcgis/core/rest/serviceArea.js";
import ServiceAreaParameters from "@arcgis/core/rest/support/ServiceAreaParameters.js";
const params = new ServiceAreaParameters({
facilities: facilitiesFeatureSet,
defaultBreaks: [5, 10, 15], // minutes
trimOuterPolygon: true,
outSpatialReference: { wkid: 4326 },
});
const saUrl =
"https://route-api.arcgis.com/arcgis/rest/services/World/ServiceAreas/NAServer/ServiceArea_World";
const result = await serviceArea.solve(saUrl, params);
result.serviceAreaPolygons.forEach((polygon) => {
console.log(
"Break:",
polygon.attributes.FromBreak,
"-",
polygon.attributes.ToBreak,
"min",
);
});
定位器(地理编码)
地址转位置
import * as locator from "@arcgis/core/rest/locator.js";
const geocodeUrl =
"https://geocode-api.arcgis.com/arcgis/rest/services/World/GeocodeServer";
const results = await locator.addressToLocations(geocodeUrl, {
address: { SingleLine: "380 New York St, Redlands, CA" },
outFields: ["Addr_type", "Match_addr", "StAddr", "City"],
maxLocations: 5,
});
results.forEach((result) => {
console.log(result.address); // Matched address
console.log(result.location); // Point geometry
console.log(result.score); // Match score (0-100)
});
位置转地址(反向地理编码)
const result = await locator.locationToAddress(geocodeUrl, {
location: { type: "point", longitude: -117.195, latitude: 34.057 },
});
console.log(result.address);
console.log(result.attributes);
位置建议(自动补全)
const suggestions = await locator.suggestLocations(geocodeUrl, {
text: "380 New York",
location: { type: "point", longitude: -117.195, latitude: 34.057 },
});
suggestions.forEach((suggestion) => {
console.log(suggestion.text);
console.log(suggestion.magicKey);
});
// Use magicKey to get the full result
const results = await locator.addressToLocations(geocodeUrl, {
address: { SingleLine: suggestions[0].text },
magicKey: suggestions[0].magicKey,
outFields: ["*"],
});
查询(REST)
无需使用 FeatureLayer,直接查询要素服务端点中的要素。
import * as query from "@arcgis/core/rest/query.js";
import Query from "@arcgis/core/rest/support/Query.js";
const featureServiceUrl =
"https://services.arcgis.com/V6ZHFr6zdgNZuVG0/arcgis/rest/services/Landscape_Trees/FeatureServer/0";
const queryParams = new Query({
where: "Height > 50",
outFields: ["*"],
returnGeometry: true,
outSpatialReference: { wkid: 4326 },
});
// JSON result
const result = await query.executeQueryJSON(featureServiceUrl, queryParams);
console.log("Features found:", result.features.length);
// Count only
const count = await query.executeForCount(featureServiceUrl, queryParams);
// Extent only
const extentResult = await query.executeForExtent(
featureServiceUrl,
queryParams,
);
// Object IDs only
const ids = await query.executeForIds(featureServiceUrl, queryParams);
查询方法
| 方法 | 返回值 | 使用场景 |
|---|---|---|
executeQueryJSON(url, query) | FeatureSet | 完整要素数据 |
executeQueryPBF(url, query) | FeatureSet | 载荷更小(PBF 格式) |
executeForCount(url, query) | number | 仅要素计数 |
executeForExtent(url, query) | { count, extent } | 边界框 + 计数 |
executeForIds(url, query) | number[] | 仅对象 ID |
查找
根据属性值查找地图服务中的要素。
import * as find from "@arcgis/core/rest/find.js";
import FindParameters from "@arcgis/core/rest/support/FindParameters.js";
const params = new FindParameters({
searchText: "Los Angeles",
layerIds: [0, 1, 2],
searchFields: ["Name", "City"],
returnGeometry: true,
outSpatialReference: { wkid: 4326 },
});
const mapServiceUrl =
"https://sampleserver6.arcgisonline.com/arcgis/rest/services/USA/MapServer";
const result = await find.find(mapServiceUrl, params);
result.results.forEach((findResult) => {
console.log("Layer:", findResult.layerId, "Value:", findResult.value);
});
识别
识别地图服务中特定位置的要素。
import * as identify from "@arcgis/core/rest/identify.js";
import IdentifyParameters from "@arcgis/core/rest/support/IdentifyParameters.js";
const params = new IdentifyParameters({
geometry: view.toMap(screenPoint),
mapExtent: view.extent,
tolerance: 3,
width: view.width,
height: view.height,
layerOption: "all",
returnGeometry: true,
spatialReference: view.spatialReference,
});
const mapServiceUrl =
"https://sampleserver6.arcgisonline.com/arcgis/rest/services/USA/MapServer";
const result = await identify.identify(mapServiceUrl, params);
result.results.forEach((identifyResult) => {
console.log("Layer:", identifyResult.layerName);
console.log("Attributes:", identifyResult.feature.attributes);
});
打印
通过服务器端打印服务将地图导出为 PDF、PNG 或其他格式。
import * as print from "@arcgis/core/rest/print.js";
import PrintTemplate from "@arcgis/core/rest/support/PrintTemplate.js";
import PrintParameters from "@arcgis/core/rest/support/PrintParameters.js";
const template = new PrintTemplate({
format: "pdf",
layout: "letter-ansi-a-landscape",
layoutOptions: {
titleText: "My Map Export",
authorText: "Map Author",
scalebarUnit: "Miles",
},
exportOptions: {
dpi: 300,
width: 800,
height: 1100,
},
});
const params = new PrintParameters({
view,
template,
});
const printUrl =
"https://utility.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%20Map%20Task";
const result = await print.execute(printUrl, params);
window.open(result.url);
地点
使用 ArcGIS Places 服务搜索兴趣点(POI)。
查询点附近的地点
import * as places from "@arcgis/core/rest/places.js";
import PlacesQueryParameters from "@arcgis/core/rest/support/PlacesQueryParameters.js";
const queryParams = new PlacesQueryParameters({
categoryIds: ["13065"], // Restaurants
radius: 500, // meters
point: { type: "point", longitude: -87.626, latitude: 41.882 },
pageSize: 20,
});
const results = await places.queryPlacesNearPoint(queryParams);
results.results.forEach((place) => {
console.log(place.name, place.categories[0].label);
console.log("Distance:", place.distance, "m");
});
// Pagination
if (results.nextPage) {
const nextResults = await results.nextPage();
}
查询范围内的地点
const queryParams = new PlacesQueryParameters({
categoryIds: ["16000"], // Landmarks and Outdoors
xmin: -87.65,
ymin: 41.87,
xmax: -87.6,
ymax: 41.9,
});
const results = await places.queryPlacesWithinExtent(queryParams);
获取地点详情
import FetchPlaceParameters from "@arcgis/core/rest/support/FetchPlaceParameters.js";
const fetchParams = new FetchPlaceParameters({
placeId: results.results[0].placeId,
requestedFields: ["all"],
});
const details = await places.fetchPlace(fetchParams);
const placeDetails = details.placeDetails;
console.log("Name:", placeDetails.name);
console.log("Address:", placeDetails.address.streetAddress);
console.log("Phone:", placeDetails.contactInfo?.telephone);
console.log("Hours:", placeDetails.hours?.opening);
console.log("Rating:", placeDetails.rating?.user);
地点类别 ID
| 类别 | ID |
|---|---|
| 艺术与娱乐 | 10000 |
| 商业与专业服务 | 11000 |
| 社区与政府 | 12000 |
| 餐饮 | 13000 |
| 医疗与健康 | 15000 |
| 地标与户外 | 16000 |
| 零售 | 17000 |
| 体育与休闲 | 18000 |
| 旅行与交通 | 19000 |
地理处理器
在 ArcGIS Server 上运行自定义地理处理任务。
同步执行
import * as geoprocessor from "@arcgis/core/rest/geoprocessor.js";
const gpUrl =
"https://sampleserver6.arcgisonline.com/arcgis/rest/services/Elevation/ESRI_Elevation_World/GPServer/Viewshed";
const params = {
Input_Observation_Point: new FeatureSet({ features: [pointGraphic] }),
Viewshed_Distance: 15000,
};
const result = await geoprocessor.execute(gpUrl, params);
const outputFeatures = result.results[0].value;
outputFeatures.features.forEach((feature) => {
graphicsLayer.add(
new Graphic({ geometry: feature.geometry, symbol: fillSymbol }),
);
});
异步执行(长时间运行)
const jobInfo = await geoprocessor.submitJob(gpUrl, params);
// Wait for completion
const completedJobInfo = await jobInfo.waitForJobCompletion({
interval: 2000,
statusCallback: (info) => {
console.log("Status:", info.jobStatus);
},
});
// Fetch results
const resultData = await completedJobInfo.fetchResultData("Result_Layer");
几何服务
执行服务器端几何操作。
import * as geometryService from "@arcgis/core/rest/geometryService.js";
const geomServiceUrl =
"https://utility.arcgisonline.com/ArcGIS/rest/services/Geometry/GeometryServer";
// Project geometries
const projected = await geometryService.project(geomServiceUrl, {
geometries: [point1, point2],
inSpatialReference: { wkid: 4326 },
outSpatialReference: { wkid: 3857 },
});
// Buffer geometries
const buffered = await geometryService.buffer(geomServiceUrl, {
geometries: [point],
distances: [1000],
unit: "meters",
outSpatialReference: { wkid: 4326 },
});
// Areas and lengths
const result = await geometryService.areasAndLengths(geomServiceUrl, {
polygons: [polygon],
lengthUnit: "meters",
areaUnit: "square-meters",
});
影像服务
import * as imageService from "@arcgis/core/rest/imageService.js";
import ImageIdentifyParameters from "@arcgis/core/rest/support/ImageIdentifyParameters.js";
const params = new ImageIdentifyParameters({
geometry: clickPoint,
returnGeometry: true,
returnCatalogItems: true,
});
const result = await imageService.identify(imageServiceUrl, params);
console.log("Pixel value:", result.value);
REST 服务身份验证
高级服务(路径规划、地理编码、地点搜索)需要身份验证。
import esriConfig from "@arcgis/core/config.js";
// Set API key globally
esriConfig.apiKey = "YOUR_API_KEY";
// Or register a token for a specific server
import esriId from "@arcgis/core/identity/IdentityManager.js";
esriId.registerToken({
server: "https://route-api.arcgis.com",
token: "YOUR_TOKEN",
});
常见问题
-
高级服务缺少身份验证:路径规划、地点搜索和地理编码服务需要 API 密钥或 OAuth 令牌。发出请求前请设置
esriConfig.apiKey。 -
使用了错误的参数类:每种 REST 服务都有自己的参数类(例如,路径规划使用
RouteParameters,最近设施使用ClosestFacilityParameters)。使用错误的类会导致静默失败。 -
忘记设置 outSpatialReference:结果默认采用服务的空间参考。请始终在参数中设置
outSpatialReference,使其与视图匹配:const params = new RouteParameters({ stops, outSpatialReference: view.spatialReference, }); -
未处理服务错误:请始终使用 try/catch 包装 REST 调用:
try { const result = await route.solve(routeUrl, routeParams); } catch (error) { if (error.name === "AbortError") { console.log("Request was cancelled"); } else { console.error("Service error:", error.message); } } -
使用旧版任务模式:
esri/tasks/*模式已被移除。请使用@arcgis/core/rest/*模块及其静态函数调用。
最后一公里配送
求解包含取货和配送约束的车辆路径问题。
import * as lastMileDelivery from "@arcgis/core/rest/lastMileDelivery.js";
// Get service description
const serviceDescription =
await lastMileDelivery.getServiceDescription(serviceUrl);
// Solve a vehicle routing problem
const result = await lastMileDelivery.solve(serviceUrl, params);
参考示例
route- 停靠点之间的路线查找directions-routelayer- 包含路线指引的路线图层basemap-places- 用于发现兴趣点的地点服务places- 地点查询和详情获取geoprocessing-viewshed- 使用视域分析进行地理处理geoprocessing-hotspot- 通过地理处理进行热点分析widgets-print- 服务端地图打印tasks-route- 路线规划任务tasks-find- 在地图服务中查找要素tasks-identify- 识别指定位置的要素tasks-query- 从服务中查询要素find- 按属性查找要素identify- 识别指定位置的要素query- 针对要素服务的 REST 查询
相关技能
- OAuth 和 API 密钥设置,请参阅
arcgis-authentication。 - FeatureLayer 查询(服务端和客户端),请参阅
arcgis-layers。 - 客户端几何操作,请参阅
arcgis-geometry-operations。 - 分析对象和要素缩减,请参阅
arcgis-spatial-analysis。