Releasing knife-santoku: a drop in replacement for knife that helps you build out internal processes


#1

Ohai Chefs!

We wanted to be able to notify a chatroom whenever anyone made changes to
the chef server, this became more of a problem as the operations team got
larger. I wrote knife-santoku as a drop in replacement for knife that lets
you run arbitrary code before or after any knife command. The primary use
case is matching what command was run and sending off notifications but you
can build out any processes with it.

Today we’re open sourcing it!

Here’s how it works. After you install it you drop your configuration in
config/santoku-config.yml and you drop something like this in
config/santoku-after.rb.

require 'etc’
match /cookbook upload (.*)/ do |cookbook|
notify :hipchat, "#{Etc.getlogin} finished uploading #{cookbook}"
end

match /create/ do
notify :hipchat
end

match /delete/ do
notify :hipchat
end

This will send off notifications whenever anyone creates, or deletes
something from the chef server and as you can see i’ve made a custom
message for the cookbook upload matcher. If you don’t use hipchat all you
need to do is write a custom santoku notifier plugin and you’ll be good to
go.

Hope some of you find this useful. Let me know if there’s anything you want
added or better yet send a pull request.

Thanks,

Kevin Nuckolls
Senior Software Engineer
Mosaik Solutions


#2

On Tue, May 15, 2012 at 11:28 PM, Kevin Nuckolls
kevin.nuckolls@gmail.com wrote:

Ohai Chefs!

We wanted to be able to notify a chatroom whenever anyone made changes to
the chef server, this became more of a problem as the operations team got
larger. I wrote knife-santoku as a drop in replacement for knife that lets
you run arbitrary code before or after any knife command. The primary use
case is matching what command was run and sending off notifications but you
can build out any processes with it.

Interesting. Any reason why you didn’t write this as a knife plugin?

Andrea


#3

Yep there were a few reasons. Mostly I tend to believe in writing the least
amount of code to solve the problem and to keep it as decoupled as
possible. Looking at the knife plugin documentation I came across this
page[1] about calling other knife plugins from within a knife plugin. As
you can see from that link it becomes a rather programmatic process. You
have to load the specific plugin you’re interested in calling, instantiate
it, configure it, and launch it by hand.

I wanted this to work with whatever plugins you may happen to have
installed so it seemed like there were three routes I could go down. I
could write a lightweight wrapper for knife that shims in two callback
functions (before and after the knife instantiation), I could go down the
path of writing all the ruby metaprogramming needed to generalize the
"calling a plugin within another plugin" code, or I could fork knife and
add in the code there directly.

The other problem with making it a knife plugin is that I wanted it to be
seamless. You don’t have to learn any new commands, it should “just work”.
I wasn’t interested in replicating what knife already does well, and I
wasn’t interested in forking knife at this point in time. The compromise
solution was to just monkeypatch one very small part of knife[2] to keep
everything running smoothly within the code that Opscode wrote and as a gem
maintainer to keep an eye on that function as new releases come out to make
sure that it still behaves as expected.

The most elegant solution is to add actual callback functions all over the
knife codebase that you can hook into in your own knife.rb. I didn’t want
to do that without opscode’s design guidance and frankly my solution was
the quickest, simplest, most flexible, and most maintainable path to a
solution that met the majority of our needs.

Hope that helps!

Kevin Nuckolls
@kevinnuckolls

[1]
http://wiki.opscode.com/display/chef/Knife+Plugins#KnifePlugins-UsingPluginswithinOtherPlugins
[2]

On Wed, May 16, 2012 at 3:39 AM, Andrea Campi
andrea.campi@zephirworks.comwrote:

On Tue, May 15, 2012 at 11:28 PM, Kevin Nuckolls
kevin.nuckolls@gmail.com wrote:

Ohai Chefs!

We wanted to be able to notify a chatroom whenever anyone made changes to
the chef server, this became more of a problem as the operations team got
larger. I wrote knife-santoku as a drop in replacement for knife that
lets
you run arbitrary code before or after any knife command. The primary use
case is matching what command was run and sending off notifications but
you
can build out any processes with it.

Interesting. Any reason why you didn’t write this as a knife plugin?

Andrea


#4

On Wed, May 16, 2012 at 5:03 PM, Kevin Nuckolls
kevin.nuckolls@gmail.com wrote:

The most elegant solution is to add actual callback functions all over the
knife codebase that you can hook into in your own knife.rb. I didn’t want to
do that without opscode’s design guidance and frankly my solution was the
quickest, simplest, most flexible, and most maintainable path to a solution
that met the majority of our needs.

Makes sense :slight_smile:
I’ll give this a spin when I find the time–we use HipChat too so it
would be a very good fit.

Andrea


#5

Glad to hear it. Let me know if there’s anything you’d like added or if you
encounter any bugs.

Thanks!
-Kevin

On Wed, May 16, 2012 at 10:12 AM, Andrea Campi <andrea.campi@zephirworks.com

wrote:

On Wed, May 16, 2012 at 5:03 PM, Kevin Nuckolls
kevin.nuckolls@gmail.com wrote:

The most elegant solution is to add actual callback functions all over
the
knife codebase that you can hook into in your own knife.rb. I didn’t
want to
do that without opscode’s design guidance and frankly my solution was the
quickest, simplest, most flexible, and most maintainable path to a
solution
that met the majority of our needs.

Makes sense :slight_smile:
I’ll give this a spin when I find the time–we use HipChat too so it
would be a very good fit.

Andrea