Question about: Bring Lost Sheep Back to the Flock - Using Automation to Manage Your Fleet

bcbackes
Contributor III

Did anyone attend the "Interactive Lab: Bring Lost Sheep Back to the Flock - Using Automation to Manage Your Fleet" session? If you have did you try out the script to see if it works?

 

I tried it on a test Mac but I don't see it populating the Jamf Management Framework even though the script says it completed successfully. Not sure what I'm missing here. I tried the original script posted in the session. NOTE: There is a typo in the beginning of the script 😉. Not sure how to get ahold of the speaker to have it updated. 
Says: #!/bih/bash

Should say: #!/bin/bash

 

Note: Some people were asking about a way to encrypt the generic Jamf Pro user account you have to create for this process so it doesn't show in clear text in the script. I followed the process used here to encrypt the password. Start at Step 3. I started with using Parameter 5 and left out the "Log Files" parameter. FYI, I did try the script as is to rule out changes I did but I had the same result - script finished successfully but no change on the test Mac.

 

1 ACCEPTED SOLUTION

bcbackes
Contributor III

Update: I found the issue where the script wasn't working. For that device record Management tab I noticed there were some pending commands. I cleared those out and reran the script and it worked as designed. 

 

Put a post below but adding it here too for visibility:

Warning: 

In further testing I found that if you have the Mac scoped to any policies set with frequency as "Ongoing" and using an "Enrollment" trigger it will rerun that policy. I had to update a couple of my prestage enrollment policies from "Ongoing" to "Once per computer". 

The reason for this is part of the process for getting the Jamf Management Framework back on the Mac is it enrolls the device. You can see this happening if you are in the "/usr/local/jamf/bin" folder. You will see "enroll" and "jamf" both show up and then the "enroll" will disappear after a few seconds when the process is completed.

View solution in original post

31 REPLIES 31

Justin496
New Contributor

Much appreciated so a phenomenal plan, your thought worked for me.

CFAHome

@Justin496 Did the script work for you? Did it actually restore the Jamf Management Framework? I wasn't having any luck with that part.

bcbackes
Contributor III

Update: I found the issue where the script wasn't working. For that device record Management tab I noticed there were some pending commands. I cleared those out and reran the script and it worked as designed. 

 

Put a post below but adding it here too for visibility:

Warning: 

In further testing I found that if you have the Mac scoped to any policies set with frequency as "Ongoing" and using an "Enrollment" trigger it will rerun that policy. I had to update a couple of my prestage enrollment policies from "Ongoing" to "Once per computer". 

The reason for this is part of the process for getting the Jamf Management Framework back on the Mac is it enrolls the device. You can see this happening if you are in the "/usr/local/jamf/bin" folder. You will see "enroll" and "jamf" both show up and then the "enroll" will disappear after a few seconds when the process is completed.

ZachH
New Contributor II
New Contributor II

Thanks for pointing out the typo! We're working on getting the link to the script updated with a fixed version.

Glad you got the rest figured out! The script relies on an MDM command to refresh the Jamf management framework and as you discovered if there are MDM commands "stuck in the pipe" so to speak, that command will get stuck behind them. Good troubleshooting!

ZachH
New Contributor II
New Contributor II

The script has been updated on the Bring Lost Sheep Back page with the typo fixed, thanks for letting us know!

bizzaredm
Contributor

Would love to see that!

triding
New Contributor III

Where is the "Bring Lost Sheep Back" page please? :-)

bcbackes
Contributor III

Here's a link to the session.

 

I should note that I've tested this on a couple of Macs. While it worked on one there is another that it didn't work on. Management tab reports "InstallApplication" failed. That Mac is on an older Jamf Binary and is not checking in or doing inventory updates but it is online. I was going to try removing the framework and test again but I have an active case open with Jamf in regards to devices like this and I'm waiting for their response after I mentioned this particular session and the success I had on the other device before I start messing around.

