Adobe Creative Cloud Deployment: Packaging a License File

CCP_Pkg_128.pngIn the previous post, we covered the scenarios in which you might want to deploy a Creative Cloud device license or serial number separate from the actual applications, as a “License File Package”. Although the Creative Cloud Packager app supports this as a workflow, the problem is that it doesn’t help you out much with regards to the files it outputs.


Adobe has had the APTEE tool around for a while, as a command-line interface to the Creative Suite licensing tools, to aid with deployment automation – it’s a single executable which confusingly does not include “APTEE” anywhere in the name of the binary: adobe_prtk.

This tool is still around, and has been updated for Creative Cloud. It’s also claimed to be installed as part of Creative Cloud Packager, which is true, but its location is not documented anywhere I could find, so I’ll save you the trouble looking for it: /Applications/Utilities/Adobe Application Manager/CCP/utilities/APTEE/adobe_prtk.

According to the official documentation for the “Create License File” option in CCP, that outputs four files:

  • AdobeSerialization
  • RemoveVolumeSerial
  • helper.bin
  • prov.xml

..there’s no adobe_prtk among those. But it turns out, if we take a look at the strings of AdobeSerialization – which the docs say we can run with “admin privileges” to license the software – some of the first strings found in the binary look an awful lot like flags to adobe_prtk:
Launching the AdobeSerialization in elevated mode ...

AdobeSerialization seems to be a purpose-built version of adobe_prtk with options baked in. This tool loads your authenticated data and license details stored in an opaque format from the prov.xml file to perform a transaction with Adobe’s licensing servers and commit the results to the local machine’s Adobe licensing database.

Along with AdobeSerialization there’s the RemoveVolumeSerial tool. Unfortunately, as mentioned previously and in Adobe’s official CCP documentation this tool is supported for “Enterprise and EEA customers only” – which means it can’t be used to deactivate a machine that is using a Device license in a Teams-based agreement. In fact, it has an LEID baked in along with the adobe_prtk options: V7{}CreativeCloudEnt-1.0-Mac-GM. (For reference, the current LEID for the Creative Cloud Teams “Complete” product is V6{}CreativeCloudTeam-1.0-Mac-GM.)

We’ve got enough hints in these two binaries to figure out that we can pass flags to adobe_prtk. From my examination, these roughly boil down to using the --tool=GetPackagePools flag for a device (Teams) license (see references to “DBCS” throughout the code, ~/Library/Logs/oobelib.log file and the prov.xml file), and --tool=VolumeSerialize for a serial number (Enterprise) license.

Using the adobe_prtk tool and knowing the LEID of the product we want to deactivate, we can also do what the RemoveVolumeSerial tool cannot do: deactivate a teams-based device. The tool options don’t seem to be different depending on a device or serial license, the issue is simply that RemoveVolumeSerial has a hardcoded LEID, whereas we can know ours by looking up the list, or even better, retrieving this automatically from the prov.xml file.

Based on this examination, it looks like adobe_prtk can perform a superset of the functions these two special binaries output from CCP can do, using a single binary. So in order to build a “licensing package” that can be installed as a native OS X installer package (and deployed with Munki, Imagr, DeployStudio, Casper, etc.) we have our necessary ingredients: we need the adobe_prtk (or “APTEE”) tool, the prov.xml file corresponding to our license, and we know the commands to install and remove the license. Still, we need to know which command flags go with which license type, and we need to set the correct LEID if we want to ever be able to deactivate the license. Why not instead use the binaries that are output by CCP? As I described above, the removal tool will not work for all license agreements. I’d rather not have to keep track of multiple different binaries if one can do all the work.

Since investigating all this I decided this would be useful to encapsulate into a script that removes the guesswork from this, and so it has been put on GitHub here: make-adobe-cc-license-pkg.

It only requires a copy of adobe_prtk, which will be discovered automatically if you’ve already installed CCP on the system running the script, and your prov.xml file output from your “Create License File” workflow. Everything else should be figured out for you, and a package will be output given the package parameters you specify:

$ ./make-adobe-cc-license-pkg --name AdobeCC_Complete --reverse-domain ca.macops prov.xml

** Found DBCS (device) license type in prov.xml
** Found LEID 'V6{}CreativeCloudTeam-1.0-Mac-GM' in prov.xml
** Extracted version from adobe_prtk Info.plist section
** Wrote uninstall script to /Users/tsutton/AdobeCC_Complete-2015.05.27.uninstall
pkgbuild: Inferring bundle components from contents of /var/folders/8t/5trmslfj2cnd5gxkbmkbn5fj38qb2l/T/tmprvCGEI
pkgbuild: Adding top-level postinstall script
pkgbuild: Wrote package to /Users/tsutton/AdobeCC_Complete-2015.05.27.pkg
** Built package at /Users/tsutton/AdobeCC_Complete-2015.05.27.pkg
** Done.

Since I use Munki, and this package can only really be properly “removed” using an uninstall script, this tool can also import the resultant package into Munki and set the appropriate uninstall_script key with an uninstall script that will be populated with the appropriate LEID. Either way the uninstall script will be saved to the package’s output directory for your own use in other systems.

See the repo’s GitHub page for more details and documentation about how the package is built.

One of the Mac sysadmin community’s biggest peeves with Adobe’s AAM installer framework is that when failures occur (and they happen a lot), useful error codes are rarely printed in the context in which one normally monitors package installations (for example /var/log/install.log). Adobe documents their error codes on their website, and so the install/uninstall scripts generated by this package actually report this info to standard output/error so you can at least immediately get a short description of why any failures might have occurred. There will always be full debug output in the various AAM logs, but the locations of these files are rarely easily discoverable or well-named (for example, ~/Library/Logs/oobelib.log).

This tool hasn’t been widely tested (thanks to Patrick Fergus again for his help testing the functionality with an Enterprise license), and it will probably be getting some tweaks or fixes over time.

Moving on, if you were using Munki or some other software management system (and hopefully you are using one of these), how would you “scope” how these licenses get deployed to machines? We’ll look at a short example using Munki in the next post.

Tagged , , , | 3 Responses

Adobe Creative Cloud Deployment – Overview

EnterpriseApp_256.pngAdobe’s Creative Cloud licensing models add some new layers of complexity surrounding large-scale deployment in organizations. As I’ve been planning and testing our rollout in areas with managed, shared workstations I’m routinely uncovering new information, and the parts of this I think might be useful to others I will cover in several posts. There are several aspects here: 1) simply wrapping one’s head around the different licensing models, 2) understanding differences in the mechanisms with which these licenses can be deployed to machines, and 3) how to maintain all of all this using a software management system such as Munki or Casper. While I can only speak with experience with a subset of the licensing types and my management tool of choice (Munki), this may be useful if you have some of these in common, or you may also be able to port some specifics to another management system.

An additional preface to these posts: Having been looking into this for quite some time I still regularly feel like I’m stumbling in the dark, I cannot keep any of the license agreement acronyms in my head for more than several minutes and in general I usually feel like I’m doing this wrong. Lacking any better guidance, however, I’m documenting some of my findings. I expect to need to revise these strategies over time.

Thanks to Patrick Fergus, who provided some additional details and clarifications about the different license types. Some of the points below are his words verbatim. Patrick has also written a number of very detailed posts on subjects I’m covering in these posts.

First, let’s review some of the new subscription-based licensing models and how that affects the mechanisms used to deploy Creative Cloud.

There are two new axes along which we can categorize licenses:

  • A license agreement type of either Teams (including education-focused licenses) or Enterprise
  • A type of license, including “Named” and “Device” (for education) or “Serial Number” (for enterprise)

Named licenses require sign-in to use the software, and these sign-ins come in three different flavors:

  • Adobe IDs, which are owned by the user and authenticated by Adobe
  • Enterprise IDs, which are owned by the organization and authenticated by Adobe
  • Federated IDs, which are owned by the organization and authenticated by the organization via SAML

Non-sign-in licenses include:

  • Device licenses are “activated” to a machine and consume a license from a “pool” for as long as that machine is activated. Different pools will exist for different product collections.
  • Serial Number Licenses “activated” to a machine and do not report back to Adobe when they are used

Caveat: Because my organization doesn’t have an Enterprise agreement, I cannot speak with actual experience with that licensing model. The approaches I talk about with respect to the “Device License” should mostly apply to the “Serial Number” model used by Enterprise agreements, however.

Here’s a screenshot borrowed from one of Adobe’s help pages on the subject. Note how Education categories can be found in the Teams (top) and Enterprise (bottom) agreements:


Enterprise agreements have the benefit, besides apparently greatly reduced cost per license, of not needing to track individual device “activations” due to Adobe allowing “anonymous” serialized activation.

If you’ll be deploying device/serial licenses, you need some way to automate the installation of the license. Adobe offers two approaches, built around their Creative Cloud Packager application

  1. Create a device-licensed package, which will contain one or more apps and also deploy the activation when the package is installed. This process also creates an uninstaller that will remove the apps and deactivate that license.
  2. Create a license file, which allows us to “migrate previously deployed named user or trial packages to serial number licenses or device licenses”: This outputs four files, which Adobe calls a “package.” It is not – it is four files, created in a directory, with no accompanying explanation. Presumably we can use this to activate and deactivate a license? (Keep reading to find out!)


