Skip to main content
Solved

Enable Lost Mode - API Question


jbisgett
Forum|alt.badge.img+12

I’m trying to enable lost mode and play sound on a group of iPads. I’ve found a way to enable lost mode, but I can’t figure out how to also send play sound command.

xmlData="<mobile_device_command>
<general>
<command>EnableLostMode</command>
<lost_mode_message>$lostModeMsg</lost_mode_message>
<lost_mode_phone>$lostModePhone</lost_mode_phone> 
</general>
<mobile_devices> 
   <mobile_device>
      <id>$i</id> 
   </mobile_device>
</mobile_devices>
</mobile_device_command>

See here for full script: https://gist.github.com/talkingmoose/f44d0d87d08b48daa0e887a6239c1766

Best answer by jbisgett

For those in need or interested, JAMF support responded to my ticket regarding this and provided this information to make it work:

Update the xml <general> section of the script I was using with the information below.

<general>
        <command>EnableLostMode</command>
        <lost_mode_message>$lostModeMsg</lost_mode_message>
        <lost_mode_phone>$lostModePhone</lost_mode_phone>
        <lost_mode_footnote>$lostModeFootnote</lost_mode_footnote>
        <always_enforce_lost_mode>true</always_enforce_lost_mode>
        <lost_mode_with_sound>true</lost_mode_with_sound>
    </general>

Info from support:
It appears the enforce lost mode and play lost mode sound options are actually parameters of the EnableLostMode command. These two options are detailed in the API page at the same level as the message, phone number, and footnote which is why we place them where they are and their corresponding descriptions are below:

always_enforce_lost_mode - 'false' if the lost mode is NOT to be re-enabled after the device is wiped and re-enrolled. Defaults to 'true'.
lost_mode_with_sound - 'true' if the device is to play a loud sound while the lost mode is enabled. Defaults to 'false'.

View original
Did this topic help you find an answer to your question?

8 replies

jbisgett
Forum|alt.badge.img+12
  • Author
  • Honored Contributor
  • 107 replies
  • June 10, 2020

I would also like to know how to include the Always Force Lost Mode command.


jbisgett
Forum|alt.badge.img+12
  • Author
  • Honored Contributor
  • 107 replies
  • Answer
  • June 10, 2020

For those in need or interested, JAMF support responded to my ticket regarding this and provided this information to make it work:

Update the xml <general> section of the script I was using with the information below.

<general>
        <command>EnableLostMode</command>
        <lost_mode_message>$lostModeMsg</lost_mode_message>
        <lost_mode_phone>$lostModePhone</lost_mode_phone>
        <lost_mode_footnote>$lostModeFootnote</lost_mode_footnote>
        <always_enforce_lost_mode>true</always_enforce_lost_mode>
        <lost_mode_with_sound>true</lost_mode_with_sound>
    </general>

Info from support:
It appears the enforce lost mode and play lost mode sound options are actually parameters of the EnableLostMode command. These two options are detailed in the API page at the same level as the message, phone number, and footnote which is why we place them where they are and their corresponding descriptions are below:

always_enforce_lost_mode - 'false' if the lost mode is NOT to be re-enabled after the device is wiped and re-enrolled. Defaults to 'true'.
lost_mode_with_sound - 'true' if the device is to play a loud sound while the lost mode is enabled. Defaults to 'false'.


Forum|alt.badge.img+1
  • New Contributor
  • 1 reply
  • March 24, 2021

To follow up on this, Big Sur changed the xpath version, which breaks the script linked above. There are a few possible fixes. I chose to follow Armin Briegel's example and just declare a local function named xpath that checks the OS version and parses as needed.

Here's my update that works as of Big Sur 11.1: gist. Note that I did not include the play sound option, nor the enforce lost mode (because it defaults to true) but you can obviously add them if desired.


Forum|alt.badge.img+5
  • Contributor
  • 56 replies
  • November 11, 2021

I've been playing around with this script and it seems promising.  I'm using this script with no changes made other than the "EDIT ME" section where you specify the lostModeMsg, lostModePhone, and lostModeFootnote.  

The issue I'm running into is with the device list.  I have a list of serial numbers where each serial is on a new line, no space, no commas.  When I run the script I get the error:

no element found at line 1, column 0, byte 0: ^ at /System/Library/Perl/Extras/5.18/darwin-thread-multi-2level/XML/Parser.pm line 187.

 

If I edit the device list and remove all but 1 serial number it works great.  As soon as I add more than 1 serial I'm back to the error above.  I've tested this on Catalina, Big Sur, and Monterey...what am I missing? 


Forum|alt.badge.img+5
  • Contributor
  • 56 replies
  • November 12, 2021

I figured out the issue:  the original script is using the wrong header information.

Instead of

--header "Accept: text/xml" \\ and --header "Content-Type: text/xml" \\

both headers should read:

--header "Accept: application/xml" \\ and --header "Content-Type: application/xml" \\

 