ZachH
New Contributor II
New Contributor II

I suppose it's possible that if those devices haven't updated in a while they may not be able to receive the refresh framework command. Though I'm not 100% sure on the requirements for that command to work. 

bcbackes
Contributor III

Yeah, I'm not sure if it's an issue with the binary version or not. The Mac is running 10.38.3 and my Cloud environment is on 10.41. I'll wait to see what Jamf Support says and if nothing else I'll try removing the existing framework and try the script again. Even if it only works on some devices it's better than what I have now.😉

triding
New Contributor III

Loved the interactive lab thanks, is there any link to get the script from at all?

ZachH
New Contributor II
New Contributor II

The link to the script can be found on the page for that lab: https://reg.jamf.com/flow/jamf/jnuc2022/home22/page/sessioncatalog/session/1650403830886001hWmZ

Near the bottom.

duff2481-1
New Contributor III

Will these and others be available to those that were not able to attend JNUC '22 at some point? 

ZachH
New Contributor II
New Contributor II

The recorded presentations themselves will be only accessible after purchasing a virtual JNUC ticket, however the simulations themselves will remain public and can be accessible via these links:

https://training.jamf.com/jnuc-2022-bring-lost-sheep-back
https://training.jamf.com/jnuc-2022-network-threat-prevention
https://training.jamf.com/jnuc-2022-jamf-school
https://training.jamf.com/jnuc-2022-jamf-single-login
https://training.jamf.com/jnuc-2022-jamf-trust

bcbackes
Contributor III

Warning: 

In further testing I found that if you have the Mac scoped to any policies set with frequency as "Ongoing" and using an "Enrollment" trigger it will rerun that policy. I had to update a couple of my prestage enrollment policies from "Ongoing" to "Once per computer". 

The reason for this is part of the process for getting the Jamf Management Framework back on the Mac is it enrolls the device. You can see this happening if you are in the "/usr/local/jamf/bin" folder. You will see "enroll" and "jamf" both show up and then the "enroll" will disappear after a few seconds when the process is completed.

bizzaredm
Contributor

Well since the script is technically available in the simulation, I hope its okay to post here. This was transcribed from the simulation, and should be reviewed before use 

EDIT: Oct 6th, 2022: Fixed is0 typo to ISO. Fixed "${ids[@]}" typo

 

#! /bih/bash

# The purpose of this script is to send a repair command (Redeploy Jamf Management Framework) via MDM to a smart group of devices•
# that have not checked in after a certain amount of time.

########### COPYRIGHT AND DISCLAIMER ########################################################
# Copyright notice - 0 2022, Erin Mcdonald, JAMF Software, LIC
# THE SOFTWARE IS PROVIDED "AS-IS, " WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
# TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
# JAMF SOFTWARE, LLC OR ANY OF ITS AFFILIATES BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN-
# CONTRACT, TORT, OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OF OR OTHER
# DEALINGS IN THE SOFTWARE, INCLUDING BUT NOT LIMITED TO DIRECT, INDIRECT, INCIDENTAL, SPECIAL, CONSEQUENTIAL
# OR PUNITIVE DAMAGES AND OTHER DAMAGES SUCH AS LOSS OF USE, PROFITS, SAVINGS, TIME OR DATA, BUSINESS INTERRUPTION,
# OR PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES.
############################################################################################

# Variables
# Replace with your environment's values
# Jamf Pro URL including 'https://' and port, if needed
URL="https://myURL.jamfcloud.com"

# Jamf Pro User account with the following permissions
# Jamf Pro Server Objects: Computers, Smart Computer Groups (Read Only), Jamf Pro Server Settings: Check-In, Computer Check-In (Read Only)
# Jamf Pro Server Actions: Sent remote Command to Install Package
username="enterUserNameBetweenQuotes"

# Password of the Jamf Pro User account
password="enterPasswordBetweenQuotes"

