Skip to content

Instantly share code, notes, and snippets.

@pdbartsch
Last active April 8, 2022 22:43
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save pdbartsch/c411558133886b47420d8b6350ac87d3 to your computer and use it in GitHub Desktop.
Save pdbartsch/c411558133886b47420d8b6350ac87d3 to your computer and use it in GitHub Desktop.

Overwrite many ArcGIS Web Layers using many maps in a single esri Project file

Step 1: Publish a bunch of web layers to ArcGIS Online or another portal using ArcGIS Pro > Share > Web Layer

Step 2: Become overwhelmed by keeping your data on ArcGIS Online in sync with your local esri maps

Step 3: Automate it

A few notes:

  • This little script asks for user input to choose between two office locations and then update the path to the esri project file
  • Uses stored credentials to keep my ArcGIS Online password separate from this code
  • It helps to have the web feature name match the name of your local map
  • I had one issue where my "Storm" map kept thinking I wanted it to overwrite a "ChilledWater" feature because the Chilled water service definition file had the word storm somewhere in the metadata.
  • ...so now it checks the name before overwriting
  • This code could be a lot more robust by adding some exception handling
  • This code could also be more succinct and applicable to multiple project files by creating a list of maps from a project file, but for now this works great for my use case
  • I'm using ArcGIS Pro. For the ArcMap mxd approach see: https://github.com/pdbartsch/update-hosted-feature-service
  • I definitely borrowed code from the following references

References:

https://www.esri.com/arcgis-blog/products/analytics/analytics/updating-your-hosted-feature-services-with-arcgis-pro-and-the-arcgis-api-for-python/ https://github.com/polanch190/Overwrite-a-Feature-Layers-ArcGIS-API-for-Python https://community.esri.com/t5/python-questions/automate-overwrite-web-layer-feature-class/td-p/20067 https://learn.arcgis.com/en/projects/schedule-automated-near-real-time-data-updates/ https://pro.arcgis.com/en/pro-app/latest/help/sharing/overview/overwrite-a-web-layer.htm

import arcpy
import os, sys
from arcgis.gis import GIS
# set path based on which office I'm working at that day
office = input("Please select office location: 1)UCSB or 2)Home Office [1/2]? : ")
if office == "1":
# UCSB office paths
prjPath = r"G:\\GIS_Projects\\web\\utilities\\utilities_web_update.aprx"
elif office == "2":
# home office paths
prjPath = r"D:\\UCSB_Data\\web\\utilities\\utilities_web_update\\utilities_web_update.aprx"
# login credentials
# password from locally stored profile
# setup by
# from arcgis.gis import GIS
# GIS(profile = 'learn_user', password = 'areallygoodpassword')
user = "pdbar"
portal = "https://ucsb.maps.arcgis.com"
gis = GIS(profile="learn_user")
# not currently using the ID but I may in the future if errors continue to
# arise from finding the wrong map file on agol
mapList = [
["atlas_index", True, True, "UCSB DFSS", "c7810fc2256b4f4b95aa53d6df276e63"],
["ChilledWater", False, False, "UCSB DFSS", "2f07cee025034e38bf2cc4fc0ff943b4"],
["Electricity", False, False, "UCSB DFSS", "4f8eaeba6153496fb26b5188b7185de4"],
["NaturalGas", False, False, "UCSB DFSS", "f7ede31bfcb845b9a41bbfcaf5abc654"],
["PotableWater", False, False, "UCSB DFSS", "3f8fd607663d4be1ab3e06a4ecb23379"],
["ReclaimedWater", False, False, "UCSB DFSS", "0b8dd79a41244e66aa6f97c7fd2ff75e"],
["SeaWater", False, False, "UCSB DFSS", "62c0c6ffaeac464fada6f8600dc081b7"],
["Sewer", False, False, "UCSB DFSS", "5b57472ccc154aca877be20cb2a1e825"],
["Storm", False, False, "UCSB DFSS", "ad4d775128e0486e910f8c5d5501e5e1"],
["Telecom", False, False, "UCSB DFSS", "cabc73190433448db7a3e52f95e2f704"],
[
"UCSB Solar Arrays",
False,
False,
"UCSB DFSS",
"b9cf4141bb6144289f739c2161f4eb2d",
],
["UCSB_Light_Poles", False, False, "UCSB DFSS", "b65dc6e55dcc41379159231a0c942a8c"],
]
def update_fs():
# Local paths to create temporary content
relPath = sys.path[0]
sddraft = os.path.join(relPath, "WebUpdate.sddraft")
sd = os.path.join(relPath, "WebUpdate.sd")
# Create a new SDDraft and stage to SD
print("Creating SD file")
arcpy.env.overwriteOutput = True
prj = arcpy.mp.ArcGISProject(prjPath)
# finds map in local aprx file that matches name given
mp = prj.listMaps(sd_fs_name)[0]
arcpy.mp.CreateWebLayerSDDraft(
mp, sddraft, sd_fs_name, "MY_HOSTED_SERVICES", "FEATURE_ACCESS", "", True, True
)
arcpy.StageService_server(sddraft, sd)
# Connect to your AGO portal
print("Connecting to {}".format(portal))
# Find the SD, update it, publish /w overwrite and set sharing and metadata
print("Search for " + sd_fs_name + " SD on portal…")
sdItem = gis.content.search(
"{} AND owner:{}".format(sd_fs_name, user), item_type="Service Definition"
)[0]
# check to see if names match before overwriting
if sdItem.title == sd_fs_name:
print(
"Found SD: {}, ID: {} Uploading and overwriting…".format(
sdItem.title, sdItem.id
)
)
sdItem.update(data=sd)
print("Overwriting existing feature service…")
fs = sdItem.publish(overwrite=True)
if shrOrg or shrEveryone or shrGroups:
print("Setting sharing options…")
fs.share(org=shrOrg, everyone=shrEveryone, groups=shrGroups)
print("Finished updating: {} – ID: {}".format(fs.title, fs.id), "\n")
else:
print("passing")
print(sd_fs_name, ": ", sdItem.title, " did not match")
pass
# loop through list of maps, set variables and run the main function
x = range(len(mapList))
for n in x:
l = mapList[n]
sd_fs_name = l[0]
shrOrg = l[1]
shrEveryone = l[2]
shrGroups = l[3]
update_fs()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment