Wednesday, 17 February 2016

Automating the distribution of Apple Mail Stationery in a corporate environment

I recently had to find a solution to distribute Apple Mail Stationery files to all the Macs in a company. Stationery for use with Apple Mail is normally distributed either as an attachment to an email or as a file on a disk and either way would normally be installed in each users individual home directory. Not only would this result in potentially multiple copies of the same stationery file on a single Mac but the location in a users home directory is a rather complex one looking for example like this -

~/Library/Containers/ Support/Mail/Stationery/Apple/Contents/Resources/Custom/

While hypothetically it might be possible to come up with a solution to both automate initial distribution of these files to each user and to distribute updates to these files to those users it seemed to me that the easiest solution was going to be to automate distributing them to each computer rather than each user especially as I was wanting to do this via Munki.

Note: This approach should equally work using similar tools like ARD, CasperSuite, etc.

The first step was therefore to locate where Apple's own included example mail stationery files were located which is…

/Library/Application Support/Apple/Mail/Stationery/Apple/Contents/Resources/

…with multiple sub-folders to organise the different categories of stationery Apple provide. An added complexity is that Apple also use the following file as an index defining the list of categories/sub-folders

/Library/Application Support/Apple/Mail/Stationery/Apple/Contents/Resources/TableOfContents.plist

I could have simply placed my files in one of the existing Apple folders but apart from this likely being confusing to users it may also be at risk of being wiped by Apple updates. I therefore wanted to create a sub-folder for my own files. I therefore needed to find a way to -

  1. Create the sub-folder
  2. Update Apple's TableOfContents if needed to include my sub-folder
  3. Copy my files in to it

I accomplished this by creating a standard Apple Installer package file with a payload of my mail stationery files, and a pre-install script in the Installer package to create the sub-folder and to update the TableOfContents index. While I have chosen to use a single Installer package to install multiple mail stationery files to the same folder this approach could easily be adapted to have individual installer package files one for each stationery file.

While the TableOfContents file is a plist file it is not of a format that makes it possible to use the standard 'defaults' command to modify it - defaults is particularly weak at handling arrays, it might have been possible to use PlistBuddy but I settled on using a perl script as part of a shell script to do this.

/bin/mkdir -p "/Library/Application Support/Apple/Mail/Stationery/Apple/Contents/Resources/MyCompanyName/Contents/Resources/" && /bin/cp -R "/private/tmp/Mail Stationery/" "$_";
searchtableofcontents=`grep '<string>MyCompanyName</string>' "/Library/Application Support/Apple/Mail/Stationery/Apple/Contents/Resources/TableOfContents.plist"`
if [ "$searchtableofcontents" != " <string>MyCompanyName</string>" ]; then
perl -i -pe 'BEGIN{undef $/;} s/<\/array>.*<\/plist>/\t<dict>\n\t\t<key>Folder Name<\/key>\n\t\t<string>MyCompanyName<\/string>\n\t<\/dict>\n<\/array>\n<\/plist>/smg' "/Library/Application Support/Apple/Mail/Stationery/Apple/Contents/Resources/TableOfContents.plist";
exit 0

I then added this installer package to my Munki repo to be automatically distributed to all the Macs. I can and have issued updated versions simply by creating a new updated installer package with a new version number and Munki picks this up and distributes it as an update.

Users can then see the mail stationery in Apple Mail as a separate folder in the standard list of stationery. Users do not have to be bothered by or confused by getting an email attachment and working out how to install it themselves. Furthermore this works even if a user uses more than one different Mac and even if the user leaves and someone else gets their Mac.

I can also automate uninstalling this and tidying things up by using the following matching Uninstall script in Munki.

searchtableofcontents=`grep '<string>MyCompanyName</string>' "/Library/Application Support/Apple/Mail/Stationery/Apple/Contents/Resources/TableOfContents.plist"`
if [ "$searchtableofcontents" == " <string>MyCompanyName</string>" ]; then
perl -i -pe 'BEGIN{undef $/;} s/\n\t<dict>\n\t\t<key>Folder Name<\/key>\n\t\t<string>MyCompanyName<\/string>\n\t<\/dict>//smg' "/Library/Application Support/Apple/Mail/Stationery/Apple/Contents/Resources/TableOfContents.plist";
exit 0

