Using geoprocessing tasks in web applications

ArcGIS web-mapping APIs

A framework for web GIS will help you get started on understanding GIS-based web applications. The ArcGIS web APIs allow web browsers to communicate to ArcGIS Server GIS Services and render (draw) geographic data and perform analysis. The ArcGIS web APIs are offered in three different flavors. They are:

The three APIs have similar functionality but are targeted towards different development languages. To get started on the development of web applications using Flex or Silverlight, you must download the libraries from the ArcGIS for Developers site. For JavaScript Web APIs, it's not necessary to download the library since this library is accessed through a web URL. The ArcGIS for Developers site provides code samples, tutorials, guides, and detailed reference material for the ArcGIS Web APIs.

Geoprocessing tasks in web applications

You can add geoprocessing functionality and data analysis to web applications using ArcGIS geoprocessing services. Each geoprocessing service contains one or more geoprocessing tasks. If you browse through an ArcGIS server's Services Directory, you can find geoprocessing services, the tasks within the service, and the parameters and properties of each task. The Geoprocessing REST services topic provides information on the hierarchy of REST resources, and Introduction to geoprocessing tasks topic provides more information on geoprocessing tasks, their parameters, and how to access them. The web APIs provide convenient objects and methods to access geoprocessing tasks and execute the functionality.

To add a geoprocessing functionality provided by a task in your web application, follow the four steps below:

  1. Initialize the geoprocessing task.
  2. Set up parameters for the task.
  3. Run the task.
  4. Render the results.

These four steps allow the application to communicate with the server, execute the task successfully, and visualize the results as needed in the application. The section below shows how to implement the four steps to successfully add geoprocessing functionality using ArcGIS Web API for Javascript. Although the object declarations, method syntax, and event handling vary in the other two web APIs, the four-steps pattern is common and applicable to all web APIs. The steps will help you understand the best practices to use geoprocessing tasks in web applications.

Using geoprocessing tasks in the JavaScript application

The ArcGIS Web API for JavaScript is one of the ArcGIS Web APIs. If you are new to the JavaScript API, visit the ArcGIS API for JavaScript site. The site includes many code samples and you can search for geoprocessing samples.

The remainder of this topic will walk you through the four steps described above to include geoprocessing tasks in web applications using ArcGIS JavaScript API.

Step 1: Initialize the geoprocessing task

To initialize a geoprocessing task, you must be aware of the task URL. The template for a geoprocessing task URL is http://<arcgis-host>/<gpservicename>/GPServer/<gptask-name>. Add the code below to your JavaScript application to initialize a geoprocessing task.

When initializing, be sure to set the outSpatialReference property of the geoprocessing task instance to the web map's spatial reference. The datasets of geoprocessing tasks may be in a different spatial reference and hence their outputs may be in a different spatial reference as well. However, web applications assume the task outputs are in the same spatial reference as that of the map. This may cause unexpected behavior when drawing outputs. Therefore, you must set the output spatial reference property of the geoprocessing task. The server will return outputs in the spatial reference specified by the outSpatialReference property.

Initialize the geoprocessing task

// esri.tasks.gp is required for using Geoprocessor.
//  Add it along with other dojo.require statements.
dojo.require(esri.tasks.gp); 

/* Step 1: Initialize Geoprocessing Task as a global variable. 
    That is, declare the variable outside a function definition 
    since we will be using gpTask variable in other methods */
var gpTaskUrl="http://myserver/ArcGIS/rest/services/" +
                   "BufferPoints/GPServer/BufferPoints";
var gpTask = new esri.tasks.Geoprocessor(gpTaskUrl);	

// Set output spatial reference property to map's spatial reference.
//   myMap is assumed to be an instance of map container esri.map.
gpTask.outSpatialReference=myMap.spatialReference;

Step 2: Set up task parameters

When executing a geoprocessing task, the web application must provide the parameter values for the geoprocessing task. To learn the parameters requirements of a task, copy and paste the task URL into the address bar of a web browser to open the Task page of the services directory. The Task page lists all the task parameters and their data types. The task page also has a help URL where you can find more information on the geoprocessing functionality, access, and use.

Learn more about task parameters properties

For the successful execution of the task, you must specify the values for all the required input parameters (esriGPParameterTypeRequired) of the task as described in the Task page. Typically, the values of the task come from one or more of the below sources:

  • Values entered by the user using the web application
  • Values from one of the current web map feature layers or graphics layers
  • The results of other tasks such as query, route tasks, and so on
  • Results of other geoprocessing tasks

The JavaScript code below shows an example of creating input features, a GPFeatureRecordsetLayer parameter from a FeatureLayer that is added to the web map, and creating buffDistance, a GPLinearUnit parameter derived from a dojo text input with an id="distance". It is assumed that the user will interactively enter the distance value. Once the task parameters are created, a JSON construct, with name-value pairs of the parameters, is constructed and sent to the server.

Setup Parameters

