Smart Group membership based on existence of a local file

vwebb
New Contributor

Is it possible to create a Smart Group that is populated based on the existence of a file on the local hard drive? I'm not seeing anything obvious so I'm assuming I'd need to create a new Extension Attribute to populate the Smart Group. Not sure if this is possible though. I've messed around a bit in the creating Extension Attributes area of Inventory Collection, but to no avail. I'm pretty sure I need a script that will check for the file, but my scripting kung-fu is weak.

16 REPLIES 16

krutaw
New Contributor

<dupe>

krutaw
New Contributor

!/bin/sh

FILENAME="$1"
[ -f $FILENAME ] && echo "<result>Found</result>" || echo "<result>Not found</result>"

jarednichols
Honored Contributor

Yep that'll do it. The alternative is a Miles Leacy special - the Dummy Package. Simply do a

#!/bin/sh
touch /Library/Application Support/JAMF/Receipts/<YourReceiptName>.pkg

This will trick Casper into seeing a piece of software "installed" by Casper. You can then make smart groups based on this. I do this to "tag" a machine to what build it was created with. For instance, one of mine looks like

#!/bin/sh
touch /Library/Application Support/JAMF/Receipts/US_TSO_1.1.pkg

This is for a US build for the TSO group, version 1.1 of the build. (I have a master list of what's in each version of each build elsewhere.)

I've also got

#!/bin/sh
touch /Library/Application Support/JAMF/Receipts/UK_PGT_1.1.pkg

This is for a UK build for the PGT group. I think you get the idea...

vwebb
New Contributor

Thanks for the responses!

Jared,
I really like this idea. Can you elaborate though on how to create the Smart Group? I've made an attribute to drop the dummy package. Let's call it Package.pkg. Thanks!

Vince

jarednichols
Honored Contributor

Sure, once your machine has gone through recon, when you're creating the smart group if you go to your Criteria tab, go to the "Receipts Information" area and then select "Packages Installed by Casper." When you then click the ellipses button "..." you'll get a list of all the packages Casper has installed in your environment on any machine - including your newly minted Dummy Packages.

In your case, you'd see "Package.pkg" in the list. Select it and voila! A smart group based on a file.

zmbarker
Contributor

Can someone explain to me what file is this script actually looking for?

#!/bin/sh
FILENAME="$1"
[ -f $FILENAME ] && echo "<result>Found</result>" || echo "<result>Not found</result>"

What I am trying to figure out is how to use this as an Ext Attribute to determine which computers have a particular file, which could be in different locations on each local computer.

Ex: On est. 500 computers there might be a file called PharmAdmit.log which could be anywhere on the local drive. I need to create a smart group (most likely based on an Ext Att script) to search and report back. I can't make a dummy receipt because these computers already have this file, I am not sending a file out.

pickerin
Contributor II

$1 is the first argument passed with the script (so it can be used on a number of packages).
So in your case, $1 will be "PharmAdmit.log"

The shell command is then performing an "if exists" (-f $FILENAME) and if found printing <result>Found</result> out (which makes is the result of the script from a Casper standpoint. OR it's printing <result>Not found</result> if the file is not found.

[-f $FILENAME] is a shell shortcut for "if exists"

zmbarker
Contributor

@pickerin - that is how I read it also. However, it will only find the file if it is located on the root of the HD. Once I move the file into a folder the results say "Not Found"

pickerin
Contributor II

@zmbarker

The script checks for the existence of the file in the same directory the script is run, it's not doing a full file system scan for it. If you put it in a sub-directory, you will have to pass the full (or relative to the script location) path as the first argument.

dwandro92
Contributor III

I've done this on our server using an extension attribute. In our case, we are checking to see if Cocoa Dialog is installed on the machine. Since .app files are seen as directories, you would just need to change "if [ -d" to "if [ -e" to check for a file. Hope this helps:

#!/bin/sh

# If Cocoa Dialog exists
if [ -d "/Library/Application Support/JAMF/bin/CocoaDialog.app" ]; then # Set result value result="Installed"
# If Cocoa Dialog does not exist
else # Set result value result="Not Installed"
fi

# Output result
echo "<result>$result</result>"

# Exit script
exit 0

zmbarker
Contributor

dwandro92 - thanks for the script. However, it does not solve my problem with having the .log file located anywhere on the local HD. Your script only checks in an absolute path.

dwandro92
Contributor III

How about this?

#!/bin/sh

# Set name of log file
logFile="PharmAdmit.log"

# Update locate database
/usr/libexec/locate.updatedb

# Check to see if the file exists (not case sensitive, when -i switch is used)
arrLogs=locate -i "$logFile"

# If a log was found
if [ "$arrLogs" != "" ]; then # Set result value
result="Found"
# If a log was not found
else
# Set result value
result="Not Found"
fi

# Output result
echo "<result>$result</result>"

# Exit script
exit 0

zmbarker
Contributor

**This script works and will search throughout the entire local HD for the file.

#!/bin/sh
FILENAME="PharmAdmit.log"
[ -n "find -x / -name "*$FILENAME" 2> /dev/null || echo """ ] && echo "<result>Found</result>" || echo "<result>Not found</result>"

mm2270
Legendary Contributor III

Use mdfind (Spotlight)

#!/bin/bash

LogFile=$( mdfind 'kMDItemKind = "Log File" && kMDItemFSName = "PharmAdmit.log"' )

if [ "$LogFile" ]; then
   echo "<results>Found</results>"
else
   echo "<results>Not Found</results>"
fi

pickerin
Contributor II

Just keep in mind how long this script could take to run...if it's searching the whole drive it's going to take a while. If it's utilizing Spotlight or another indexed database it'll be quick, but it will only be found if in fact the file was present when an index run completed, so there is room for error.

rjford
New Contributor II
Posted: 10/24/13 at 11:18 PM by mm2270 Use mdfind (Spotlight)

!/bin/bash

LogFile=$( mdfind 'kMDItemKind = "Log File" && kMDItemFSName = "PharmAdmit.log"' ) if [ "$LogFile" ]; then echo "<results>Found</results>" else echo "<results>Not Found</results>" fi

Thank you for this.. this is still working as of 10.13.

Only tweak was it needs to be <result> not <results>