Note: The above script's If statement has exactly the number of spaces needed in it so be careful when copying it.

Note: Munki uses the package receipts list to delete i.e. uninstall the actual mail stationery files, the above script simply removes the sub-folder entry from the Apple TableOfContents file.

Saturday, 13 February 2016

Munki and Microsoft Office licenses

Many Mac using organisations will use a free open-source tool called Munki to deploy applications and updates for those applications including of course Microsoft Office for Mac. If you have a Microsoft volume license this is extremely easy as all you have to do is download the ISO and add the contents to your Munki repo. If you however still have individual aka. ‘boxed’ license numbers for Office then matters are a bit more complicated.

Firstly a bit of a rant about Microsoft and their ‘Volume’ licenses. To most people volume implies a volume discount as anyone who has to do the weekly supermarket shopping run will be familiar with. This also applies to most software companies but not Microsoft. Instead volume when associated with Microsoft probably refers to how loud their customers will scream when they see how much they are being ripped off by Microsoft. You will be staggered to learn that a Microsoft volume license for Office 2016 costs almost exactly double the price of the same number of ‘boxed’ Office 2016 copies. Yes you read that correctly double!

Now this is on top of the long standing practice by not only Microsoft but most software companies of not allowing you to convert individual boxed licenses to be part of a volume license and therefore requiring you to pay full price for a new volume license. This is as I said a longstanding practice and while arguably unfair and arguably counter-productive in that it can discourage customers moving to a volume license which even ignoring costs would be in the long-term interest of Microsoft as well.

Historically small organisations would start off by buying boxed licenses and then grow to a size that the simpler administration provided by a volume license becomes important, most companies at some point would hit this problem. (These days companies might start off with Office 365 and then move to a volume license.)

Note: The fact that the volume license for Office costs double the price of the same number of boxed copies applies to both Mac and Windows versions. At least one can say unusually that Microsoft are treating both Mac and Windows customers equally bad.

The main purpose of this post is therefore to describe how to continue to use boxed Microsoft licenses on Macs via Munki and to still keep much of the benefit of simplicity provided otherwise by a volume license.

The steps to do this are simple to do and only require a modest amount of initial work.
  1. Add as normal the (boxed) Office installer to your Munki repo
  2. Use Munki to deploy Office to a new Mac
  3. On the new Mac launch Office and manually activate its license as normal
  4. This will create the license file on that Mac, this now needs to be copied to your Munki server, I create an additional sub-folder in the Munki repo called licenses for this purpose, and then in the licenses folder create another folder called office2008 or office2011 or office2016 as appropriate, then create in that a folder named with the serial number of the Mac e.g. CK123456789Z and finally put the office license file in that
For Office2008 the license file is located at
/Applications/Microsoft Office 2008/Office/OfficePID.plist
For Office2011 the license file is located at
For Office2016 the license file is located at

So on your Munki repo you will have something like this
./licenses/office2008/CK123456789Z/OfficePID.plist or
./licenses/office2011/CK123456789Z/ or

This now makes it possible to have Munki automatically install the license file the next time the same Mac needs Office reinstalling, perhaps after replacing a fault hard disk or fitting a bigger hard disk or wiping and reinstalling the entire Mac. As the license file is linked to the same Mac all that is required is to copy the license file back to the same location. To do this I use the following post-install script in Munki for the Office install.

Note: This example script is for Office 2011 it should be very obvious what changes are needed for other versions of Office based on the above information.

serialnumber=$(/usr/sbin/system_profiler SPHardwareDataType | /usr/bin/grep 'Serial Number (system)' | /usr/bin/awk '{print $NF}')
/usr/bin/curl$officeversion/$serialnumber/$filename –o $location/$filename

Note: If you run the Munki install of Office before a license file has been 
created and added to the relevant sub-folder of the licenses folder this is not 
a problem as Office will still be installed successfully and you simply have to 
license it manually, thereafter assuming you remember to copy the license file 
to the relevant folder in your Munki repo this will be copied automatically 
after the install of Office.