jbisgett
Forum|alt.badge.img+12
  • Author
  • Honored Contributor
  • 107 replies
  • October 17, 2022

I've updated this script to use bearer tokens, Jamf Policy variables, and pull device ids from a Mobile Device group instead of a csv. The api user will need read access to Mobile Device Smart Groups and Mobile Device Static groups, depending on which type of group the devices are in.

 

#!/bin/bash # Based on script written by talkingmoose # https://gist.github.com/talkingmoose/f44d0d87d08b48daa0e887a6239c1766 ############################### ## Declare Variables ############################### # Server connection information jssURL=${4} jssUser=${5} jssPass=${6} # Mobile Device groupID deviceGroupID=${7} # Lost Mode messaging lostModeMsg=${8} lostModePhone=${9} lostModeFootnote=${10} ############################### ## Don't Edit Below Here ############################### # Request Auth Token - valid for 30 minutes authToken=$( /usr/bin/curl \\ --request POST \\ --silent \\ --url "$jssURL/api/v1/auth/token" \\ --user "$jssUser:$jssPass" ) # Parse Auth Token token=$( /usr/bin/plutil \\ -extract token raw - <<< "$authToken" ) tokenExpiration=$( /usr/bin/plutil \\ -extract expires raw - <<< "$authToken" ) localTokenExpirationEpoch=$( TZ=GMT /bin/date -j \\ -f "%Y-%m-%dT%T" "$tokenExpiration" \\ +"%s" 2> /dev/null ) # Subtract five minutes (300 seconds) from localTokenExpirationEpoch renewalTime=$(( $localTokenExpirationEpoch - 300 )) renewToken() { # renew auth token authToken=$( /usr/bin/curl \\ --header "Accept: application/json" \\ --header "Authorization: Bearer $token" \\ --request POST \\ --silent \\ --url "$jssURL/api/v1/auth/keep-alive" ) # parse auth token token=$( /usr/bin/plutil \\ -extract token raw - <<< "$authToken" ) tokenExpiration=$( /usr/bin/plutil \\ -extract expires raw - <<< "$authToken" ) localTokenExpirationEpoch=$( TZ=GMT /bin/date -j \\ -f "%Y-%m-%dT%T" "$tokenExpiration" \\ +"%s" 2> /dev/null ) # update the renewal time for another 25 minutes renewalTime=$(( $localTokenExpirationEpoch - 300 )) } # Make an API call to retrieve a list of device IDs from the group deviceList=$( /usr/bin/curl \\ --header "Accept: application/xml" \\ --header "Authorization: Bearer $token" \\ --request GET \\ --silent \\ --url "$jssURL/JSSResource/mobiledevicegroups/id/$deviceGroupID" | xmllint --format - 2>/dev/null | awk -F'>|<' '/<id>/{print $3}' | sed 1,2d ) # Loop through the device IDs and send an EnableLostMode command to Jamf via the API for deviceID in $deviceList; do # If renewaltime is less than current time, renew auth token now=$( /bin/date +"%s" ) if [[ "$renewalTime" -lt "$now" ]]; then renewToken fi # Log command execution logTime=$(date "+%Y-%m-%d - %H:%M:%S:") echo "$logTime Sending EnableLostMode command to device $deviceID..." # Construct EnableLostMode API command xmlData="<mobile_device_command> <general> <command>EnableLostMode</command> <lost_mode_message>$lostModeMsg</lost_mode_message> <lost_mode_phone>$lostModePhone</lost_mode_phone> <lost_mode_footnote>$lostModeFootnote</lost_mode_footnote> <always_enforce_lost_mode>true</always_enforce_lost_mode> <lost_mode_with_sound>true</lost_mode_with_sound> </general> <mobile_devices> <mobile_device> <id>$deviceID</id> </mobile_device> </mobile_devices> </mobile_device_command>" # flattened XML flatXML=$( /usr/bin/xmllint --noblanks - <<< "$xmlData" ) # Send EnableLostMode command /usr/bin/curl \\ --header "Authorization: Bearer $token" \\ --request POST \\ --silent \\ --header "Content-Type: application/xml" \\ --url "$jssURL/JSSResource/mobiledevicecommands/command/EnableLostMode" -d "$flatXML" done # expire auth token /usr/bin/curl \\ --header "Authorization: Bearer $token" \\ --request POST \\ --silent \\ --url "$jssURL/api/v1/auth/invalidate-token" exit 0

mvu
Forum|alt.badge.img+20
  • Jamf Heroes
  • 878 replies
  • February 14, 2023
jbisgett wrote:

I've updated this script to use bearer tokens, Jamf Policy variables, and pull device ids from a Mobile Device group instead of a csv. The api user will need read access to Mobile Device Smart Groups and Mobile Device Static groups, depending on which type of group the devices are in.

 