//Step 2: Setup Parameters of the task
function setupParameters(){
   /* The code below assumes that the web map 
     has a featurelayer with id fLayer. */

   // Get Input Parameter 1 : GPFeatureRecordSetLayer from fLayer.
   var inputFeatures = new esri.tasks.FeatureSet();			    
   inputFeatures.features = map.getLayer("fLayer").graphics;
   inputFeatures.fields=map.getLayer("fLayer").fields;

   // Get Input Parameter 2 : GPLinearunit from a dojo UI element
   var buffDistance = new esri.tasks.LinearUnit();
   buffDistance.distance=dojo.byId(distance).value;
   buffDistance.units=esriMiles;

   // Create Parameter list with name-value pairs.
   // Names must match the parameter name in Task page.
   // Parameters must be in the same-order as in Task page.
   var params= {"Input_Features":inputFeatures, 
              "Distance":buffDistance};

   // Return name-value pairs of parameters
   return params;
}
NoteNote:

The GPFeatureRecordSetLayer and GPRecordSetLayer parameters have a default schema defined by the task. You can find the schema for the parameters in the Task page. A schema of a GPFeatureRecordSetLayer consists of geometry, spatial reference, fields, and features. It is a good practice to ensure GPFeatureRecordSetLayer parameters have all the properties as defined in the schema for successful results.

Step 3: Run the task

To run a task you should use the execute or submitJob method of the geoprocessor instance (gpTask) based on the supported operation of the geoprocessing task. You can find the supported operation of the task in the Task page. Task operation: execute and Task operation: submitJob topics explain the difference between the operations and the server and client communication for the operation.

Task operation: execute

If the supported operation of the task is Execute Task, you must use the execute method of the geoprocessor instance and pass the parameters. You must define event handlers that will steer the application on successful and failed requests. The onExecuteComplete event will be raised when the task executes successfully and returns the result and geoprocessing messages. The onError event is raised when a task execution fails. When the task fails, the server will return an error instance with HTML error code and geoprocessing messages, if any.

Task operation: execute

function myGPExecuteTask(){
 // Get params from setupParameters method described above.
 var params=setupParameters();

 // Setup onTaskSuccess and onTaskFailure event handlers.
 dojo.connect(gpTask, "onExecuteComplete",onTaskSuccess);
 dojo.connect(gpTask, "onError",onTaskFailure);

 // Execute gpTask with params
 gpTask.execute(params);
}

// Callback when the Task operation succeeded
function onTaskSuccess(results, messages) {
  // Do something with the results...
  // More info on rendering the results in section below    
}

// Handler that is invoked when the Task operation has failed
function onTaskFailure(error) {
  // Report error 
  alert("Error:"+ error); 
}

Task operation: submitJob

If the supported operation of the task is the submitJob operation, you must use the Geoprocessor.submitJob method and pass the parameters. In the case of submitJob, three events are raised, and they must be handled appropriately in the web application.

onStatusUpdate

When the current status of the job is received

onJobComplete

When the job has completed successfully

onError

When the job fails

  • onStatusUpdate: Unlike execute, in the case of submitJob, the server creates a job and assigns a jobId. submitJob operations do not notify the client when a job is complete, so it's up to the client to check with the service to determine the status of the job. Web applications, by default, send status requests to the server every second to determine the status of the task. Each time the status response is received, the onStatusUpdate event is raised. You can increase or decrease the status check interval through the Geoprocessor.setUpdateDelay method if needed. The onStatusUpdate event is raised every time the status of the job is checked. The event handler receives a JobInfo instance containing the job ID, the job status, and any GPMessages returned by the server. You can use this information to keep track of the progress of the task.
  • onJobComplete: When JobInfo.jobStatus = STATUS_SUCCEEDED, the onJobComplete event is raised. The results are not automatically returned to the client when the operation is completed, but instead are stored on the server, and the client must send a request to retrieve them. In the onJobComplete event handler, you can invoke the Geoprocessor.getResultData method and get the results. Each output parameter is an independent resource, and the getResultData method of the geoprocessor instance must be invoked for each output parameter of the task. You must supply the jobId returned by the event handler and the name of the output parameter in the getResultData method. You must also create an event handler for the onGetResultDataComplete event. The onGetResultDataComplete event is raised when the result value of the output parameter is received by the web application.
  • onError: The onError event is raised when a submitJob request or status request times out or if the geoprocessing tasks failed. The event will return an error instance with HTML error code.
You can learn more about jobs, job ID, jobstatus, and the server-client communication in submitJob operations in Task operation: submitJob. The code below shows how you can submit a job to the server and handle the events.

Task operation: submitJob

function myGPSubmitJob(){
 // Get params from setupParameters method described above.
 var params=setupParameters();

 // Setup event handlers.
 dojo.connect(gpTask, "onJobComplete",onTaskComplete);
 dojo.connect(gpTask, "onError",onTaskFailure);
 dojo.connect(gpTask, "onStatusUpdate",onTaskStatus);
 gpTask.submitJob(params);
}

