Arcgis for Server download from service workaround

6529
12
02-09-2015 01:39 AM
PeriklisPanagiotidis
New Contributor II

     As Arcgis for server has not a built in download shapefile(or any other format) functionality the "clip and ship" geoprocessing example is being suggested by many users and developers. However I find it quite limiting. As far as I understand, the "Extract Data" tool requires first to be run with a pre-defined set of Layers as a "Parameter" just like the "Zion" example.

     What I (and many other developers) need is a script/service that takes an Arcgis Server service as an input (or a relevant js object like featureset) and returns a shapefile (or any other format) as an output. Of course I am referring to a client web application. I am using the Javascript API but if I am not mistaken Flex developers face the same issue. Thanks.

12 Replies
nita14
by
Occasional Contributor III

HI Periklis,

You can do what you want with one geoprocessing tool: JSON to Feature . Here is the workflow:

    1) Create the python script to Query input Map or Feature Service (send request to Query Endpoint). Pass the output JSON to arcpy.JSONToFeatures_conversion tool. Zip the output shape and expose it as GPDataFIle as an output parameter

     2) Share the script as a Geoprocessing Service

Regards,

Adam

PeriklisPanagiotidis
New Contributor II

Thanks Adam, that simplified things a lot. You actually don't need to use JSON to Feature tool. You can save it directly to shapefile. I will put the code below.

However I am still frustrated that I have to go through the service to get to the file instead of doing that in the background. Geoserver has that functionality built in

In any case, if anyone wants to use the script below they will probably want to add a return string with the file name according their needs.

import arcpy

from arcpy import env

import zipfile

import sys

import os

import glob

from random import randint

baseURL= arcpy.GetParameterAsText(0)

where = '1=1'

fields ='*'

token = ''

#The above variables construct the query

query = "?where={}&outFields={}&returnGeometry=true&f=json&token={}".format(where, fields, token)

fsURL = baseURL + query

fs = arcpy.FeatureSet()

fs.load(fsURL)

fs.save(arcpy.env.scratchFolder+"\\"+"download_file.shp")

#Randomize file name

def random_with_N_digits(n):

    range_start = 10**(n-1)

    range_end = (10**n)-1

    return randint(range_start, range_end)

#Ziping the shapefile files

def zipShapefile(inShapefile, newZipFN):

  if not (os.path.exists(inShapefile)):

    print inShapefile + ' Does Not Exist'

    return False

  if (os.path.exists(newZipFN)):

    os.remove(newZipFN)

  if (os.path.exists(newZipFN)):

    return False

  zipobj = zipfile.ZipFile(newZipFN,'w')

  for infile in glob.glob( inShapefile.lower().replace(".shp",".*")):

    zipobj.write(infile,os.path.basename(infile),zipfile.ZIP_DEFLATED)

  zipobj.close()

  return True

randomname = str(random_with_N_digits(8))

InputShapeFile = arcpy.env.scratchFolder+"\\"+"download_file.shp"

#Public folder. Probably you will want to change this

OutputZipFile = "C:\\inetpub\\wwwroot\\Shapefiles\\"+randomname+"_file.zip"

zipShapefile(InputShapeFile,OutputZipFile)

print "done!"

JasonHansel
New Contributor

Hi,

Python Noob. All I would like is for our users to be able to Download a layer(s) from a Map Service in .shp/,gdb output. I'm not digging the Extract Toolset, mainly because users "might" get inaccurate data via Clip. I would rather use a 'Select' but am not having a bunch of luck. I tried the above code but am getting errors, see below. Any help is Grate-ly appreciated. Thanks!

Runtime error
Traceback (most recent call last):
File "<string>", line 33, in <module>
File "c:\program files (x86)\arcgis\desktop10.5\arcpy\arcpy\arcobjects\arcobjects.py", line 175, in load
return convertArcObjectToPythonObject(self._arc_object.Load(*gp_fixargs(args)))
RuntimeError: RecordSetObject: Cannot open table for Load

0 Kudos