Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
delete_jamf_remote_policies.py
#!/usr/bin/python
import base64
import urllib2
import re
from time import time
import xml.etree.ElementTree as etree
from CoreFoundation import CFPreferencesCopyAppValue # pylint: disable=no-name-in-module
def read_jamf_api_creds():
'''Reads Jamf credentials from a stored preference file.'''
pref_domains = ['com.github.autopkg', 'com.yourcompany.jamf']
jss_url = jss_usr = jss_pwd = None
for domain in pref_domains:
jss_url = CFPreferencesCopyAppValue('JSS_URL', domain)
jss_usr = CFPreferencesCopyAppValue('API_USERNAME', domain)
jss_pwd = CFPreferencesCopyAppValue('API_PASSWORD', domain)
if all((jss_url, jss_usr, jss_pwd)):
break
if not all((jss_url, jss_usr, jss_pwd)):
print ('[ERROR] Please check to make sure your Jamf credentials are '
'stored in the designated preference(s): {}'.format(pref_domains))
exit(1)
return jss_url, base64.b64encode(jss_usr + ':' + jss_pwd)
def jamf_api_call(url, credentials, method='', data=None):
'''Makes a Jamf API call.'''
request = urllib2.Request(url)
request.add_header('Authorization', 'Basic ' + credentials)
if method.upper() in ('POST', 'PUT', 'DELETE'):
request.get_method = lambda: method
if method.upper() in ('POST', 'PUT') and data is not None:
request.add_header('Content-Type', 'application/xml')
return urllib2.urlopen(request, data)
request.add_header('Accept', 'application/xml')
return urllib2.urlopen(request)
def main():
'''Main function.'''
# Get Jamf credentials.
jss_url, credentials = read_jamf_api_creds()
# Set name pattern for Jamf Remote policies.
policy_name_pattern = r'[\d\-]+ at [\d:]+ (A|P)M \| [\w\.@]+ \| [\d]+ Computers?'
# Get names and IDs of all policies.
url = '{}/JSSResource/policies'.format(jss_url)
response = jamf_api_call(url, credentials)
policies_xml = etree.fromstring(response.read())
policies = policies_xml.findall('policy')
print 'Found {} total Jamf policies.'.format(len(policies))
# Iterate through policies and remove the ones that match the Jamf Remote naming pattern.
for policy in policies:
rmatch = re.search(policy_name_pattern, policy.find('name').text)
if rmatch:
try:
print 'Removing policy ID {}: "{}"...'.format(
policy.find('id').text,
policy.find('name').text),
url = '{}/JSSResource/policies/id/{}'.format(jss_url, policy.find('id').text)
start_time = time()
response = jamf_api_call(url, credentials, 'DELETE')
end_time = time()
print 'Completed in {:0.2f} seconds.'.format(end_time - start_time)
except urllib2.HTTPError as err:
print 'HTTP error:', err.code
except KeyboardInterrupt:
print '\nReceived Control-C, stopping now.'
break
if __name__ == '__main__':
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.