// Event handler for onJobComplete event
function onTaskComplete(jobInfo) {
    /* Get the value of an output parameter Buffer_polygons
      using getResultData. The name of the output
      may vary in your gpTask*/      
    dojo.connect(gpTask, "onGetResultDataComplete",
                      onTaskResultComplete);
    gpTask.getResultData(jobInfo.jobId, 
                          "Buffer_polygons");
}

// Event handler for onStatusUpdate event
function onTaskStatus(jobInfo) {
     //write status to console to help debugging
    console.log(jobInfo.jobStatus);
}

// Event handler for onError event
function onTaskFailure(error) {
  // Report error 
  alert("Error:"+ error); 
}

Step 4: Rendering the result

The results of a geoprocessing task are rendered based on the data type of the output parameter.

GPFeatureRecordSetLayer

The output features are usually drawn on the web map as a graphics layer to show the geoprocessing result.

GPRecordSet

The output records are displayed in a grid, or the values are used to create charts and graphs.

GPRasterDataLayer

Output rasters can be downloaded but cannot be drawn on the map. However, you can use a Result Map Service to visualize raster data.

Learn more about Result Map Service and Using result map service in web applications

GPDataFile

Output files can be downloaded, or files such as .gpx and .csv can be processed by the web application.

GPBoolean, GPDataFile, GPLong, GPDouble, GPString, GPLinearUnit, GPDate

Outputs are displayed using HTML or other widgets.

Results from the onExecuteComplete event handler

In the case of the execute operation, the onExecuteComplete event returns the results and messages of the geoprocessing task. The results instance is an array of all the output parameters of the task, and the entries in the array are always in the order as listed in the Task page. Hence, the parameter values can be identified by their position in the array. Each output parameter in the array has a parameter name, its data type, and value. The code below shows how to access the first output parameter in the results. In the code below, the output parameter is known to be a GPFeatureRecordSetLayer output and therefore the code shows how to render it as a graphics layer and add it to the web application.

Rendering results from the onExecuteComplete event handler

function onTaskSuccess(results, messages) {
    /* Retrieve the output parameter value based 
      on its position from the result instance.
      In the case shown below, the output is the first output 
      parameter of the task and it
      is a GPFeatureRecordSetLayer.*/
    var featureset = results[0].value;
   
    // Create a graphics layer with features
    var taskResultLayer= new esri.layers.GraphicsLayer
              ({id:"MyGPExecuteResultLayer"});
    
    // Create a symbol based on the geometry. 
    // The geometry is assumed to be polygons in the code below
    var simplePolySymbol = new esri.symbol.SimpleFillSymbol();
    simplePolySymbol.setOutline(new esri.symbol.SimpleLineSymbol(
                  esri.symbol.SimpleLineSymbol.STYLE_SOLID,
                  new dojo.Color([0,0,0,0.5]), 1));
    simplePolySymbol.setColor(new dojo.Color([255,0,0,0.7]));
    
    // Create graphics from features and add it graphicslayer 
    dojo.forEach(featureset.features,function(feature){
             feature.setSymbol(simplePolySymbol);
             //Add feature to the graphics layer
             taskResultLayer.add(feature);});
    }
    // Add graphicslayer to webmap 
    //  myMap is assumed to be an instance of map container esri.map
    myMap.addLayer(taskResultLayer)
}

Results from the onGetResultDataComplete event handler

The onGetResultDataComplete event provides a result instance. Unlike the results from the onExecuteComplete event, the result instance will have values only for the requested parameter. The parameter result will have the requested parameter's name, data type, and value. The parameter value is retrieved from the result and used as needed. The code below shows rendering the results of a GPFeatureRecordSetLayer parameter from a parameter result instance.

Results from the onGetResultDataComplete event handler

function onTaskResultComplete(paramResult) {
   // Retrieve the value of the parameter from the paramresult
   var featureSet = paramResult.value;

   // Create a graphics layer with features
   var taskResultLayer= new esri.layers.GraphicsLayer
              ({id:"MyGPSubmitJobResultLayer"});
    
   // Create a symbol based on the geometry. 
   // The geometry is assumed to be polygons in the code below
   var simplePolySymbol = new esri.symbol.SimpleFillSymbol();
   simplePolySymbol.setOutline(new esri.symbol.SimpleLineSymbol(
                  esri.symbol.SimpleLineSymbol.STYLE_SOLID,
                  new dojo.Color([0,0,0,0.5]), 1));
   simplePolySymbol.setColor(new dojo.Color([255,0,0,0.7]));
    
   // Create graphics from features and add it graphicslayer 
   dojo.forEach(featureset.features,function(feature){
             feature.setSymbol(simplePolySymbol);
             //Add feature to the graphics layer
             taskResultLayer.add(feature);});
   }
   // Add graphicslayer to webmap 
   //   myMap is assumed to be an instance of map container esri.map.
   myMap.addLayer(taskResultLayer)
}

Flex and Silverlight API

The four steps described above for JavaScript applications is applicable to Flex and Silverlight API as well. You can find code samples for using geoprocessing tasks in Flex API and Silverlight API in their respective online SDKs.

12/18/2014