ESM: import * as arcade from "@arcgis/core/arcade.js";
CDN: const arcade = await $arcgis.import("@arcgis/core/arcade.js");
Object: @arcgis/core/arcade
Since: ArcGIS Maps SDK for JavaScript 4.24
This module allows you to evaluate Arcade expressions outside traditional ArcGIS Arcade profiles. Profiles define the valid input variables (i.e. profile variables) for expressions, supported functions, and valid return types of expressions. All Arcade expressions executed in the ArcGIS Maps SDK for JavaScript must conform to the rules of the profile where they are written. The createArcadeExecutor method provides an API for executing Arcade expressions outside the context of predefined ArcGIS Arcade profiles.
This module allows you to do the following:
createArcadeExecutor(script, profile, options){Promise<ArcadeExecutor>}
Compiles an Arcade expression and its profile into an executor. The executor provides functions to evaluate the results for profile variables.
Parameters
Specification
The Arcade expression to compile and execute.
The profile definition used to execute the given expression. The profile defines the profile variable names and data types the user may use as inputs in the expression. The variable instances are provided to the executor function.
optionalSince 4.33 Options used to configure the executor.
Specification
lruCache any
optionalSince 4.33
optionalSince 4.33 Required for expressions that use the GetUser()
Arcade function.
Returns
Type Description Promise<ArcadeExecutor> Resolves to an ArcadeExecutor that provides a synchronous (if applicable) and asynchronous function used to evaluate the compiled Arcade expression when provided with valid input profile variables.Examples
// Synchronous execution for all features in layer view
// % of the population not in labor force
const arcadeScript = "(($feature.POP_16UP - $feature.EMP_CY) / $feature.POP_16UP) * 100"
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
const laborForceExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = laborForceExecutor.fieldsUsed;
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return laborForceExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
// Asynchronous execution for one feature clicked in the view
const profile = {
variables: [{
name: "$feature",
type: "feature"
}, {
name: "$layer",
type: "featureSet"
}]
};
// This expression executes on each feature click. It compares the % of the population
// not participating in the labor force with the same value of all features within
// one mile of the selected feature's location
const arcadeScript = `
var featureNotLaborForce = Round((($feature.POP_16UP - $feature.EMP_CY)/$feature.POP_16UP)*100);
var id = $feature.OBJECTID;
var neighbors = Filter( Intersects( $layer, BufferGeodetic($feature, 1, "mile") ), "OBJECTID <> @id" );
if( Count(neighbors) == 0 ){
return "No neighbors within 1 mile";
}
var neighborsNotLaborForceAverage = Average(neighbors, "( (POP_16UP - EMP_CY) / POP_16UP) * 100");
var difference = Round(featureNotLaborForce - neighborsNotLaborForceAverage);
var differenceText = IIF(difference > 0, "+"+difference, Text(difference));
return differenceText;
`;
const neighborhoodExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = neighborhoodExecutor.fieldsUsed;
view.on("click", async (event) => {
const hitResponse = await view.hitTest(event, include: { layer });
const hitGraphic = hitResponse?.results[0].graphic;
const scriptResult = await neighborhoodExecutor.executeAsync({
"$feature": hitGraphic,
"$layer": hitGraphic.layer
}, {
spatialReference: view.spatialReference
});
// display the value of scriptResult in a UI component or use it
// in some form of client-side analysis
});
createArcadeProfile(profileName){Profile}
Since: ArcGIS Maps SDK for JavaScript 4.25 arcade since 4.24, createArcadeProfile added at 4.25.
Creates a Profile definition for an Arcade profile implemented in the ArcGIS Maps SDK for JavaScript. The result of this should be provided to the createArcadeExecutor method.
Parameter
The name of the Arcade profile definition to create. The values "feature-reduction-popup"
and "feature-reduction-popup-element"
are deprecated since 4.32.
Possible Values:"aggregate-field"|"form-constraint"|"feature-z"|"field-calculation"|"form-calculation"|"labeling"|"popup"|"popup-element"|"popup-feature-reduction"|"popup-element-feature-reduction"|"visualization"|"popup-voxel"|"popup-element-voxel"|"feature-reduction-popup"|"feature-reduction-popup-element"
Returns
Type Description Profile Returns the profile definition used to execute an expression with the ArcadeExecutor.Example
const labelingProfile = arcade.createArcadeProfile("labeling");
// creates the following object to be provided to the createArcadeExecutor method.
// {
// variables: [{
// name: "$feature",
// type: "feature"
// }]
// }
const labelExecutor = await createArcadeExecutor("$feature.NAME + ' COUNTY'", labelingProfile);
ArcadeExecutor
An executor provides a synchronous (if applicable) and asynchronous function used to evaluate the compiled Arcade expression with the inputs of the declared profile variables. It also provides metadata about the compilation result.
A function that can be invoked to evaluate the compiled expression for a set of profile variables. Will return the results of the evaluation. This function will only be available if isAsync
is false.
Asynchronous function that evaluates the compiled expression. This function may always be used to evaluate the expression, but must be used if isAsync
is true.
Since 4.33 Asynchronous function that evaluates the compiled expression for a batch of profile variable instances. This is the preferred execution method for large batches of features that require asynchronous execution.
References the names of fields used in the compiled expression when working with the $feature
profile variable or functions that expect field names, such as Expects
. Field names referenced here should be requested by the underlying layer or datastore. In JavaScript, this is typically done with layer.outFields
.
Indicates whether the expression accesses or uses a feature's geometry.
Indicates whether the compiled expression accesses data using a FeatureSet function and therefore must be executed using the executeAsync
function. If false
, the expression may be executed with execute
or executeAsync
.
Examples
// Synchronous execution for all features in layer view
// % of the population not in labor force
const arcadeScript = "(($feature.POP_16UP - $feature.EMP_CY) / $feature.POP_16UP) * 100"
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
const laborForceExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = laborForceExecutor.fieldsUsed;
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return laborForceExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
// Asynchronous execution for one feature clicked in the view
const profile = {
variables: [{
name: "$feature",
type: "feature"
}, {
name: "$layer",
type: "featureSet"
}]
};
// This expression executes on each feature click. It compares the % of the population
// not participating in the labor force with the same value of all features within
// one mile of the selected feature's location
const arcadeScript = `
var featureNotLaborForce = Round((($feature.POP_16UP - $feature.EMP_CY)/$feature.POP_16UP)*100);
var id = $feature.OBJECTID;
var neighbors = Filter( Intersects( $layer, BufferGeodetic($feature, 1, "mile") ), "OBJECTID <> @id" );
if( Count(neighbors) == 0 ){
return "No neighbors within 1 mile";
}
var neighborsNotLaborForceAverage = Average(neighbors, "( (POP_16UP - EMP_CY) / POP_16UP) * 100");
var difference = Round(featureNotLaborForce - neighborsNotLaborForceAverage);
var differenceText = IIF(difference > 0, "+"+difference, Text(difference));
return differenceText;
`;
const neighborhoodExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = neighborhoodExecutor.fieldsUsed;
view.on("click", async (event) => {
const hitResponse = await view.hitTest(event, include: { layer });
const hitGraphic = hitResponse?.results[0].graphic;
const scriptResult = await neighborhoodExecutor.executeAsync({
"$feature": hitGraphic,
"$layer": hitGraphic.layer
}, {
spatialReference: view.spatialReference
});
// display the value of scriptResult in a UI component or use it
// in some form of client-side analysis
});
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
// Arcade expression defined by user...
const syncExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = syncExecutor.fieldsUsed;
// throw error if expression from user uses
// invalid functions that require async execution
if(syncExecutor.isAsync){
throw new Error("Invalid expression. Expression should not use FeatureSet functions.");
}
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return syncExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
ArcadeServices
Since: ArcGIS Maps SDK for JavaScript 4.33 arcade since 4.24, ArcadeServices added at 4.33.
ArcadeServices provides access to services and user information that are required for executing Arcade expressions.
An ArcGIS Portal instance. This is required for expressions that use the GetUser()
Arcade function. By default, the portal referenced in esriConfig.portalUrl is used.
ArrayElementType
The type definition of a profile variable of type array
.
The Arcade data type of the variable. See ProfileVariableInstanceType to see the mapping of Arcade types to JavaScript types.
Possible Values:"dictionary"|"feature"|"featureSet"|"featureSetCollection"|"geometry"|"number"|"text"|"date"|"dateOnly"|"time"|"boolean"|"knowledgeGraph"|"voxel"
optionalOnly applicable when type
is dictionary
. The type definitions of the dictionary's properties. The names of these properties should not begin with the $
character.
Only applicable when type
is array
. The type definition of the Array's items. Arcade arrays must be of a single type when used as an input profile variable. When indicating an elementType, you do not need to specify a name for the element.
ArrayVariable
The type definition for an Arcade array profile variable.
The name of the profile variable. To follow Arcade's naming convention, this should start with the $
character unless this variable is nested in a DictionaryVariable.
The Arcade data type of the variable. For ArrayVariable, the type is always array
. The corresponding JavaScript type to an Arcade Array is an array following the specification defined in ProfileVariableInstanceType.
The type definition of the Array's items. Arcade arrays must be of a single type when used as an input profile variable. When indicating an elementType, you do not need to specify a name for the element.
Example
const profile = {
variables: [{
name: "$checkpoints",
type: "array",
elementType: {
type: "feature"
}
}]
};
BatchExecuteContext
Since: ArcGIS Maps SDK for JavaScript 4.33 arcade since 4.24, BatchExecuteContext added at 4.33.
The context of the Arcade expression for batch execution.
The expected spatial reference of input geometries in geometry functions. If executing an expression in the context of a map, then set the spatial reference of the view to this property. If executing an expression in the context of a layer, then use the layer's spatial reference. If not specified, then the spatial reference defaults to WebMercator.
optionalDefault Value:system
Since 4.28 Defines the default time zone in which to create and display Arcade date types. Possible values include any time zone that may be set on the View.timeZone. Generally, if the Arcade context's profile involves a map, or features originating from a map, the value of View.timeZone should be set here. By default, the time zone is set to "system".
optionalDefault Value:64
The maximum number of concurrent executions of the expression.
DictionaryVariable
The type definition for an Arcade dictionary profile variable.
The name of the profile variable. To follow Arcade's naming convention, this should start with the $
character unless this variable is nested in another DictionaryVariable. See the example below.
The Arcade data type of the variable. The corresponding JavaScript type to an Arcade Dictionary is a plain Object following the specification defined in ProfileVariableInstanceType.
The value is always "dictionary".
optionalThe type definitions of the dictionary's properties. The names of these properties should not begin with the $
character.
Example
const profile = {
variables: [{
name: "$analysisParams",
type: "dictionary",
properties: [{
name: "distance",
type: "number"
}, {
name: "projectType",
type: "text"
}, {
name: "includeBuffer",
type: "boolean"
}]
}, {
name: "$projectLocation",
type: "feature"
}]
};
ExecuteContext
The execution context of the Arcade expression.
The expected spatial reference of input geometries in geometry functions. If executing an expression in the context of a map, then set the spatial reference of the view to this property. If executing an expression in the context of a layer, then use the layer's spatial reference. If not specified, then the spatial reference defaults to WebMercator.
optionalDefault Value:system
Since 4.28 Defines the default time zone in which to create and display Arcade date types. Possible values include any time zone that may be set on the View.timeZone. Generally, if the Arcade context's profile involves a map, or features originating from a map, the value of View.timeZone should be set here. By default, the time zone is set to "system".
optionalSince 4.33
optionalSince 4.33 Required for expressions that use the GetUser()
Arcade function.
Examples
// the input feature's geometry is expected
// to be in the spatial reference of the view
// All Arcade dates will be represented in the
// time zone of the view or web map.
await executor.executeAsync({
"$feature": feature
}, {
spatialReference: view.spatialReference,
timeZone: view.timeZone
});
// the input feature's geometry is expected
// to be in the spatial reference of the layer
await executor.executeAsync({
"$feature": feature
}, {
spatialReference: layer.spatialReference
});
// the input feature's geometry is expected
// to be Web Mercator
await executor.executeAsync({
"$feature": feature
});
ExecuteFunction(profileVariableInstances, context){ResultType}
Executes the compiled Arcade expression synchronously with the given profile variable instances. This function may not be used if the expression accesses data using FeatureSet functions.
Returns
Type Description ResultType Returns the value of the evaluated expression.Examples
// Synchronous execution for all features in layer view
// % of the population not in labor force
const arcadeScript = "(($feature.POP_16UP - $feature.EMP_CY) / $feature.POP_16UP) * 100"
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
const laborForceExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = laborForceExecutor.fieldsUsed;
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return laborForceExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
const profile = {
variables: [{
name: "$feature",
type: "feature"
}]
};
// Arcade expression defined by user...
const syncExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = syncExecutor.fieldsUsed;
// throw error if expression from user uses invalid functions
if(syncExecutor.isAsync){
throw new Error("Invalid expression. Expression should not use FeatureSet functions.");
}
const { features } = await layerView.queryFeatures();
const allValues = features.map( (feature) => {
return syncExecutor.execute({
"$feature": feature
});
});
// allValues can be displayed in a chart, or used to
// report stats for this variable
ExecuteFunctionAsync(profileVariableInstances, context){Promise<ResultType>}
Executes the compiled Arcade expression asynchronously with the given profile variable instances.
Returns
Type Description Promise<ResultType> Resolves to the value of the evaluated expression.Example
// Asynchronous execution for one feature clicked in the view
const profile = {
variables: [{
name: "$feature",
type: "feature"
}, {
name: "$layer",
type: "featureSet"
}]
};
// This expression executes on each feature click. It compares the % of the population
// not participating in the labor force with the same value of all features within
// one mile of the selected feature's location
const arcadeScript = `
var featureNotLaborForce = Round((($feature.POP_16UP - $feature.EMP_CY)/$feature.POP_16UP)*100);
var id = $feature.OBJECTID;
var neighbors = Filter( Intersects( $layer, BufferGeodetic($feature, 1, "mile") ), "OBJECTID <> @id" );
if( Count(neighbors) == 0 ){
return "No neighbors within 1 mile";
}
var neighborsNotLaborForceAverage = Average(neighbors, "( (POP_16UP - EMP_CY) / POP_16UP) * 100");
var difference = Round(featureNotLaborForce - neighborsNotLaborForceAverage);
var differenceText = IIF(difference > 0, "+"+difference, Text(difference));
return differenceText;
`;
const neighborhoodExecutor = await createArcadeExecutor(arcadeScript, profile);
// ensures data values from fields used in the expression are
// available when the expression executes.
layer.outFields = neighborhoodExecutor.fieldsUsed;
view.on("click", async (event) => {
const hitResponse = await view.hitTest(event, include: { layer });
const hitGraphic = hitResponse?.results[0].graphic;
const scriptResult = await neighborhoodExecutor.executeAsync({
"$feature": hitGraphic,
"$layer": hitGraphic.layer
}, {
spatialReference: view.spatialReference
});
// display the value of scriptResult in a UI component or use it
// in some form of client-side analysis
});
ExecuteFunctionAsyncBatch(inputData, variableInstancesCreator, context){Promise<SettledArcadePromise[]>}
Since: ArcGIS Maps SDK for JavaScript 4.33 arcade since 4.24, ExecuteFunctionAsyncBatch added at 4.33.
Executes the compiled Arcade expression asynchronously for a batch of profile variable instances (i.e. inputs). This is the preferred execution method for large batches of features that require asynchronous execution.
Parameters
An iterable object, such as an array or collection, containing the data used to hydrate the profile variable instances.
Callback function used to create profile variable instances from each inputData
item.
The context with which to execute the expression.
Returns
Type Description Promise<SettledArcadePromise[]> Resolves with the results of evaluating the expression for eachinputData
item.
Example
const profile = {
variables: [{
name: "$text",
type: "text"
}]
};
const arcadeScript = `
var locale = GetEnvironment().locale; // browser locale
var result = TranslateText($text, locale);
// result will be a dictionary with the translated text
if (result.success){
if(HasValue(result, ["results", 0, "translation"])){
// returns "Hola mundo" if the device locale is 'es' and $text is "Hello world"
return result.results[0].translation[locale];
}
if (HasValue(result, ["results", 0, "text"])){
// returns "Hello world" if translation could not be performed
return result.results[0].text;
}
}
return "Translation not successful";
`;
const executor = await createArcadeExecutor(arcadeScript, profile);
const textToTranslate = ["Hello world", "Goodbye world", "Hello again", "Goodbye again"];
const translatedText = await executor.executeAsyncBatch(
textToTranslate,
(input) => ({
"$text": input
})
);
// persist the translated text for later use
Layer types that may be used to back FeatureSets in Arcade expressions.
FulfilledArcadePromise
Since: ArcGIS Maps SDK for JavaScript 4.33 arcade since 4.24, FulfilledArcadePromise added at 4.33.
Type definition for a fulfilled promise of the asynchronous execution of an Arcade expression.
The value is always "fulfilled".
The result of the evaluated expression.
Profile
Defines the definitions of a profile's input variables. This consists of an array of objects specifying the name of each profile variable and its Arcade data type. All profile names must begin with the $
character.
The Arcade type definitions for profile variables used as input to the compiled expression.
Example
const profile = {
variables: [{
name: "$mapClick",
type: "geometry"
}, {
name: "$threshold",
type: "number"
}, {
name: "$feature",
type: "feature"
}, {
name: "$map",
type: "featureSetCollection"
}]
};
The type definition of a profile variable. See the individual profile variable types for more information and examples.
The JavaScript types that may be used as inputs to profile variables when evaluating compiled expressions with ExecuteFunction or ExecuteFunctionAsync. See the table below for the following mapping of JavaScript types that may be used to hydrate profile variables for corresponding Arcade data types.
RejectedArcadePromise
Since: ArcGIS Maps SDK for JavaScript 4.33 arcade since 4.24, RejectedArcadePromise added at 4.33.
Type definition for a rejected promise of the asynchronous execution of an Arcade expression.
The value is always "rejected".
The reason for the rejection.
The JavaScript type of the result returned from the Arcade expression.
Since: ArcGIS Maps SDK for JavaScript 4.33 arcade since 4.24, SettledArcadePromise added at 4.33.
Type definition for a settled promise of the asynchronous execution of an Arcade expression.
SimpleVariable
The type definition for a simple Arcade profile variable.
The name of the profile variable. To follow Arcade's naming convention, this should start with the $
character unless this variable is nested in a DictionaryVariable.
The Arcade data type of the variable. See ProfileVariableInstanceType to see the mapping of Arcade types to JavaScript types.
Possible Values:"feature"|"featureSet"|"featureSetCollection"|"geometry"|"number"|"text"|"date"|"dateOnly"|"time"|"boolean"|"knowledgeGraph"|"voxel"
Example
const profile = {
variables: [{
name: "$mapClick",
type: "geometry"
}, {
name: "$threshold",
type: "number"
}, {
name: "$feature",
type: "feature"
}, {
name: "$map",
type: "featureSetCollection"
}]
};
VariableInstancesCreator(inputData){Object}
Since: ArcGIS Maps SDK for JavaScript 4.33 arcade since 4.24, VariableInstancesCreator added at 4.33.
Callback function used to create profile variable instances from generic input data.
Parameter
inputData any
Input data used to hydrate the profile variable instances.
Returns
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4