First script in a long time

I was wondering if I could get some feedback on my script to grab time from our MDM... I blocked out all of the important stuff. I really appreciate any guidance, since I am long out of practice.

#!/bin/bash
serial=$1
# get last seen value of ipad

lastseen=$(curl -s -X "GET" "https://myairwatchmdm.com/api/mdm/devices/serialnumber/$serial" -H "Authorization: Basic bartsimpson=" -H "aw-tenant-code: marge" | xmllint --format -|grep LastSeen | awk -F "T|<" '{print $3}' | awk -F: '{printf "%1.0f",($1*60)+$2+($3%60)}')

# get UTC time
utc=$(UTC date -j %s)

#get time difference
timediff="$((utc-lastseen))"

# Ipad exit successful 

if [[ "$timediff" -eq 0 ]] || [[ "$timediff" -lt 3600 ]];
echo "$timediff"
then exit 0; 

# Ipad warning threshhold 
    
elif [[ "$timediff" -gt 3600 && "$timediff" -lt 3701 ]];
echo  "$lastseen tablet is reaching warning threshold"
then exit 1; 

# Ipad not seen for more then sixty minutes

elif [[ "$timediff" -gt 3600 ]]; 
echo  "$lastseen tablet has not been seen in more then an hour"
then exit 2; 

# Ipad serial number invalid

elif [[ "$lastseen" = '^[a-ZA-Z]*$' ]] || [[ -z "$lastseen" ]];
echo "Serial Number Invaild"
then exit 3; 
fi

This is not doing what you require:

elif [[ "$lastseen" = '^[a-ZA-Z]*$' ]] || [[ -z "$lastseen" ]];

See Parsing null or empty output: post #4

This validity check also looks out of place here as part of an elif statement, because in the if statements you are comparing timediff, not lastseen.

If anything it should probably occur as a separate if statement right after

 lastseen=$( ... )

But lastseen is a timestamp, not a serial number, so the error message seems not as exact as it might be?
--

if [[ "$timediff" -eq 0 ]] || [[ "$timediff" -lt 3600 ]];
echo "$timediff"
then exit 0;

Should be:

if [[ "$timediff" -eq 0 ]] || [[ "$timediff" -lt 3600 ]]
then 
  echo "$timediff"
  exit 0

or

if [[ $timediff -eq 0 || $timediff -lt 3600 ]]
then 
  echo "$timediff"
  exit 0

or

if (( timediff == 0 || timediff < 3600 ))
then

--
It is good to have proper indentation

--
Your script should test the validity of $1

On top of what Scrutinizer already said,

  • I'd be surprised if UTC date worked.
  • the grep | awk | awk organ could be squeezed into a smaller one.
  • "$timediff" -lt 3600 includes == 0 .
  • in your decision tree, you're missing the $timediff == 3600 case.

what I was trying to do with the $last seen was to account for any output other then a number or null output. I guess my logic is incorrect.

Is there a way I can combine the whole curl command and part the last seen time and look for any error or null output?

elif [[ "$lastseen" = '^[a-ZA-Z]*$' ]] || [[ -z "$lastseen" ]];
echo "Serial Number Invaild"
then exit 3; 
fi

Thanks for the feedback

Post a (few?) unprocessed line(s) from that output.

The xml looks like this (I blocked out the sensitive bits) I am using grep to get the last seen value.

LocationGroupName><UserName>myipad</UserName><UserEmailAddress>myipad@myorg.com</UserEmailAddress><Ownership>C</Ownership><PlatformId title="Apple">2</PlatformId><Platform>Apple</Platform><ModelId title="iPad Mini with Retina (16 GB Space Gray)">2</ModelId><Model>iPad Mini with Retina (16 GB Space Gray)</Model><OperatingSystem>11.1.0</OperatingSystem><PhoneNumber /><LastSeen>2017-12-12T16:49:33.863</LastSeen><EnrollmentStatus>Enrolled</EnrollmentStatus><ComplianceStatus>Compliant</ComplianceStatus><CompromisedStatus>false</CompromisedStatus><LastEnrolledOn>2017-11-07T20:21:19.36</LastEnrolledOn><LastComplianceCheckOn>2017-12-12T16:21:29.97</LastComplianceCheckOn><LastCompromisedCheckOn>0001-01-01T00:00:00</LastCompromisedCheckOn><IsSupervised>true</IsSupervised><IsRemoteManagementEnabled>False</IsRemoteManagementEnabled><DataEncryptionYN>N</DataEncryptionYN><AcLineStatus>0</AcLineStatus><VirtualMemory>0</VirtualMemory><OEMInfo>ME276LL</OEMInfo><DeviceCapacity>12.052879333496094</DeviceCapacity><AvailableDeviceCapacity>10.491180419921875</AvailableDeviceCapacity><LastSystemSampleTime>2017-12-12T16:49:35</LastSystemSampleTime><IsDeviceDNDEnabled>false</IsDeviceDNDEnabled><IsDeviceLocatorEnabled>fal

Not sure what you need the NULL test for. Try (provided the date command on your system (the version of either you dodn't mention, btw) allows for it):

lastseen=$(curl . . .  | awk 'match ($0, "<LastSeen>[^<]*") {print substr($0, RSTART+10, RLENGTH-10)}')
if [[ "$lastseen" =~ [0-9]{4}-[0-9]{2}-[0-9]{2}T([0-9]{2}:){2}[0-9]{2}. ]]
  then  timediff=$(( $(date +%s) - $(date +%s -d$lastseen)))
  .
  .
  .
  fi

Can I substitute seconds with minutes in the date command?

timediff=$(( $(date +%m) - $(date +%m -d$lastseen)))

.

That weren't constructive as it would ignore hours, days, months, years. %s is NOT a date's seconds' part, but the total count of seconds from "the epoque".
%m , btw, specifies the month.

when I print the time diff in my if then I want to display in minutes in my echo.

so it would be ideal to have the display in minutes in the echo

if [[ "$timediff" -eq 0 || "$timediff" -lt 3600 ]]
then 
echo "$timediff"
exit 0

There's an easy conversion from seconds to minutes.

Thanks for the feedback, I am almost there with it... I think I have a solution regarding the serial number.

can i set a default value for the serial number or last seen var if its null?

serial="FPLTL05YFCM5"
# get last seen value of ipad

lastseen=$(curl -s -X "GET" "https://cn705.awmdm.com/api/mdm/devices/serialnumber/$serial" -H "Authorization: Basic bmFnaW9zOm5ITXBZaVBiNHpGZ201WVk=" -H "aw-tenant-code:  Mg0dJDVw02tyPHhFqU8uS3t0ZzkRqJ8mjDHGplY68WI=" | xmllint --format -|grep LastSeen | awk -F "T|<" '{print $3}' | awk -F: '{printf "%1.0f",($1*60)+$2+($3%60)}')

elif [[ "$1" = '^[a-ZA-Z]*$' ]] || [[ -z "$lastseen" ]];
echo "Serial Number Invaild"
then exit 3; 

and if the default value = 1 then I can exit out of the script?