#!/bin/bash # Based on script written by talkingmoose # https://gist.github.com/talkingmoose/f44d0d87d08b48daa0e887a6239c1766 ############################### ## Declare Variables ############################### # Server connection information jssURL=${4} jssUser=${5} jssPass=${6} # Mobile Device groupID deviceGroupID=${7} # Lost Mode messaging lostModeMsg=${8} lostModePhone=${9} lostModeFootnote=${10} ############################### ## Don't Edit Below Here ############################### # Request Auth Token - valid for 30 minutes authToken=$( /usr/bin/curl \\ --request POST \\ --silent \\ --url "$jssURL/api/v1/auth/token" \\ --user "$jssUser:$jssPass" ) # Parse Auth Token token=$( /usr/bin/plutil \\ -extract token raw - <<< "$authToken" ) tokenExpiration=$( /usr/bin/plutil \\ -extract expires raw - <<< "$authToken" ) localTokenExpirationEpoch=$( TZ=GMT /bin/date -j \\ -f "%Y-%m-%dT%T" "$tokenExpiration" \\ +"%s" 2> /dev/null ) # Subtract five minutes (300 seconds) from localTokenExpirationEpoch renewalTime=$(( $localTokenExpirationEpoch - 300 )) renewToken() { # renew auth token authToken=$( /usr/bin/curl \\ --header "Accept: application/json" \\ --header "Authorization: Bearer $token" \\ --request POST \\ --silent \\ --url "$jssURL/api/v1/auth/keep-alive" ) # parse auth token token=$( /usr/bin/plutil \\ -extract token raw - <<< "$authToken" ) tokenExpiration=$( /usr/bin/plutil \\ -extract expires raw - <<< "$authToken" ) localTokenExpirationEpoch=$( TZ=GMT /bin/date -j \\ -f "%Y-%m-%dT%T" "$tokenExpiration" \\ +"%s" 2> /dev/null ) # update the renewal time for another 25 minutes renewalTime=$(( $localTokenExpirationEpoch - 300 )) } # Make an API call to retrieve a list of device IDs from the group deviceList=$( /usr/bin/curl \\ --header "Accept: application/xml" \\ --header "Authorization: Bearer $token" \\ --request GET \\ --silent \\ --url "$jssURL/JSSResource/mobiledevicegroups/id/$deviceGroupID" | xmllint --format - 2>/dev/null | awk -F'>|<' '/<id>/{print $3}' | sed 1,2d ) # Loop through the device IDs and send an EnableLostMode command to Jamf via the API for deviceID in $deviceList; do # If renewaltime is less than current time, renew auth token now=$( /bin/date +"%s" ) if [[ "$renewalTime" -lt "$now" ]]; then renewToken fi # Log command execution logTime=$(date "+%Y-%m-%d - %H:%M:%S:") echo "$logTime Sending EnableLostMode command to device $deviceID..." # Construct EnableLostMode API command xmlData="<mobile_device_command> <general> <command>EnableLostMode</command> <lost_mode_message>$lostModeMsg</lost_mode_message> <lost_mode_phone>$lostModePhone</lost_mode_phone> <lost_mode_footnote>$lostModeFootnote</lost_mode_footnote> <always_enforce_lost_mode>true</always_enforce_lost_mode> <lost_mode_with_sound>true</lost_mode_with_sound> </general> <mobile_devices> <mobile_device> <id>$deviceID</id> </mobile_device> </mobile_devices> </mobile_device_command>" # flattened XML flatXML=$( /usr/bin/xmllint --noblanks - <<< "$xmlData" ) # Send EnableLostMode command /usr/bin/curl \\ --header "Authorization: Bearer $token" \\ --request POST \\ --silent \\ --header "Content-Type: application/xml" \\ --url "$jssURL/JSSResource/mobiledevicecommands/command/EnableLostMode" -d "$flatXML" done # expire auth token /usr/bin/curl \\ --header "Authorization: Bearer $token" \\ --request POST \\ --silent \\ --url "$jssURL/api/v1/auth/invalidate-token" exit 0

Hi @jbisgett 

 

Trying to give this a shot. New to API stuff. Once you declare your variables, how do you execute this API script? Probably a dumb question, but I'm learning.


mvu
Forum|alt.badge.img+20
  • Jamf Heroes
  • 878 replies
  • February 17, 2023
mvu wrote:

Hi @jbisgett 

 

Trying to give this a shot. New to API stuff. Once you declare your variables, how do you execute this API script? Probably a dumb question, but I'm learning.


For others in need, the script below worked. Make sure the jss api user account permissions are correct. Ended up needing 5 boxes checked off.

https://github.com/robjschroeder/Jamf-API-Scripts/blob/main/api-EnableLostMode-MobileDeviceGroup.sh

Thank you Jamf and shout out to Kristen B!


Reply


Cookie policy

We use cookies to enhance and personalize your experience. If you accept you agree to our full cookie policy. Learn more about our cookies.

 
Cookie settings