J'ai rencontré de nombreux utilisateurs qui ont demandé la possibilité de télécharger les services de fonctionnalités hébergés ArcGIS Online et les services de fonctionnalités/cartes ArcGIS Server. Voir l'outil ci-joint pour faire exactement cela. L'outil vous permettra également de télécharger les pièces jointes des services de fonctionnalités hébergés ArcGIS Online. J'espère que les utilisateurs trouveront cela utile et pratique.<\/P>
<\/P>
Mise à jour 10\/08\/17:<\/STRONG> L'outil téléchargera désormais les domaines de valeurs codées dans la géodatabase. De plus, consolidation des versions 2x et 3x en un seul outil. L'outil peut être exécuté depuis ArcGIS Pro ou ArcGIS Desktop.<\/P>Mise à jour 13\/11\/17: <\/STRONG>L'outil prend désormais en charge l'utilisation d'une clause where pour interroger le service.<\/P>Mise à jour 14\/03\/17:<\/STRONG> Mise à jour vers un script unique pour ArcMap\/Pro utilisant le module requests<\/P>Mise à jour 17\/01\/19:<\/STRONG> Merci à Adam Eversole<\/A> d'avoir signalé que la fonctionnalité de cet outil peut désormais être prise en charge par l'outil Feature Class to Feature Class<\/A> d'ArcGIS Pro :<\/P><\/P><\/BODY><\/HTML>
<\/P><\/BODY><\/HTML>
James Crandall can you share the service you are working with to an ArcGIS group and invite my user account (jskinner_CountySandbox)? If so, what is the query you are trying to execute? I'll try setting up the parameters to execute the script with the query.
Hi Jake -- I'm running this as a scheduled task (a . bat executes the .py script), so no Toolbox implementation.
The whereClause is how I posted in my last reply -- I just want to change to only use features from the service after an input date using the CreationDate column. The whereClause works and applied correctly and the script runs most the way thru. It fails when attempting to add attachments and create the match table.
Here's the first whereClause statement(s) setup (whereClause2 is for the date filter, I left the original whereClause the same):
<SPAN class="comment token"># Return largest ObjectID</SPAN> whereClause <SPAN class="operator token">=</SPAN> <SPAN class="string token">'1=1'</SPAN> whereClause2 <SPAN class="operator token">=</SPAN> <SPAN class="string token">"CreationDate>'{}'"</SPAN><SPAN class="punctuation token">.</SPAN>format<SPAN class="punctuation token">(</SPAN>inputD<SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">if</SPAN> whereClause <SPAN class="operator token">==</SPAN> <SPAN class="string token">''</SPAN><SPAN class="punctuation token">:</SPAN> whereClause <SPAN class="operator token">=</SPAN> <SPAN class="string token">'1=1'</SPAN> <SPAN class="comment token">#params = urllib.urlencode({'f': 'pjson', 'where': "CreationDate>'{}'".format(inputDate), 'outFields': '*', 'token': token, 'returnGeometry': 'true'})</SPAN> params <SPAN class="operator token">=</SPAN> <SPAN class="punctuation token">{</SPAN><SPAN class="string token">'where'</SPAN><SPAN class="punctuation token">:</SPAN> whereClause2<SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'returnIdsOnly'</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="string token">'true'</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'token'</SPAN><SPAN class="punctuation token">:</SPAN> token<SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'f'</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="string token">'json'</SPAN><SPAN class="punctuation token">}</SPAN> req <SPAN class="operator token">=</SPAN> urllib2<SPAN class="punctuation token">.</SPAN>Request<SPAN class="punctuation token">(</SPAN>baseURL<SPAN class="punctuation token">,</SPAN> urllib<SPAN class="punctuation token">.</SPAN>urlencode<SPAN class="punctuation token">(</SPAN>params<SPAN class="punctuation token">)</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">print</SPAN> baseURL response <SPAN class="operator token">=</SPAN> urllib2<SPAN class="punctuation token">.</SPAN>urlopen<SPAN class="punctuation token">(</SPAN>req<SPAN class="punctuation token">)</SPAN> data <SPAN class="operator token">=</SPAN> json<SPAN class="punctuation token">.</SPAN>load<SPAN class="punctuation token">(</SPAN>response<SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">try</SPAN><SPAN class="punctuation token">:</SPAN> data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'objectIds'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">.</SPAN>sort<SPAN class="punctuation token">(</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">except</SPAN><SPAN class="punctuation token">:</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>AddError<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"\nURL is incorrect. Or, Service is secure, please enter username and password.\n"</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="comment token">#sys.exit()</SPAN> OIDs <SPAN class="operator token">=</SPAN> data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'objectIds'</SPAN><SPAN class="punctuation token">]</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>AddMessage<SPAN class="punctuation token">(</SPAN>OIDs<SPAN class="punctuation token">)</SPAN> count <SPAN class="operator token">=</SPAN> len<SPAN class="punctuation token">(</SPAN>data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'objectIds'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN> iteration <SPAN class="operator token">=</SPAN> int<SPAN class="punctuation token">(</SPAN>data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'objectIds'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="operator token">-</SPAN><SPAN class="number token">1</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN> minOID <SPAN class="operator token">=</SPAN> int<SPAN class="punctuation token">(</SPAN>data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'objectIds'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="number token">0</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="operator token">-</SPAN> <SPAN class="number token">1</SPAN> OID <SPAN class="operator token">=</SPAN> data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'objectIdFieldName'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="line-numbers-rows"><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN></SPAN>
I get the correct list of OIDs. Also, I can see that it retrieves the attachments & creates replica just fine
It fails in the section
<SPAN class="comment token"># Add Attachments</SPAN> <SPAN class="comment token"># Create Match Table</SPAN> <SPAN class="keyword token">if</SPAN> whereClause <SPAN class="operator token">!=</SPAN> <SPAN class="string token">'1=1'</SPAN><SPAN class="punctuation token">:</SPAN> attachmentGlobalIDs <SPAN class="operator token">=</SPAN> <SPAN class="punctuation token">[</SPAN><SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">for</SPAN> x <SPAN class="keyword token">in</SPAN> data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'layers'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="number token">0</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'features'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">if</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attributes'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN>OID<SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">in</SPAN> OIDs<SPAN class="punctuation token">:</SPAN> attachmentGlobalIDs<SPAN class="punctuation token">.</SPAN>append<SPAN class="punctuation token">(</SPAN>x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attributes'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'GlobalID'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">try</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">for</SPAN> x <SPAN class="keyword token">in</SPAN> data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'layers'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="number token">0</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attachments'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">if</SPAN> whereClause <SPAN class="operator token">!=</SPAN> <SPAN class="string token">'1=1'</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">for</SPAN> attachmentGlobalID <SPAN class="keyword token">in</SPAN> attachmentGlobalIDs<SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">if</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'parentGlobalId'</SPAN><SPAN class="punctuation token">]</SPAN> <SPAN class="operator token">==</SPAN> attachmentGlobalID<SPAN class="punctuation token">:</SPAN> gaUrl <SPAN class="operator token">=</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'url'</SPAN><SPAN class="punctuation token">]</SPAN> gaFolder <SPAN class="operator token">=</SPAN> cwd <SPAN class="operator token">+</SPAN> os<SPAN class="punctuation token">.</SPAN>sep <SPAN class="operator token">+</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'parentGlobalId'</SPAN><SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">if</SPAN> <SPAN class="operator token">not</SPAN> os<SPAN class="punctuation token">.</SPAN>path<SPAN class="punctuation token">.</SPAN>exists<SPAN class="punctuation token">(</SPAN>gaFolder<SPAN class="punctuation token">)</SPAN><SPAN class="punctuation token">:</SPAN> os<SPAN class="punctuation token">.</SPAN>makedirs<SPAN class="punctuation token">(</SPAN>gaFolder<SPAN class="punctuation token">)</SPAN> gaName <SPAN class="operator token">=</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'name'</SPAN><SPAN class="punctuation token">]</SPAN> gaValues <SPAN class="operator token">=</SPAN> <SPAN class="punctuation token">{</SPAN><SPAN class="string token">'token'</SPAN> <SPAN class="punctuation token">:</SPAN> token <SPAN class="punctuation token">}</SPAN> gaData <SPAN class="operator token">=</SPAN> urllib<SPAN class="punctuation token">.</SPAN>urlencode<SPAN class="punctuation token">(</SPAN>gaValues<SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">try</SPAN><SPAN class="punctuation token">:</SPAN> urllib<SPAN class="punctuation token">.</SPAN>urlretrieve<SPAN class="punctuation token">(</SPAN>url<SPAN class="operator token">=</SPAN>gaUrl <SPAN class="operator token">+</SPAN> <SPAN class="string token">'/'</SPAN> <SPAN class="operator token">+</SPAN> gaName<SPAN class="punctuation token">,</SPAN> filename<SPAN class="operator token">=</SPAN>os<SPAN class="punctuation token">.</SPAN>path<SPAN class="punctuation token">.</SPAN>join<SPAN class="punctuation token">(</SPAN>gaFolder<SPAN class="punctuation token">,</SPAN> gaName<SPAN class="punctuation token">)</SPAN><SPAN class="punctuation token">,</SPAN>data<SPAN class="operator token">=</SPAN>gaData<SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">except</SPAN><SPAN class="punctuation token">:</SPAN> PrintException<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"Error Retrieving Attachments"</SPAN><SPAN class="punctuation token">)</SPAN> rows <SPAN class="operator token">=</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>da<SPAN class="punctuation token">.</SPAN>InsertCursor<SPAN class="punctuation token">(</SPAN>fc <SPAN class="operator token">+</SPAN> <SPAN class="string token">"__ATTACH"</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="punctuation token">[</SPAN><SPAN class="string token">"GlobalID_Str"</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">"PhotoPath"</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN> rows<SPAN class="punctuation token">.</SPAN>insertRow<SPAN class="punctuation token">(</SPAN><SPAN class="punctuation token">(</SPAN>x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'parentGlobalId'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">,</SPAN> cwd <SPAN class="operator token">+</SPAN> os<SPAN class="punctuation token">.</SPAN>sep <SPAN class="operator token">+</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'parentGlobalId'</SPAN><SPAN class="punctuation token">]</SPAN> <SPAN class="operator token">+</SPAN> os<SPAN class="punctuation token">.</SPAN>sep <SPAN class="operator token">+</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'name'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">del</SPAN> rows hasrow <SPAN class="operator token">=</SPAN> <SPAN class="token boolean">True</SPAN><SPAN class="line-numbers-rows"><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN></SPAN>
Specifically, it throws an error here
<SPAN class="keyword token">if</SPAN> hasrow <SPAN class="operator token">==</SPAN> <SPAN class="token boolean">True</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">try</SPAN><SPAN class="punctuation token">:</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>AddMessage<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"Adding attachments"</SPAN><SPAN class="punctuation token">)</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>AddAttachments_management<SPAN class="punctuation token">(</SPAN>fc<SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'GlobalID_Str'</SPAN><SPAN class="punctuation token">,</SPAN> fc <SPAN class="operator token">+</SPAN> <SPAN class="string token">'__ATTACH'</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'GlobalID_Str'</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'PhotoPath'</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">except</SPAN><SPAN class="punctuation token">:</SPAN> PrintException<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"Error Retrieving Attachments"</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">try</SPAN><SPAN class="punctuation token">:</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>MakeTableView_management<SPAN class="punctuation token">(</SPAN>fc <SPAN class="operator token">+</SPAN> <SPAN class="string token">'__ATTACH'</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">"tblView"</SPAN><SPAN class="punctuation token">)</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>SelectLayerByAttribute_management<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"tblView"</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">"NEW_SELECTION"</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">"DATA_SIZE = 0"</SPAN><SPAN class="punctuation token">)</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>DeleteRows_management<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"tblView"</SPAN><SPAN class="punctuation token">)</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>DeleteField_management<SPAN class="punctuation token">(</SPAN>fc <SPAN class="operator token">+</SPAN> <SPAN class="string token">'__ATTACH'</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'GlobalID_Str'</SPAN><SPAN class="punctuation token">)</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>DeleteField_management<SPAN class="punctuation token">(</SPAN>fc <SPAN class="operator token">+</SPAN> <SPAN class="string token">'__ATTACH'</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'PhotoPath'</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">except</SPAN> Exception<SPAN class="punctuation token">,</SPAN> e<SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">print</SPAN> <SPAN class="string token">"Error removing empty rows from attachment table"</SPAN> PrintException<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"Error removing empty rows from attachment table"</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="keyword token">pass</SPAN><SPAN class="line-numbers-rows"><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN></SPAN>
The except block throws the print "Error removing empty rows from attachment table".
Jonathan Holt I believe something is corrupt with the attachments. When trying to view them in a Web Map I get a 404 error.
James Crandall I ran the script in PyScripter with the following parameters:
I did not make any changes to anything else within the script and it downloaded the data with attachments successfully.
I get a KeyError: 'GlobalID' on the last line in this block:
<SPAN class="comment token"># Add Attachments</SPAN> <SPAN class="comment token"># Create Match Table</SPAN> <SPAN class="keyword token">if</SPAN> whereClause <SPAN class="operator token">!=</SPAN> <SPAN class="string token">'1=1'</SPAN><SPAN class="punctuation token">:</SPAN> attachmentGlobalIDs <SPAN class="operator token">=</SPAN> <SPAN class="punctuation token">[</SPAN><SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">for</SPAN> x <SPAN class="keyword token">in</SPAN> data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'layers'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="number token">0</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'features'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">print</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attributes'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN>OID<SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">if</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attributes'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN>OID<SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">in</SPAN> OIDs<SPAN class="punctuation token">:</SPAN> attachmentGlobalIDs<SPAN class="punctuation token">.</SPAN>append<SPAN class="punctuation token">(</SPAN>x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attributes'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'GlobalID'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN> <SPAN class="operator token"><</SPAN><SPAN class="operator token">-</SPAN><SPAN class="operator token">-</SPAN>KeyError thrown here <SPAN class="line-numbers-rows"><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN></SPAN>
If you can, share the service to a group and invite my user account (jskinner_CountySandbox). I can try executing the script to see if I receive the same error.
Thanks! Invite to group sent. There's only 1 hosted FS in there.
I'm having the same error KeyError: 'GlobalID' at the same location as James
I get this error when I use a where clause and get attachments.
The tool runs successfully with either a where clause or "get attachments", but throws the error when I try to do both.
The data that I'm trying to download is a hosted feature layer originally from Survey 123
Thanks for that. I should have mentioned the additional detail you provided, it's probably important:
Hosted FS
Source to a Survey123 survey
Attachments
Thanks again!
How would I alter this code if my feature service has related tables?
James Crandall I had to change GlobalID to globalid in the below segment of code:
<SPAN class="comment token"># Add Attachments</SPAN> <SPAN class="comment token"># Create Match Table</SPAN> <SPAN class="keyword token">if</SPAN> whereClause <SPAN class="operator token">!=</SPAN> <SPAN class="string token">'1=1'</SPAN><SPAN class="punctuation token">:</SPAN> attachmentGlobalIDs <SPAN class="operator token">=</SPAN> <SPAN class="punctuation token">[</SPAN><SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">for</SPAN> x <SPAN class="keyword token">in</SPAN> data<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'layers'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="number token">0</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'features'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">if</SPAN> x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attributes'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN>OID<SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">in</SPAN> OIDs<SPAN class="punctuation token">:</SPAN> attachmentGlobalIDs<SPAN class="punctuation token">.</SPAN>append<SPAN class="punctuation token">(</SPAN>x<SPAN class="punctuation token">[</SPAN><SPAN class="string token">'attributes'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'globalid'</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">)</SPAN><SPAN class="line-numbers-rows"><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN></SPAN>
It appears Survey123 uses this field casing for the GlobalID field. There didn't seem to be any attachments, so I added one to OBJECTID 1 and the script executed successfully with the following parameters:
Lianne Scott
Anthony Von Moos this tool will not maintain the relationship class. You can download the related tables by executing the tool for the features, and then again for the table(s). You would need to recreate the relationship class once the data is downloaded.
Hi Jake Skinner, I'm trying to use your lovely tool to download data from a secure ArcGIS Server feature service but I'm getting an error message saying "URL is incorrect. Or, Service is secure, please enter username and password." I've checked the URL and username and password that I'm entering and I'm sure I've entered them correctly because I used the same credentials to view the data in ArcGIS Desktop. Before I got this error message I was getting a different error message, an InsecureRequestWarning saying that an "Unverified HTTPS request is being made." I trust the connection so after some brief investigations I added a couple of lines to the top of your script to disable warnings about the connection being insecure:
from requests.packages.urllib3.exceptions import InsecureRequestWarning
requests.packages.urllib3.disable_warnings(InsecureRequestWarning)
But now I get the message "URL is incorrect. Or, Service is secure, please enter username and password."
I'm now unsure as to what to do next. Are you able to offer any advice about why I'm seeing this message or how I might overcome it?
Mike Steven if your ArcGIS Server instance is not using Windows Authentication, can you private message me on GeoNET with the URL and username/password? I can investigate the issue.
Thanks Jake Skinner. It says that I can only send a message to people that are following me, please can you follow me?
I believe the issue is with how the token is being generated. You do not have administrative access enabled, so you will need to update the portion of the Generate Token code:
<SPAN class="comment token"># Genereate token for AGS feature service</SPAN> <SPAN class="keyword token">if</SPAN> agsService <SPAN class="operator token">==</SPAN> <SPAN class="string token">'true'</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="keyword token">try</SPAN><SPAN class="punctuation token">:</SPAN> arcpy<SPAN class="punctuation token">.</SPAN>AddMessage<SPAN class="punctuation token">(</SPAN><SPAN class="string token">'\nGenerating Token\n'</SPAN><SPAN class="punctuation token">)</SPAN> server <SPAN class="operator token">=</SPAN> baseURL<SPAN class="punctuation token">.</SPAN>split<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"//"</SPAN><SPAN class="punctuation token">)</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="number token">1</SPAN><SPAN class="punctuation token">]</SPAN><SPAN class="punctuation token">.</SPAN>split<SPAN class="punctuation token">(</SPAN><SPAN class="string token">"/"</SPAN><SPAN class="punctuation token">)</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="number token">0</SPAN><SPAN class="punctuation token">]</SPAN> tokenURL <SPAN class="operator token">=</SPAN> <SPAN class="string token"><SPAN>'</SPAN><A class="jive-link-external-small" href="https://community.esri.com/external-link.jspa?url=http%3A%2F%2F" target="_blank">http://</A><SPAN>'</SPAN></SPAN> <SPAN class="operator token">+</SPAN> server <SPAN class="operator token">+</SPAN> <SPAN class="string token">'/arcgis/admin/generateToken'</SPAN> params <SPAN class="operator token">=</SPAN> <SPAN class="punctuation token">{</SPAN><SPAN class="string token">'username'</SPAN><SPAN class="punctuation token">:</SPAN> username<SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'password'</SPAN><SPAN class="punctuation token">:</SPAN> password<SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'client'</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="string token">'requestip'</SPAN><SPAN class="punctuation token">,</SPAN> <SPAN class="string token">'f'</SPAN><SPAN class="punctuation token">:</SPAN> <SPAN class="string token">'pjson'</SPAN><SPAN class="punctuation token">}</SPAN> response <SPAN class="operator token">=</SPAN> requests<SPAN class="punctuation token">.</SPAN>post<SPAN class="punctuation token">(</SPAN>tokenURL<SPAN class="punctuation token">,</SPAN> data <SPAN class="operator token">=</SPAN> params<SPAN class="punctuation token">,</SPAN> verify <SPAN class="operator token">=</SPAN> <SPAN class="token boolean">False</SPAN><SPAN class="punctuation token">)</SPAN> token <SPAN class="operator token">=</SPAN> response<SPAN class="punctuation token">.</SPAN>json<SPAN class="punctuation token">(</SPAN><SPAN class="punctuation token">)</SPAN><SPAN class="punctuation token">[</SPAN><SPAN class="string token">'token'</SPAN><SPAN class="punctuation token">]</SPAN> <SPAN class="keyword token">except</SPAN><SPAN class="punctuation token">:</SPAN> token <SPAN class="operator token">=</SPAN> <SPAN class="string token">''</SPAN> <SPAN class="keyword token">pass</SPAN><SPAN class="line-numbers-rows"><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN></SPAN>
Change the tokenURL in the above to the fully qualified domain name of your ArcGIS Server instance with port 6080. Ex:
tokenURL <SPAN class="operator token">=</SPAN> <SPAN class="string token"><SPAN>'</SPAN><A class="jive-link-external-small" href="https://community.esri.com/external-link.jspa?url=http%3A%2F%2Fags1.esri.com%3A6080%2Farcgis%2Fadmin%2FgenerateToken" target="_blank">http://ags1.esri.com:6080/arcgis/admin/generateToken</A><SPAN>'</SPAN></SPAN><SPAN class="line-numbers-rows"><SPAN></SPAN></SPAN>
Let me know if that works for you.
Thanks for the suggestion, unfortunately it's still showing the same error message. If I change the script to:
tokenURL = 'http://' + server + ':6080/arcgis/admin/generateToken'
It still gives the "URL is incorrect. Or, Service is secure, please enter username and password" message. If I go to that url in a browser, the page times out from taking too long to respond.
Still in a browser if I go to http://<domain>/arcgis/tokens or http://<domain>/arcgis/tokens/generateToken it loads a page that you can generate a token on. But if I then change the script to:
tokenURL = 'http://' + server + '/arcgis/tokens/generateToken'
It still gives the "URL is incorrect. Or, Service is secure, please enter username and password" message.
You will not want to specify the server variable in the URL. This will take the portion of URL that, I believe, is your web server where the web adaptor is installed. You will want to specify the fully qualified domain name of the server where ArcGIS Server is installed. For example, my ArcGIS Server machine is ags1.esri.com, and my web server where the web adaptor is installed is webserver.esri.com. For the URL, the following would not work:
http://webserver.esri.com:6080/arcgis/admin/generateToken
But the following would:
http://ags1.esri.com:6080/arcgis/admin/generateToken
You organization might be enforcing SSL handshakes all of the sudden. With URLib, you'll need to hard code the path to your org's ssl cert.
If I set GetAttachments = 'True' and leave the CWD blank it still downloads the photos to my root directory. Would I have to set the CWD to false for it to stop downloading them to a directory?
Anthony Von Moos the attachments need to be downloaded to a directory if you want them to exist within the feature class. The attachments are downloaded to disk, and then added to the attachment table. The attachments can be deleted from disk afterwards, as they then exist within the attachments table.
If you do not want attachments at all, then you will want to set the getAttachments = 'false'.
Awesome, I was able to get that to work with one of my features. When I try to use that for a table with attachments I get the following error.
Traceback (most recent call last): File "C:\Road Approches\Subgrade_isnp.py", line 663, in <module> if hasrow == True:NameError: name 'hasrow' is not defined
Any ideas?
If I add you to a group could you take a look at my table with attachments I'm trying to download? I have had no luck getting this to work.
Thank you
Apologies Jake Skinner, I wasn't actually putting in the server name (the variable in that part of the script is named 'server' and I was just using that variable name).
I don't know the server name so what I had used in the script was:
http://<domain name>:6080/arcgis/admin/generateToken
but it still gives the same error message. Any ideas why?
Anthony Von Moos this is a bug with table's and attachments. The tool creates a replica of the data, and the bug appears to not retain any attachments when doing so for a table.
One possible workaround would be to use the ArcGIS API for Python. Here is a sample script that will download hosted feature service to a local zip file:
ArcGIS-Python-API-Samples/Backup Hosted Services.ipynb at master · jmirmelstein/ArcGIS-Python-API-Samples · GitHub
Mike Steven if you copy/paste the URL you reference above into a web browser, does it resolve correctly?
Jake Skinner in a web browser if I go to:
http://<domain name>/arcgis/admin/generateToken
then there is a message saying that administrative access has been disabled.
In a web browser if I go to:
http://<domain>:6080/arcgis/tokens or http://<domain>:6080/arcgis/tokens/generateToken
then the browser says that the connection timed out.
In a web browser if I go to the same urls as above but without the :6080, i.e.:
http://<domain>/arcgis/tokens or http://<domain>/arcgis/tokens/generateToken
then it eventually does load a page which would generate a token but it is taking a long time (in the region of 30-60 seconds for the page to load). However putting the same urls into the python script gives the error message about "URL is incorrect...". Is it possible that the problem is with the amount of time it seems to be taking to generate the token?
Do you know how to run a Jupyter notebook on a schedule? I'm looking to run this on a daily basis and can't find a simple way to run my .ipynb on a schedule.
Anthony Von Moos do you have ArcGIS Pro installed? You can have the code in a .py file and run this on the server where Pro is installed. For example, open notepad and add the following lines:
cd "C:\Program Files\ArcGIS\Pro\bin\Python\envs\arcgispro-py3" python "C:\path\to\script.py"<SPAN class="line-numbers-rows"><SPAN></SPAN><SPAN></SPAN><SPAN></SPAN></SPAN>
Save the text file and then rename the extension to .bat. You can use Windows Task Scheduler to execute the bat file on a scheduled basis.
Awesome, Thanks for the info!
Les membres connectés peuvent publier, suivre les mises à jour, et plus encore. Nouveau ici ? Inscrivez-vous gratuitement.
Find useful guides, FAQs, and documents to help you navigate and make the most of Esri Community.