Posted on 05-07-2015 08:53 AM
I found a feature request to allow mass-editing computer information, which was marked as "not planned." That's a little disappointing, as it seems a natural thing an administrator would want to do in response to a search result. Oh, well.
In particular, I'd like to find machines of a particular model, or alternatively, those whose PO date is within a particular range. I'd like to mark these items as leased, update the lease expiration date, and add a PO number.
It looks like JAMF's suggestion is to use the API. Has anyone done anything along these lines that would be able to provide their "recipe?"
Solved! Go to Solution.
Posted on 05-07-2015 09:00 AM
@georgecm12 I did not go as far as searching for specific information, I simply used the API to update lease expiration data for all of my machines. I was able to take a CSV file that had the serial number and lease expiration information in it and run it against the API. In turn, all of my machines have lease data now. The discussion we had about this on JAMF Nation is here:
You could adjust the script I used, or the other posted there by @luispalumbo to accomplish some of what you want. If you created a CSV file that held the serial numbers, lease data and PO information, you could update all of your systems, or just the ones that you have info for. Writing these values to a machine that already has these values does no harm that I can tell.
Posted on 05-07-2015 09:00 AM
@georgecm12 I did not go as far as searching for specific information, I simply used the API to update lease expiration data for all of my machines. I was able to take a CSV file that had the serial number and lease expiration information in it and run it against the API. In turn, all of my machines have lease data now. The discussion we had about this on JAMF Nation is here:
You could adjust the script I used, or the other posted there by @luispalumbo to accomplish some of what you want. If you created a CSV file that held the serial numbers, lease data and PO information, you could update all of your systems, or just the ones that you have info for. Writing these values to a machine that already has these values does no harm that I can tell.
Posted on 05-07-2015 10:27 AM
That works, Steve. Looks like newer versions of the API default to JSON output, not XML. As a result, the script as you wrote it doesn't work anymore, but you can send a header that tells the server to send XML instead.
Posted on 05-26-2015 04:44 PM
Would be great if you could do this via an inventory action. I did see a feature request that appears to be alive. It says under review. I just want to be able to find a bunch of machines and then mass update information about purchased vs leased as well as lease start and expiration dates.
The request is here : https://jamfnation.jamfsoftware.com/featureRequest.html?id=545
@stevewood Are you still using your script and API thing ? Works well ? Looks harder than it needs to be.
Posted on 05-27-2015 11:16 AM
@rcorbin yep, that's the method I use. Of course I only have to run it once every few months when I have new leases to put into the JSS. The process isn't really that complicated if you ask me. Gather the lease data into a CSV file, run the script, and you're done.
Posted on 08-22-2017 04:10 PM
I recently had to do this as well - wrote some python to make it happen. You'll need the following things on your machine:
You should be able to just run the script with 'python <script-name> <csv-name>'.
Here's the python:
#!/usr/bin/env python
import sys
import csv
from datetime import datetime
import requests
import argparse
import jamfconfig
parser = argparse.ArgumentParser()
parser.add_argument("leaseList", help="CSV of leased machines")
args = parser.parse_args()
epoch = datetime(1970, 1, 1)
def dictify_csv(csvFile):
'''Import the csv from commandline, turn that into a list of dicts (one per machine).'''
reader = csv.DictReader(open(csvFile, 'r'))
dict_list = []
for row in reader:
dict_list.append(row)
return dict_list
class computer:
def __init__(self, computerDict):
self.serial = computerDict['Serial_num']
if self.serial[0] == "S":
self.serial = self.serial[1:]
self.lease_expires = datetime.strptime(computerDict['End_date'], '%m/%d/%Y')
self.lease_expires_epoch = (self.lease_expires - epoch).total_seconds()
def update_purchase_data(self):
url = jamfconfig.url + '/JSSResource/computers/udid/' + self.udid
payload = ("<computer><purchasing><is_purchased>false</is_purchased><is_leased>true</is_leased><lease_expires_epoch>" + str(int(self.lease_expires_epoch * 1000)) + "</lease_expires_epoch></purchasing></computer>")
b = requests.put(url, auth=(jamfconfig.user, jamfconfig.password), headers={'Accept': 'application/json'}, data=payload, verify=False)
if b.status_code == 201:
print(" Added lease expiration date for " + self.serial)
else:
print("[***] UNABLE TO ADD DATA")
def exists_in_jamf(self):
url = jamfconfig.url + '/JSSResource/computers/match/' + self.serial
b = requests.get(url, auth=(jamfconfig.user, jamfconfig.password), headers={'Accept': 'application/json'}, verify=False)
record = b.json()
if len(record['computers']) == 0:
print(machine.serial + " doesn't exist in jss")
return False
if len(record['computers']) >= 1:
for i in record['computers']:
self.udid = i['udid']
print(self.serial + " exists in jss. Adding leasing data.")
return True
try:
for line in dictify_csv(args.leaseList):
machine = computer(line)
if machine.exists_in_jamf():
machine.update_purchase_data()
except KeyboardInterrupt:
sys.exit()
A note about json/xml - I was originally trying to update the records by sending json, but was always getting a 415 (unsupported media?). Uploading as XML resolved.
Good luck!