Setting the Screen Saver to a static image

On our Windows systems we have a static image as our screen saver and I wanted to match that on our Macs.  There are several options in the Screen Saver settings of System Preferences.  I needed to figure out how to set a default across all our Macs with a script.Screen Shot 2018-02-02 at 1.55.51 PM.png

Continue reading


Automator application to run script as root

I was recently asked to create a shortcut on our users’ Desktops to kick off the High Sierra install. We are caching the installer through our management system. In the past I have created a shortcut to the installer on their Desktop, but that required them to click through the many continue buttons. This method will use the startosinstall script from Slack member @bp to start the install with minimal user interaction. Continue reading

Signing Installer Packages with Automator

Apple packages (.pkgs) are opened by the GUI or the command line installer command. If a package is unsigned and gets a quarantine flag (from being transferred over a network), the GUI Installer will refuse to run it.Screen Shot 2016-11-02 at 3.07.35 PM.png We can get around that with a right-click -> Open, but we shouldn’t be training computer users to ignore security warnings like this.

Screen Shot 2016-11-04 at 4.49.33 PM.png
If you are creating your own packages, and users or techs may run them manually, then you really should be signing them. Even if you are deploying them in a way that a person won’t see a warning, signing packages can be very easy and provide a check that nothing changed since you created it. See below the break for how to easily automate signing packages. Continue reading

Mounting File Shares Based on AD Group Membership using Enterprise Connect

[edit] Apple changed something in macOS 10.13 High Sierra. The mount_share() function in the below python needs to be changed to set the open_options and mount_options to ‘None’. This can be done like

def mount_share(share_path):
    # Mounts a share at /Volumes, returns the mount point or raises an error
    sh_url = CoreFoundation.CFURLCreateWithString(None, share_path, None)
    # Set UI to reduced interaction
    #open_options  = {NetFS.kNAUIOptionKey: NetFS.kNAUIOptionNoUI}
    # Allow mounting sub-directories of root shares
    #mount_options = {NetFS.kNetFSAllowSubMountsKey: True}
    # Mount!
    result, output = NetFS.NetFSMountURLSync(sh_url, None, None, None, None, None, None)
    # Check if it worked
    if result != 0:
         raise Exception('Error mounting url "%s": %s' % (share_path, output))
    # Return the mountpath
    return str(output[0])


In a previous post, I discussed using ldapsearch to look up user data from AD.  In this post we will use the user’s memberOf attribute to mount the appropriate file share.

Some background on my use case for this.  The company I work for has ~15,000 Windows computers in use bound to AD.  When a user logs in, a GPO runs a batch file hosted on the domain controller’s file share.  The batch file is basically a large case statement

if in group A; then
    mount shares X and Y
if in group B; then
    mount share Z

I wanted to provide our Mac users with a similar experience.  Read how below the break. Continue reading

Using ldapsearch to get AD data

It has been common for Macs to be bound to Active Directory for a variety of reasons.  Recently, the trend has been to move away from binding due to password/lock out issues, the rise of cloud based services, and SSO options that are more comprehensive of the services users need.

With the move away from binding, one thing we lose is the ability to look up user and group data with dscl. Here is a decent primer on dscl: (just replace every instance of netinfo with dslocal in your mind).

With this move we need another tool to query for information and ldapsearch can do this for us.  There are a lot of ways to use ldapsearch depending on your end goal.  This post will discuss getting user data out of an Active Directory server.  In a future post I hope to explain how I am using this to mount the appropriate file shares for users based on their group membership. Continue reading

Update to network GeekTool script

I have been seeing a lot of noise in my logs about IO80211ScanManager scanning for Wi-Fi networks constantly.  I finally noticed that it was triggered by system_profiler and realized that I was using system_profiler to find my current Wi-Fi network and what channel I was connected to. See the original here:

So I changed how I find that data in my GeekTool script.  I also took the opportunity to simplify the whole thing a bit more.  Here is the new version:

#! /bin/bash
services=$(networksetup -listallnetworkservices)
while read service; do
	ip=$(networksetup -getinfo "$service" | grep "IP address" | grep -v "IPv6" | awk '{print $3}')
	if [ "$ip" != "" ]; then
		echo "$service : $ip"
		if [ "$service" == "Wi-Fi" ]; then
			NetName=$(/System/Library/PrivateFrameworks/Apple80211.framework/Versions/Current/Resources/airport -I | grep SSID | grep -v BSSID | cut -d":" -f2 | tr -d '[[:space:]]')
			Channel=$(/System/Library/PrivateFrameworks/Apple80211.framework/Versions/Current/Resources/airport -I | grep channel | cut -d":" -f2 | tr -d '[[:space:]]')
			echo "$NetName / $Channel"
done <<<"$services"

if [ $connection = false ]; then
	echo "No Connected Services"
	extIP=$(curl -s | sed 's/[a-zA-Z<>/ :]//g')
	if [ "$extIP" != "" ]; then
		echo "External IP: $extIP"
		echo "No External Connection"

Instead of system_profiler the airport command to get the network name and channel.  This stopped the all the message in my logs. I also moved the name and channel logic into the main while read block. This prevents the name and channel from getting separated from the Wi-Fi network IP.

Unhide /Users in 10.9.3

[Further Edit] The below was fixed by Apple.  This is no longer necessary, but I’ll leave it here incase the ideas help someone. [/Further Edit]

[Edit] So the below doesn’t actually work. Something changes the permissions and hidden flag after my launch daemon runs. I added a check of the files (just ls > to a file) and they get set correctly but by the time I am logged in something has changed it back. [/edit]

The recent 10.9.3 update has made a strange change for a number of OS X users.  The directory that holds everyone’s home folder, /Users, has been hidden along with the /Users/Shared folder. Continue reading