# Smart Group of computers that have not checked in for X amount of days, replace the # after the = with the ID of the smart group
smartGroup=#

# Get a bearer token for all API calls

encodedCredentials=$( printf "$username:$password" | /usr/bin/iconv -t ISO-8859-1 | /usr/bin/base64 -i - )
bearerToken=$(/usr/bin/curl "$URL/uapi/auth/tokens" \
--silent \
-- request POST \
--header "Authorization: Basic $encodedCredentials" )

# parse authToken for token, omit expiration
token=$( /usr/bin/awk -F \" '{ print $4 }' <<< "$bearerToken" | /usr/bin/xargs )

# Execute the mdm command

# Get membership details of Computer Group that contains computers that have not checked in in a set amount of days
ids+=($(curl --request GET \
--url${URL}/JSSResource/computergroups/id/$smartGroup \
--header 'Accept: application/xml' \
--header "Authorization: Bearer ${token}"| xmllint --xpath '//computer_group/computers/computer/id' - 2> /dev/null | sed s/'<id>'//g | sed s/'<\/ id>'/','/g | sed 's/.$//' | sort -n | tr ',' ' '))

# for loop to go through all IDs in the group and send the remote command to redeplopy the framework

for id in "${ids[@]}"; do
if [[ $id -gt 0 ]]; then
 echo "$id"
# Post Redeploy command to computer
curl --request POST \
--url ${URL}/api/v1/jamf-management-framework/redeploy/${id} \
--header 'Content-Type: application/ison' \
--header "Authorization: Bearer ${token}" 
else
echo "Device id {$id} invalid, skipping..."

fi
done

# Invalidate the token
curl --request POST \
--url ${URL}/api/v1/auth/invalidate-token \
--header 'Accept: application/ison' \
--header "Authorization: Bearer ${token}"
exit 0

 



duff2481-1
New Contributor III

I get error of the below when i attempt to test this script   Anyone else seeing this? 

/usr/bin/iconv: conversion to IS0-8859-1 unsupported
/usr/bin/iconv: try '/usr/bin/iconv -l' to get the list of supported encodings

 

Typo.. 
isO not is(zero)

if you update that, it should work.

I would reference bcbackes post below

bcbackes
Contributor III

Here is the script that I'm using that encrypts the Jamf Pro User account per Joshua Roskos process for his Log Collection Script found here - start at Step 3. This script is working for me. Parameters for the script below are as follows:
Parameter 4 - empty

Parameter 5 - Jamf Pro URL

Parameter 6 - Jamf Pro User

Parameter 7 - Jamf Pro Password (Encrypted)

Parameter 8 - Salt

Parameter 9 - Passphrase

Parameter 10 - empty

Parameter 11 - empty

 

#!/bin/bash

# The purpose of this script is to send a repair command (Redeploy Jamf Management Framework) via MDM to a smart group of devices 
# that have not checked in after a certain amount of time. 

########### COPYRIGHT AND DISCLAIMER #############################################################################
# Copyright notice - © 2022, Erin Mcdonald, JAMF Software, LLC
# THE SOFTWARE IS PROVIDED "AS-IS," WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED 
# TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL 
# JAMF SOFTWARE, LLC OR ANY OF ITS AFFILIATES BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 
# CONTRACT, TORT, OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OF OR OTHER 
# DEALINGS IN THE SOFTWARE, INCLUDING BUT NOT LIMITED TO DIRECT, INDIRECT, INCIDENTAL, SPECIAL, CONSEQUENTIAL 
# OR PUNITIVE DAMAGES AND OTHER DAMAGES SUCH AS LOSS OF USE, PROFITS, SAVINGS, TIME OR DATA, BUSINESS INTERRUPTION, 
# OR PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES.
##################################################################################################################

# Updated 9-28-22 by Brant Backes to include encryption steps for the Jamf Pro Password as identified in Joshua Roskos Log Collection Script instructions: https://github.com/kc9wwh/logCollection/wiki/Using-Encrypted-Strings
# Make sure to enter in the script parameter labels and update the variable below for the Smart Group on line 34.

# Variables
# Replace with your environment's values
# Jamf Pro URL including 'https://' and port, if needed
URL="$5"  

# Jamf Pro User account with the following permissions
# Jamf Pro Server Objects: Computers, Smart Computer Groups (Read Only), Jamf Pro Server Settings: Check-In, Computer Check-In (Read Only) 
# Jamf Pro Server Actions: Sent remote Command to Install Package
username="$6" 

# Password of the Jamf Pro User account
password=$(echo "$7" | /usr/bin/openssl enc -aes256 -d -a -A -S "$8" -k "$9") 

# Smart Group of computers that have not checked in for X amount of days, replace the # after the = with the ID of the smart group
smartGroup=#

# Get a bearer token for all API calls

encodedCredentials=$( printf "$username:$password" | /usr/bin/iconv -t ISO-8859-1 | /usr/bin/base64 -i - )

bearerToken=$( /usr/bin/curl "$URL/uapi/auth/tokens" \
--silent \
--request POST \
--header "Authorization: Basic $encodedCredentials" )


# parse authToken for token, omit expiration
token=$( /usr/bin/awk -F \" '{ print $4 }' <<< "$bearerToken" | /usr/bin/xargs )

# Execute the mdm command

# Get membership details of Computer Group that contains computers that have not checked in in a set amount of days
ids+=($(curl --request GET \
--url ${URL}/JSSResource/computergroups/id/$smartGroup \
--header 'Accept: application/xml' \
--header "Authorization: Bearer ${token}"| xmllint --xpath '//computer_group/computers/computer/id' - 2> /dev/null | sed s/'<id>'//g | sed s/'<\/id>'/','/g | sed 's/.$//' | sort -n | tr ',' ' '))

# for loop to go through all IDs in the group and send the remote command to redeplopy the framework

for id in "${ids[@]}"; do
	if [[ $id -gt 0 ]]; then
		echo "$id"
		# Post Redeploy command to computer
		curl --request POST \
		--url ${URL}/api/v1/jamf-management-framework/redeploy/${id} \
		--header 'Content-Type: application/json' \
		--header "Authorization: Bearer ${token}"
	else
		echo "Device id ${id} invalid, skipping..."
	fi
done

# Invalidate the token
curl --request POST \
--url ${URL}/api/v1/auth/invalidate-token \
--header 'Accept: application/json' \
--header "Authorization: Bearer ${token}"

exit 0

 

duff2481-1
New Contributor III

I'm receiving the following error when testing in our QA environment. It's appear to not read within our smartgroup. Has anyone else seen this? 

[[: {[@]}: syntax error: operand expected (error token is "{[@]}")

 

@duff2481-1  Are you using my script above that has the credentials encrypted or do you have them in plain text. If you are using the encrypted version I would try changing your script to use it in plain text and then test it again in QA. If it works than the issue is with the encrypted creds. 

duff2481-1
New Contributor III

I'm using the plain text script version for initial testing and communication.  Using same creds running basic get command, i can view smartgroup and or specific machines when calling API so i think i'm good from that perspective.

Maybe check to see that the Jamf Pro user account you are using has the correct permissions? I found that when I first setup my generic Jamf Pro User account I inadvertently checked the wrong box. I went back through slowly and fixed my errors.  Here is what I have for settings:


Jamf Pro Server Objects: 

Computers - Read/Update

Smart Computer Groups - Read

 

Jamf Pro Server Settings:

Check-In - Read

Computer Check-in Setting - Read

 

Jamf Pro Server Actions:

Send Computer Remote Command to Install Package - Check

duff2481-1
New Contributor III

So I didn't have the server actions checked, much appreciate that. This looks to be permissions based and I know for a fact that if i visit our URL:

https://url.com:8443/JSSResource/computergroups/id/29 I'm prompted to enter credentials and the same creds used in web interface are in the script. This then shows one machine, ID, name, mac address etc.. 

 

 

./lostSheep-QA-Unencrypted.sh: line 54: [[: {[@]}: syntax error: operand expected (error token is "{[@]}")
Device id {{[@]}} invalid, skipping...
{
  "httpStatus" : 401,
  "errors" : [ ]
}%  

 

 

 Could there be something within the bearer token that I need to review?

Can you post your script in here making sure to sanitize anything specific to your environment?

duff2481-1
New Contributor III

Sure, here it is: 

#!/bin/bash
#Testing within QA Environment 
# The purpose of this script is to send a repair command (Redeploy Jamf Management Framework) via MDM to a smart group of devices•
# that have not checked in after a certain amount of time.

########### COPYRIGHT AND DISCLAIMER ########################################################
# Copyright notice - 0 2022, Erin Mcdonald, JAMF Software, LIC
# THE SOFTWARE IS PROVIDED "AS-IS, " WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
# TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
# JAMF SOFTWARE, LLC OR ANY OF ITS AFFILIATES BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN-
# CONTRACT, TORT, OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OF OR OTHER
# DEALINGS IN THE SOFTWARE, INCLUDING BUT NOT LIMITED TO DIRECT, INDIRECT, INCIDENTAL, SPECIAL, CONSEQUENTIAL
# OR PUNITIVE DAMAGES AND OTHER DAMAGES SUCH AS LOSS OF USE, PROFITS, SAVINGS, TIME OR DATA, BUSINESS INTERRUPTION,
# OR PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES.
############################################################################################

# Variables
# Replace with your environment's values
# Jamf Pro URL including 'https://' and port, if needed
URL="https://url.com:8443"

# Jamf Pro User account with the following permissions
# Jamf Pro Server Objects: Computers, Smart Computer Groups (Read Only), Jamf Pro Server Settings: Check-In, Computer Check-In (Read Only)
# Jamf Pro Server Actions: Sent remote Command to Install Package
username="apiuser"

# Password of the Jamf Pro User account
password="password"

# Smart Group of computers that have not checked in for X amount of days, replace the # after the = with the ID of the smart group
smartGroup=29

# Get a bearer token for all API calls

encodedCredentials=$( printf "$username:$password" | /usr/bin/iconv -t ISO-8859-1 | /usr/bin/base64 -i - )
bearerToken=$(/usr/bin/curl "$URL/uapi/auth/tokens" \
--silent \
-- request POST \
--header "Authorization: Basic $encodedCredentials" )

# parse authToken for token, omit expiration
token=$( /usr/bin/awk -F \" '{ print $4 }' <<< "$bearerToken" | /usr/bin/xargs )

# Execute the mdm command

# Get membership details of Computer Group that contains computers that have not checked in in a set amount of days
ids+=($(curl --request GET ${URL}/JSSResource/computergroups/id/$smartGroup \
--header 'Accept: application/xml' \
--header "Authorization: Bearer ${token}"| xmllint --xpath '//computer_group/computers/computer/id' - 2> /dev/null | sed s/'<id>'//g | sed s/'<\/ id>'/','/g | sed 's/.$//' | sort -n | tr ',' ' '))

# for loop to go through all IDs in the group and send the remote command to redeplopy the framework

for id in "${ids[@]}"; do
if [[ $id -gt 0 ]]; then
 echo "$id"
# Post Redeploy command to computer
curl --request POST \
--url ${URL}/api/v1/jamf-management-framework/redeploy/${id} \
--header 'Content-Type: application/ison' \
--header "Authorization: Bearer ${token}" 
else
echo "Device id {$id} invalid, skipping..."

fi
done

# Invalidate the token
curl --request POST \
--url ${URL}/api/v1/auth/invalidate-token \
--header 'Accept: application/ison' \
--header "Authorization: Bearer ${token}"
exit 0

 

I think it's erroring on the bearer credentials.  If i encrypt username / password and then attempt to call bearerToken command, it fails with 401 there. 

I've noticed another type-o.  when calling POST to update the API call says "application/ison", this should be application/json with a "j"..

curl --request POST \
--url ${URL}/api/v1/jamf-management-framework/redeploy/${id} \
--header 'Content-Type: application/ison' \
--header "Authorization: Bearer ${token}" 

 continuing to test . 

Yep, I saw a couple typos and a couple formatting things. Try this - make sure to put your environment stuff back in there.

#!/bin/bash
#Testing within QA Environment 
# The purpose of this script is to send a repair command (Redeploy Jamf Management Framework) via MDM to a smart group of devices•
# that have not checked in after a certain amount of time.

########### COPYRIGHT AND DISCLAIMER ########################################################
# Copyright notice - 0 2022, Erin Mcdonald, JAMF Software, LIC
# THE SOFTWARE IS PROVIDED "AS-IS, " WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
# TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
# JAMF SOFTWARE, LLC OR ANY OF ITS AFFILIATES BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN-
# CONTRACT, TORT, OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OF OR OTHER
# DEALINGS IN THE SOFTWARE, INCLUDING BUT NOT LIMITED TO DIRECT, INDIRECT, INCIDENTAL, SPECIAL, CONSEQUENTIAL
# OR PUNITIVE DAMAGES AND OTHER DAMAGES SUCH AS LOSS OF USE, PROFITS, SAVINGS, TIME OR DATA, BUSINESS INTERRUPTION,
# OR PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES.
############################################################################################

# Variables
# Replace with your environment's values
# Jamf Pro URL including 'https://' and port, if needed
URL="https://url.com:8443"

# Jamf Pro User account with the following permissions
# Jamf Pro Server Objects: Computers, Smart Computer Groups (Read Only), Jamf Pro Server Settings: Check-In, Computer Check-In (Read Only)
# Jamf Pro Server Actions: Sent remote Command to Install Package
username="apiuser"

# Password of the Jamf Pro User account
password="password"

# Smart Group of computers that have not checked in for X amount of days, replace the # after the = with the ID of the smart group
smartGroup=29

# Get a bearer token for all API calls

encodedCredentials=$( printf "$username:$password" | /usr/bin/iconv -t ISO-8859-1 | /usr/bin/base64 -i - )
bearerToken=$( /usr/bin/curl "$URL/uapi/auth/tokens" \
--silent \
--request POST \
--header "Authorization: Basic $encodedCredentials" )

# parse authToken for token, omit expiration
token=$( /usr/bin/awk -F \" '{ print $4 }' <<< "$bearerToken" | /usr/bin/xargs )

# Execute the mdm command

# Get membership details of Computer Group that contains computers that have not checked in in a set amount of days
ids+=($(curl --request GET \
--url ${URL}/JSSResource/computergroups/id/$smartGroup \
--header 'Accept: application/xml' \
--header "Authorization: Bearer ${token}"| xmllint --xpath '//computer_group/computers/computer/id' - 2> /dev/null | sed s/'<id>'//g | sed s/'<\/ id>'/','/g | sed 's/.$//' | sort -n | tr ',' ' '))

# for loop to go through all IDs in the group and send the remote command to redeplopy the framework

for id in "${ids[@]}"; do
if [[ $id -gt 0 ]]; then
 echo "$id"
# Post Redeploy command to computer
curl --request POST \
--url ${URL}/api/v1/jamf-management-framework/redeploy/${id} \
--header 'Content-Type: application/json' \
--header "Authorization: Bearer ${token}" 
else
echo "Device id {$id} invalid, skipping..."

fi
done

# Invalidate the token
curl --request POST \
--url ${URL}/api/v1/auth/invalidate-token \
--header 'Accept: application/json' \
--header "Authorization: Bearer ${token}"
exit 0

duff2481-1
New Contributor III

Interestingly enough, I've had to use double quotes in a couple of locations in order to have it run successfully.  In addition when parsing with the SED command, this failed all-together.  I reverted to calling for just the text() of the value within the container 

This finally worked for me.  Thank you @bcbackes for reviewing and assisting me.  

#!/bin/bash
#Testing within QA Environment 
# The purpose of this script is to send a repair command (Redeploy Jamf Management Framework) via MDM to a smart group of devices•
# that have not checked in after a certain amount of time.

########### COPYRIGHT AND DISCLAIMER ########################################################
# Copyright notice - 0 2022, Erin Mcdonald, JAMF Software, LIC
# THE SOFTWARE IS PROVIDED "AS-IS, " WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
# TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
# JAMF SOFTWARE, LLC OR ANY OF ITS AFFILIATES BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN-
# CONTRACT, TORT, OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OF OR OTHER
# DEALINGS IN THE SOFTWARE, INCLUDING BUT NOT LIMITED TO DIRECT, INDIRECT, INCIDENTAL, SPECIAL, CONSEQUENTIAL
# OR PUNITIVE DAMAGES AND OTHER DAMAGES SUCH AS LOSS OF USE, PROFITS, SAVINGS, TIME OR DATA, BUSINESS INTERRUPTION,
# OR PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES.
############################################################################################

# Variables
# Replace with your environment's values
# Jamf Pro URL including 'https://' and port, if needed
URL="https://url.com:8443"

# Jamf Pro User account with the following permissions
# Jamf Pro Server Objects: Computers, Smart Computer Groups (Read Only), Jamf Pro Server Settings: Check-In, Computer Check-In (Read Only)
# Jamf Pro Server Actions: Sent remote Command to Install Package
username="apiuser"

# Password of the Jamf Pro User account
password="password"

# Smart Group of computers that have not checked in for X amount of days, replace the # after the = with the ID of the smart group
smartGroup=29

# Get a bearer token for all API calls

encodedCredentials=$( printf "$username:$password" | /usr/bin/iconv -t ISO-8859-1 | /usr/bin/base64 -i - )
bearerToken=$( /usr/bin/curl "$URL/uapi/auth/tokens" \
--silent \
--request POST \
--header "Authorization: Basic $encodedCredentials" )

# parse authToken for token, omit expiration
token=$( /usr/bin/awk -F \" '{ print $4 }' <<< "$bearerToken" | /usr/bin/xargs )

# Execute the mdm command

# Get membership details of Computer Group that contains computers that have not checked in in a set amount of days
ids+=($(curl --request GET \
--url ${URL}/JSSResource/computergroups/id/$smartGroup \
--header 'Accept: application/xml' \
--header "Authorization: Bearer ${token}"| xmllint --xpath "/computer_group/computers/computer/id/text()" - ))
# for loop to go through all IDs in the group and send the remote command to redeplopy the framework

for id in "${ids[@]}"; do
if [[ $id -gt 0 ]]; then
 echo "$id"
# Post Redeploy command to computer
curl --request POST \
--url ${URL}/api/v1/jamf-management-framework/redeploy/${id} \
--header 'Content-Type: application/json' \
--header "Authorization: Bearer ${token}" 
else
echo "Device id {$id} invalid, skipping..."

fi
done

# Invalidate the token
curl --request POST \
--url ${URL}/api/v1/auth/invalidate-token \
--header 'Accept: application/json' \
--header "Authorization: Bearer ${token}"
exit 0

 

duff2481-1
New Contributor III

Question -- Is anyone running 12.6 and also trying to test?  Working through the encrypted script now and getting a 402 error.  I'm almost positive it's related to token encryption.  I notice the following when using encrypted script method.

*** WARNING : deprecated key derivation used.
Using -iter or -pbkdf2 would be better.