The first seems like a sane option; the application(s) and license are included as a single package bundled together. Munki even supports importing these in a single step along with the accompanying uninstaller package, and has special logic tailored to support uninstalling these, while still using Adobe’s provided uninstallers. This works well if you don’t anticipating mixing Named and Device/Serial licenses, and are doing all licenses from the same pool, or a small, manageable number of them.

If however, your org will also be using Named licenses, or you expect to find yourself handling device licenses in various pools and want to just treat the device license or serial separate from the actual application installers and manage them independently, option (2) (creating a device license file independent of the application) seems to make more sense.

Nick McSpadden and Patrick Fergus also discovered a critical problem with (1), if one creates multiple device license packages from the same pool, for example creating a separate Photoshop and After Effects package both from a “Complete” pool, or multiple serial number packages with the same serial number, removing any one of these licensed application packages will uninstall the license as well.

This is not an issue that would affect everyone – despite moving away from the “Creative Suite [X] Premium” product model, the “pools” (or serial numbers) are still logical collections of applications, so it’s possible that one might just build packages containing all the applications from a pool and not consider a need to add or remove individual applications from this pool on an ongoing basis.

It affects me, however: with many subscriptions to the Complete pool while still not needing half of the applications for many of our workstations, I’m instead opting to build individual application installers that I’d still like to be able to manage atomically without needing to worry that removing one product will cause another to cease functioning. An unlicensed Creative Cloud installation prompts a user with a completely hostile dialog prompt:


Karl Gibson of the Adobe IT Toolkit team has acknowledged that this is a bug, and it’s scheduled to be addressed in an upcoming update. Also, Nick McSpadden has documented his solution to this “overlapping” install/uninstall issue, which is to combine the licensed installer with the “Named” (ie. unlicensed) uninstaller, so that if a product is removed using the uninstall pkg, the machine remains licensed. For serial number installations this is perhaps more feasible because serial number installations are “anonymous,” and an active installation doesn’t consume a license from an (expensive) pool of licenses.

So, solution (2) it is for me, at least as of today. This is partly to mitigate this bug, and partly to offer a more flexible workflow as the deployment of Creative Cloud pans out. In my environment we’ll most likely be seeing use of both Named and Device licenses, so it is also helpful to be not building and tracking duplicate packages for the same applications.

Update (Jul 2, 2015): Unfortunately, (2) doesn’t currently work in my testing of deploying license files for use with the 2015 apps. The apps install, but I immediately see a “Sign In Required” prompt on launch. They seem to work fine when deployed as part of an all-in-one device/serialized installer. I’m awaiting confirmation from the Adobe team responsible for CCP about this issue. Nick McSpadden has written a 2015 version of the blog post above covering his use of the method linked to just above.

Update (Jul 15, 2015): A new minor release of CCP came out recently, and I used it to rebuild another licensing file. I noted that the adobe_prtk that comes with this one is a newer (9.x) version. A licensing file from this build seems to work for both 2014 and 2015 applications. Adobe was never able to reproduce the issue, but I can reliably reproduce that a license file built from a CCP two weeks after the 2015 apps were released doesn’t work, while one built with the very latest build of CCP works. This doesn’t further inspire confidence..

In posts which will soon follow, I’ll cover the steps involved to build an OS X installer package from CCP’s “Device File Package [sic]”, a couple simple approaches to managing this license package using Munki, and some odds and ends.

Tagged , , | 3 Responses

Upcoming conference talks for 2015

Pepijn Bruienne just posted a nice summary of the Apple administration-focused conferences coming up in 2015. I’m also happy to be a small part of several of those coming up:

Anthony Reimer has organized for its second year the MacDeployment workshop, hosted at the University of Calgary’s Integrated Arts Media Labs. I’m looking forward to visiting as the IAML seems similar to the environment I support at Concordia University’s Faculty of Fine Arts, and the Prairies are one of the only parts of Canada I’ve not yet visited.

Thanks to some great timing, one day later I’ll be speaking at the new MacDevOps YVR conference taking place at Simon Fraser University in Vancouver, organized by Mat X and Brian Warsing. Mat and Brian have recruited a great lineup of speakers, so it’s going to be a very packed day. I was born in BC but didn’t grow up there, and it will be almost exactly 15 years since I was last in Vancouver.

These two days (June 18-19) I’ll be giving an introduction to Python in the context of Mac administration.

Finally, I’m lucky to be returning to Göteborg, Sweden for MacSysAdmin 2015 on September 29 through October 2. It was an absolute pleasure last year to attend, speak and meet so many members of our community, thanks to Tycho – and I’m looking forward to traveling there again. This time I’ll be giving a tour and demoing some of my Mac sysadmin tools I maintain on GitHub.

Hope to see you at these great events!

Tagged | Leave a comment