Cooking with Cinc

So what’s cooking?

As part of a private project I’m looking to deploy a Goiardi server, and what better way to do so than with Cinc Client? My first stop was, as always, the Chef Supermarket, where one can find excellent cookbooks to feed into Cinc. There I found this cookbook by Matt Whiteley.

It’s a little bit dated, but that’s an easy issue to solve; We’ll update it! The new trend in community cookbooks is to write ‘resource cookbooks’, that is cookbooks that define custom resources and libraries but no recipes. I therefor set out to write a custom resource to install and manage a goiardi instance.

Cinc + Test Kitchen

After a bit of keyboard smashing I was ready for some kitchen magic. I didn’t need any new plugins or gems, just a few lines in my cookbook’s kitchen.yml:

  name: chef_zero
  require_chef_omnibus: true
  chef_omnibus_root: /opt/cinc

Using the usual chef-zero provisioner, I simply point kitchen to the Cinc Project’s Omnitruck and to the correct folder. Then when I run kitchen test:

-----> Installing Chef install only if missing package
       Downloading to file /tmp/
       Trying curl...
       Download complete.
       el 7 x86_64
       Getting information for cinc stable  for el...
         to file /tmp/
       Updating / installing...
          1:cinc-15.5.15-1.el7               ################################# [100%]
       Symlinking chef-apply command to cinc-wrapper for compatibility...
       Symlinking chef-client command to cinc-wrapper for compatibility...
       Symlinking chef-shell command to cinc-wrapper for compatibility...
       Symlinking chef-solo command to cinc-wrapper for compatibility...
       Thank you for installing Cinc Client, the community build based on Chef Infra Client!
       Transferring files to <remove-centos-7>
       Redirecting to cinc-client...
       Starting Cinc Client, version 15.5.15

And now we’re testing with Cinc! You’ll note there was no license prompt, as you’d expect from a free-as-in-beer distribution.

But now my files are full of lies

One thing I like to do in my file and template resources is to add a “This is a Chef generated file” type disclaimer. But this isn’t a Chef generated file, it’s a Cinc generated file! If I just put Cinc, then it shows Cinc to a Chef Infra™ user too. Thankfully that’s another easy solve. We can call on the distribution constants implemented by the Cinc Project upstream like so:

require 'chef/dist'

file '/tmp/a_file' do
  content "This file was generated by #{Chef::Dist::PRODUCT}"
  action :create

Now when my cookbook writes /tmp/a_file, it’ll output the name of the product you’re using, whether that’s Cinc, Chef Infra™ or MyOrgPrivateDistroOfChefInfraClient (please don’t name it that, for the sanity of your users o.O ). You can find a complete list of these distribution constants in (don’t forget to navigate to the appropriate tag for your version!).

Do note this is the first implementation of distro constants and unlikely to be the last. While I’m excited to share this little trick with you all I also feel I should warn against using it just yet without some sort of safeguard against having a constant pulled from under you. Said safeguard can be as simple as:

require 'chef/dist'
product = Chef::Dist::PRODUCT || 'A Configuration Manager'
log "This log resource is being executed by #{product}"

Back to my cookbook!

So I wrote a resource called goiardi_install, tested it with Cinc in test-kitchen, and adjusted my templates so they output the correct product name to all the cookbook’s users. What’s left? Publishing of course! The initial intent was to PR the resources to the goiardi cookbook but following some discussions on Slack we opted to release it as cinc-goiardi and to officially support it, since we currently recommend Goiardi as a FOSS Chef Infra™ server alternative. With the resources published, I wrote a quick and dirty wrapping recipe:

# Recipe my_goiardi::default

goiardi_install 'goiardi' do
  version '0.11.10'

And voila! We can run that through Chef Infra™ or Cinc Client seamlessly.