Is there a way to stop and start a map/feature service in ArcGIS Server via python?
Solved! Go to Solution.
Lots of useful info has already been posted, it can just be a chore to sort through it to get exactly what you need. This is compounded by the fact that there are always many different ways to do the same thing and makes it extra confusing. Here is the Python code I use to start/stop a single service. It uses all built-in modules so there's no need to install anything extra.
"""Based on these 2014 resources by Kevin Hibma (Product Engineer at Esri):
ArcGIS Server Administration Toolkit - 10.1+
http://www.arcgis.com/home/item.html?id=12dde73e0e784e47818162b4d41ee340
AdministeringArcGISServerwithPython_DS2014
https://github.com/arcpy/AdministeringArcGISServerwithPython_DS2014
Other related information can be found in the ArcGIS Help Resources
Scripting with the ArcGIS REST API
http://resources.arcgis.com/en/help/main/10.2/0154/0154000005r1000000.htm
"""
# Required imports
import urllib
import urllib2
import json
import contextlib ## context manager to clean up resources when exiting a 'with' block
def main(): ## Entry point into the script
# Local variables
## Authentication
adminUser = r"someuser"
adminPass = r"passw0rd"
## ArcGIS Server Machine
server = "SERVERNAME"
port = "6080"
## Services ("FolderName/ServiceName.ServiceType")
svc = "SampleWorldCities.MapServer"
try:
# Get ArcGIS Server token
expiration = 60 ## Token timeout in minutes; default is 60 minutes.
token = getToken(adminUser, adminPass, server, port, expiration)
# Perform action on service
action = "start" ## "start" or "stop"
jsonOuput = serviceStartStop(server, port, svc, action, token)
## Validate JSON object result
if jsonOuput['status'] == "success":
print "{} {} successful".format(action.title(), str(svc))
else:
print "Failed to {} {}".format(action, str(svc))
raise Exception(jsonOuput)
except Exception, err:
print err
# Function to generate a token from ArcGIS Server; returns token.
## http://resources.arcgis.com/en/help/arcgis-rest-api/02r3/02r3000000m5000000.htm
def getToken(adminUser, adminPass, server, port, expiration):
# Build URL
url = "http://{}:{}/arcgis/admin/generateToken?f=json".format(server, port)
# Encode the query string
query_dict = {
'username': adminUser,
'password': adminPass,
'expiration': str(expiration), ## Token timeout in minutes; default is 60 minutes.
'client': 'requestip'
}
query_string = urllib.urlencode(query_dict)
try:
# Request the token
with contextlib.closing(urllib2.urlopen(url, query_string)) as jsonResponse:
getTokenResult = json.loads(jsonResponse.read())
## Validate result
if "token" not in getTokenResult or getTokenResult == None:
raise Exception("Failed to get token: {}".format(getTokenResult['messages']))
else:
return getTokenResult['token']
except urllib2.URLError, e:
raise Exception("Could not connect to machine {} on port {}\n{}".format(server, port, e))
# Function to start or stop a service on ArcGIS Server; returns JSON response.
## http://resources.arcgis.com/en/help/arcgis-rest-api/02r3/02r3000001s6000000.htm
def serviceStartStop(server, port, svc, action, token):
# Build URL
url = "http://{}:{}/arcgis/admin".format(server, port)
requestURL = url + "/services/{}/{}".format(svc, action)
# Encode the query string
query_dict = {
"token": token,
"f": "json"
}
query_string = urllib.urlencode(query_dict)
# Send the server request and return the JSON response
with contextlib.closing(urllib.urlopen(requestURL, query_string)) as jsonResponse:
return json.loads(jsonResponse.read())
if __name__ == '__main__':
main()
NOTE: I am trying to do this from a different server from where AGS is installed.
I have to stop a service to run some code on the FC in SDe. Then restart the Service.
Can I call a python script on another server?
Can I do this via arcpy?
yes.
The "released" version of the toolbox is
Downloadable tools for ArcGIS Server administration | ArcGIS Blog
direct link to download page... http://www.arcgis.com/home/item.html?id=12dde73e0e784e47818162b4d41ee340
Might want to look at this thread too
I have done some additional work on a copy locally that reads the credentials from a .ini file so it doesn't echo the admin credentials in the results tab. Also, I know Kevin Hibma is working on a new version, but haven't heard any release date (I think it's a, "as I have time" project)
edit: btw, my modified toolset allows me to search the running services that are using a datasource so I shut down all those. Then I totally replace the fgdb before starting those services back up. I will eventually post it, but not ready yet.
Was looking into the AGS Admin link...saw the below.
Not sure where to download all the scripts and stuff from the Zip file too?
Can I specify a single Service?
Pretty confused right now.....
def stopStartServices(server, port, adminUser, adminPass, stopStart, serviceList, token=None):
''' Function to stop, start or delete a service.
Requires Admin user/password, as well as server and port (necessary to construct token if one does not exist).
stopStart = Stop|Start|Delete
serviceList = List of services. A service must be in the <name>.<type> notation
If a token exists, you can pass one in for use.
'''
# Get and set the token
if token is None:
token = gentoken(server, port, adminUser, adminPass)
# modify the services(s)
for service in serviceList:
op_service_url = "http://{}:{}/arcgis/admin/services/{}/{}?token={}&f=json".format(server, port, service, stopStart, token)
status = urllib2.urlopen(op_service_url, ' ').read()
if 'success' in status:
print (str(service) + " === " + str(stopStart))
else:
print status
return
If you download that admin toolbox, use the tool. One you put in your server name port (usually 6080) and admin credentials, it should list ALL the services, where running or not. That is why I'm modifying it. Cause otherwise when you rerun it to start the services back up, it will include anything your checked to "stop" whether or not is was running before.
That might not make sense, but just run it so you get the GUI, and it should make more sense.
my modified toolset allows me to search the running services that are using a datasource so I shut down all those. Then I totally replace the fgdb before starting those services back up. I will eventually post it, but not ready yet.
Looking forward to that!
Blake, if you get anxious and want to take a look at my scripts, DM me. The issue is I'm writeing/testing for an internal addin and I have too much hardcoded (i.e. my .fgdb for example) for use in this addin. But the functionality is there and working. For GP services it actually has to read from the manifest.json for the service on the c: drive to see if it is being used. Some of these things I still need to pull out to be separate functions....but off that project for a couple weeks right now.
So I only need one line of code?
http://server:port/arcgis/admin/services/Maps/SeattleMap.MapServer/start
What about credentials etc. and the 100 lines of code in the previous posts.
Hi Jay
Not quite that simple. You will have to generate a token and pass that as part of the request. Are you familiar with making http/https requests with python? Have a look at the request module. If I have time today I will put together an example script.
cheers
Callum