Renaming computers using asset_tag data (API)

Sean_M_Harper
Contributor

I just inherited a JSS one week after a 650 Macbook Air deploy. In this deploy, no machines have been bound or named, but asset tag info was recorded into the JSS (in the asset_tag field). Each of them has the name "Macbook Air" or "User's Macbook Air".

What I need to do:

  1. Rename the devices (both in actuality and in the JSS) using data already stored in the asset_tag field of the JSS record for each machine.

  2. The names need to be changed to the asset tag with “-MAC” after it. An example is: If my asset tag is 12345, my computer name needs to be “12345-MAC”.

I need to be able to run this script in a policy, once against each machine to change its name. Only after this is done can I move forward and begin to bind machines to active directory.

Any assistance would be great, and thanks in advance!

1 ACCEPTED SOLUTION

derivethegeek
New Contributor II

Hello,

After working with Sean_M_Harper for about 30 minutes or so, we were able to come up with this working solution.

#!/bin/bash

MACADDRESS=$(networksetup -getmacaddress en0 | awk '{ print $3 }')
JSS=https://jss.example.com:8443
API_USER=username
API_PASS=password
ASSET_TAG_INFO=$(curl -k $JSS/JSSResource/computers/macaddress/$MACADDRESS --user $API_USER:$API_PASS | cut -d "," -f 12 | cut -d ":" -f 2 | sed 's/"//g')
SERIAL_NUMBER=$(system_profiler SPHardwareDataType | awk '/Serial/ {print $4}')
SUFFIX="-MAC"

if [ -n "$ASSET_TAG_INFO" ]; then
  echo "Processing new name for this client..."
  echo "Changing name..."
  scutil --set HostName "$ASSET_TAG_INFO"$SUFFIX
  scutil --set ComputerName "$ASSET_TAG_INFO"$SUFFIX
  echo "Name change complete. ("$ASSET_TAG_INFO"$SUFFIX)"

else
  echo "Asset Tag information was unavailable. Using Serial Number instead."
  echo "Changing Name..."
  scutil --set HostName $SERIAL_NUMBER$SUFFIX
  echo "Name Change Complete ($SERIAL_NUMBER$SUFFIX)"

fi

Basically, the first 'if' statement will check if the string $ASSET_TAG_INFO is null; if so, proceed to rename with serial number (as to not end up with blank or weird names) and your preferred suffix. If not, continue on and rename with info pulled from the JSS and preferred suffix. Quite simple, actually.

With the flexibility of cut, you can determine any field you would like to pull and perform similar actions for other requests. Either way, hopefully someone will find this helpful in the future.

Regards.

View solution in original post

10 REPLIES 10

derivethegeek
New Contributor II

Hello,

After working with Sean_M_Harper for about 30 minutes or so, we were able to come up with this working solution.

#!/bin/bash

MACADDRESS=$(networksetup -getmacaddress en0 | awk '{ print $3 }')
JSS=https://jss.example.com:8443
API_USER=username
API_PASS=password
ASSET_TAG_INFO=$(curl -k $JSS/JSSResource/computers/macaddress/$MACADDRESS --user $API_USER:$API_PASS | cut -d "," -f 12 | cut -d ":" -f 2 | sed 's/"//g')
SERIAL_NUMBER=$(system_profiler SPHardwareDataType | awk '/Serial/ {print $4}')
SUFFIX="-MAC"

if [ -n "$ASSET_TAG_INFO" ]; then
  echo "Processing new name for this client..."
  echo "Changing name..."
  scutil --set HostName "$ASSET_TAG_INFO"$SUFFIX
  scutil --set ComputerName "$ASSET_TAG_INFO"$SUFFIX
  echo "Name change complete. ("$ASSET_TAG_INFO"$SUFFIX)"

else
  echo "Asset Tag information was unavailable. Using Serial Number instead."
  echo "Changing Name..."
  scutil --set HostName $SERIAL_NUMBER$SUFFIX
  echo "Name Change Complete ($SERIAL_NUMBER$SUFFIX)"

fi

Basically, the first 'if' statement will check if the string $ASSET_TAG_INFO is null; if so, proceed to rename with serial number (as to not end up with blank or weird names) and your preferred suffix. If not, continue on and rename with info pulled from the JSS and preferred suffix. Quite simple, actually.

With the flexibility of cut, you can determine any field you would like to pull and perform similar actions for other requests. Either way, hopefully someone will find this helpful in the future.

Regards.

View solution in original post

Sean_M_Harper
Contributor

Thanks derivethegeek, I appreciate the help! Lets hope this script will help others begin to use the API 🙂

alexjdale
Valued Contributor III

Another option besides cut is xpath, something like:

ASSET_TAG_INFO=$(curl -k $JSS/JSSResource/computers/macaddress/$MACADDRESS --user $API_USER:$API_PASS |  xpath /computer/general/asset_tag | awk '{gsub(/<[^>]*>/,"")};1')

I use xpath because it lets me drill right to the node I need by name, it sounds like cut might be relying on data being on a specific line in the API result every time?

Sean_M_Harper
Contributor

Personally I have never used xpath, but its likely a far more "fool proof" method. I will look into this as a way to enhance this script.

MrP
Contributor III

I did this before I saw ajaxdale's post. Same concept of grabbing the correct value no matter what the position in the results.

ASSET_TAG_INFO=$(curl -k $JSS/JSSResource/computers/macaddress/$MACADDRESS --user $API_USER:$API_PASS  | awk 'BEGIN { FS = "asset_tag" } ; {print $2}'  | awk -F, '{print $1}' | awk 'BEGIN { FS = """ } ; { print $3}')

BrysonTyrrell
Contributor II

If you're extracting a value using xpath you don't need to pipe out to awk of another utility:

ASSET_TAG_INFO=$(curl -k $JSS/JSSResource/computers/macaddress/$MACADDRESS --user $API_USER:$API_PASS |  xpath '/computer/general/asset_tag/text()')

MrP
Contributor III

@brysontyrrell Excellent! Jamf changed the formatting between 9.93 and 9.96 from "," to "<>". I assume it's xml. Anyway what I wrote immediately stopped working after upgrading. Using your line grabs the value perfectly.

wlevan
New Contributor II

Don't mean to hijack this thread but.....Is there an update for the script to do it with Jamf Cloud? I tried and it won't connect.

mwineke
New Contributor

So, for our purposes, we're using the UUID (local) as UDID (Jamf Pro field) for record matching purposes.
This following works, and eliminates xpath (which was erroring out):

assettag=$(curl -k -u "${user}:${pass}" ${jssurl}/JSSResource/computers/udid/${udid} -X GET | awk 'BEGIN { FS = "asset_tag" } ; {print $2}' | cut -f2 -d ">" | cut -f1 -d "<")

Thanks everyone, for all of the data parsing wizardry!

Mauricio
Contributor II

Big Sur has changed the xpath

For an explanation:
https://scriptingosx.com/2020/10/dealing-with-xpath-changes-in-big-sur/

To make this call work

ASSET_TAG_INFO=$(curl -k $JSS/JSSResource/computers/macaddress/$MACADDRESS --user $API_USER:$API_PASS |  xpath '/computer/general/asset_tag/text()')

Change it to

ASSET_TAG_INFO=$(curl -k $JSS/JSSResource/computers/macaddress/$MACADDRESS --user $API_USER:$API_PASS |  xmllint --xpath '/computer/general/asset_tag/text()' -)