Versioned Environments

Hi All,

I am looking for the best way for versioning the multiple environments.
For instance, we have now 3 main environments (like dev, staging and
production) Now we want to have multiple environment versions per each of
these three (dev/ver1, production/ver2, etc.)
Although I didn’t find any Chef way to achieve that, I wonder if any of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !


Michael L.

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your cookbooks
in metadata.rb, and have specific versions of your cookbook available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind bigmyx@gmail.com wrote:

Hi All,

I am looking for the best way for versioning the multiple environments.
For instance, we have now 3 main environments (like dev, staging and
production) Now we want to have multiple environment versions per each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if any of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

Hi Mike,

Thanks for your reply,
Yes we use internal chef cookbook versions all the time, but this time we want to use the similar for the environment.
I know environments do not support it, and I wonder of there some "nice" workaround for this ..

On Oct 11, 2012, at 1:43 PM, Mike miketheman@gmail.com wrote:

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your cookbooks
in metadata.rb, and have specific versions of your cookbook available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind bigmyx@gmail.com wrote:

Hi All,

I am looking for the best way for versioning the multiple environments.
For instance, we have now 3 main environments (like dev, staging and
production) Now we want to have multiple environment versions per each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if any of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

I've implemented this as a series of environments that get promoted into/out of. Basically take the environment policy and attributes from A and slam them into B.

Adam

On Oct 11, 2012, at 5:39 AM, Michael Leikind wrote:

Hi Mike,

Thanks for your reply,
Yes we use internal chef cookbook versions all the time, but this time we want to use the similar for the environment.
I know environments do not support it, and I wonder of there some "nice" workaround for this ..

On Oct 11, 2012, at 1:43 PM, Mike miketheman@gmail.com wrote:

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your cookbooks
in metadata.rb, and have specific versions of your cookbook available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind bigmyx@gmail.com wrote:

Hi All,

I am looking for the best way for versioning the multiple environments.
For instance, we have now 3 main environments (like dev, staging and
production) Now we want to have multiple environment versions per each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if any of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

I implemented application swim lanes as a data bag per application
with environments as items and the top-level keys being lanes.
( So, production has four instances per app, each instance has a
version and maybe some custom attributes you use in a config template
or something. )

After that, it's just a matter of retrieving the appropriate data bag
item for the environment and doing a for loop.

If you spend a bit of time up front writing the cookbook with this in
mind, you can support additional lanes very easily -- just update the
application data bag.

On Thu, Oct 11, 2012 at 9:36 AM, Adam Jacob adam@opscode.com wrote:

I've implemented this as a series of environments that get promoted into/out of. Basically take the environment policy and attributes from A and slam them into B.

Adam

On Oct 11, 2012, at 5:39 AM, Michael Leikind wrote:

Hi Mike,

Thanks for your reply,
Yes we use internal chef cookbook versions all the time, but this time we want to use the similar for the environment.
I know environments do not support it, and I wonder of there some "nice" workaround for this ..

On Oct 11, 2012, at 1:43 PM, Mike miketheman@gmail.com wrote:

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your cookbooks
in metadata.rb, and have specific versions of your cookbook available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind bigmyx@gmail.com wrote:

Hi All,

I am looking for the best way for versioning the multiple environments.
For instance, we have now 3 main environments (like dev, staging and
production) Now we want to have multiple environment versions per each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if any of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

Sounds interesting, would you mind posting an example of your data bag?

Cheers, Torben
Am 11.10.2012 20:26 schrieb "steve ." leftathome@gmail.com:

I implemented application swim lanes as a data bag per application
with environments as items and the top-level keys being lanes.
( So, production has four instances per app, each instance has a
version and maybe some custom attributes you use in a config template
or something. )

After that, it's just a matter of retrieving the appropriate data bag
item for the environment and doing a for loop.

If you spend a bit of time up front writing the cookbook with this in
mind, you can support additional lanes very easily -- just update the
application data bag.

On Thu, Oct 11, 2012 at 9:36 AM, Adam Jacob adam@opscode.com wrote:

I've implemented this as a series of environments that get promoted
into/out of. Basically take the environment policy and attributes from A
and slam them into B.

Adam

On Oct 11, 2012, at 5:39 AM, Michael Leikind wrote:

Hi Mike,

Thanks for your reply,
Yes we use internal chef cookbook versions all the time, but this time
we want to use the similar for the environment.
I know environments do not support it, and I wonder of there some
"nice" workaround for this ..

On Oct 11, 2012, at 1:43 PM, Mike miketheman@gmail.com wrote:

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your cookbooks
in metadata.rb, and have specific versions of your cookbook available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind bigmyx@gmail.com
wrote:

Hi All,

I am looking for the best way for versioning the multiple
environments.
For instance, we have now 3 main environments (like dev, staging and
production) Now we want to have multiple environment versions per
each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if any
of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

Sure!

For application 'app' in environments 'dev' and 'live' your data bag
might look like this:

"app": {
"dev": {
"0": {
"version": "0.16.1"
"active": "0"
}
"1": {
"version": "0.11.0"
"active": "1"
}
}
"live": {
"0": {
"version": "0.6.1"
"active": "1"
}
"1": {
"version": "0.6.2"
"active": "0"
}
}
}

Hope that helps.

On Fri, Oct 12, 2012 at 10:28 AM, Torben Knerr ukio@gmx.de wrote:

Sounds interesting, would you mind posting an example of your data bag?

Cheers, Torben

Am 11.10.2012 20:26 schrieb "steve ." leftathome@gmail.com:

I implemented application swim lanes as a data bag per application
with environments as items and the top-level keys being lanes.
( So, production has four instances per app, each instance has a
version and maybe some custom attributes you use in a config template
or something. )

After that, it's just a matter of retrieving the appropriate data bag
item for the environment and doing a for loop.

If you spend a bit of time up front writing the cookbook with this in
mind, you can support additional lanes very easily -- just update the
application data bag.

On Thu, Oct 11, 2012 at 9:36 AM, Adam Jacob adam@opscode.com wrote:

I've implemented this as a series of environments that get promoted
into/out of. Basically take the environment policy and attributes from A and
slam them into B.

Adam

On Oct 11, 2012, at 5:39 AM, Michael Leikind wrote:

Hi Mike,

Thanks for your reply,
Yes we use internal chef cookbook versions all the time, but this time
we want to use the similar for the environment.
I know environments do not support it, and I wonder of there some
"nice" workaround for this ..

On Oct 11, 2012, at 1:43 PM, Mike miketheman@gmail.com wrote:

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your cookbooks
in metadata.rb, and have specific versions of your cookbook available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind bigmyx@gmail.com
wrote:

Hi All,

I am looking for the best way for versioning the multiple
environments.
For instance, we have now 3 main environments (like dev, staging and
production) Now we want to have multiple environment versions per
each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if any
of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

Cool, thanks!

On Fri, Oct 12, 2012 at 11:52 PM, steve . leftathome@gmail.com wrote:

Sure!

For application 'app' in environments 'dev' and 'live' your data bag
might look like this:

"app": {
"dev": {
"0": {
"version": "0.16.1"
"active": "0"
}
"1": {
"version": "0.11.0"
"active": "1"
}
}
"live": {
"0": {
"version": "0.6.1"
"active": "1"
}
"1": {
"version": "0.6.2"
"active": "0"
}
}
}

Hope that helps.

On Fri, Oct 12, 2012 at 10:28 AM, Torben Knerr ukio@gmx.de wrote:

Sounds interesting, would you mind posting an example of your data bag?

Cheers, Torben

Am 11.10.2012 20:26 schrieb "steve ." leftathome@gmail.com:

I implemented application swim lanes as a data bag per application
with environments as items and the top-level keys being lanes.
( So, production has four instances per app, each instance has a
version and maybe some custom attributes you use in a config template
or something. )

After that, it's just a matter of retrieving the appropriate data bag
item for the environment and doing a for loop.

If you spend a bit of time up front writing the cookbook with this in
mind, you can support additional lanes very easily -- just update the
application data bag.

On Thu, Oct 11, 2012 at 9:36 AM, Adam Jacob adam@opscode.com wrote:

I've implemented this as a series of environments that get promoted
into/out of. Basically take the environment policy and attributes
from A and
slam them into B.

Adam

On Oct 11, 2012, at 5:39 AM, Michael Leikind wrote:

Hi Mike,

Thanks for your reply,
Yes we use internal chef cookbook versions all the time, but this
time
we want to use the similar for the environment.
I know environments do not support it, and I wonder of there some
"nice" workaround for this ..

On Oct 11, 2012, at 1:43 PM, Mike miketheman@gmail.com wrote:

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your cookbooks
in metadata.rb, and have specific versions of your cookbook
available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind bigmyx@gmail.com
wrote:

Hi All,

I am looking for the best way for versioning the multiple
environments.
For instance, we have now 3 main environments (like dev, staging
and
production) Now we want to have multiple environment versions per
each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if
any
of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

This has been a hot topic for us. We have multiple data centers that use
one chef server as the source. As we have multiple front end load
balancers that can either be running a different version of things or is in
the process of going through a rolling upgrade, we've had to avoid role or
environment clobbering.

When a node launches it knows what role it's supposed to be. We've
implemented what I call fancy roles. They are versioned by a name/date
combination and cookbooks are versioned inside of the role. In the code
repository we have separate directories for prod/stage/dev. For us it's a
matter of spinning up a new farm of nodes with a specific name/date role or
updating the running node to the new role. It does create some duplication
but what we felt was the safest for having a set of nodes that need to
maintain a specific version of state or waiting to be upgraded.

It would be incredibly nice if Chef had the same versioning concept for
roles or environments that cookbooks have.

On Sat, Oct 13, 2012 at 4:25 AM, Torben Knerr ukio@gmx.de wrote:

Cool, thanks!

On Fri, Oct 12, 2012 at 11:52 PM, steve . leftathome@gmail.com wrote:

Sure!

For application 'app' in environments 'dev' and 'live' your data bag
might look like this:

"app": {
"dev": {
"0": {
"version": "0.16.1"
"active": "0"
}
"1": {
"version": "0.11.0"
"active": "1"
}
}
"live": {
"0": {
"version": "0.6.1"
"active": "1"
}
"1": {
"version": "0.6.2"
"active": "0"
}
}
}

Hope that helps.

On Fri, Oct 12, 2012 at 10:28 AM, Torben Knerr ukio@gmx.de wrote:

Sounds interesting, would you mind posting an example of your data bag?

Cheers, Torben

Am 11.10.2012 20:26 schrieb "steve ." leftathome@gmail.com:

I implemented application swim lanes as a data bag per application
with environments as items and the top-level keys being lanes.
( So, production has four instances per app, each instance has a
version and maybe some custom attributes you use in a config template
or something. )

After that, it's just a matter of retrieving the appropriate data bag
item for the environment and doing a for loop.

If you spend a bit of time up front writing the cookbook with this in
mind, you can support additional lanes very easily -- just update the
application data bag.

On Thu, Oct 11, 2012 at 9:36 AM, Adam Jacob adam@opscode.com wrote:

I've implemented this as a series of environments that get promoted
into/out of. Basically take the environment policy and attributes
from A and
slam them into B.

Adam

On Oct 11, 2012, at 5:39 AM, Michael Leikind wrote:

Hi Mike,

Thanks for your reply,
Yes we use internal chef cookbook versions all the time, but this
time
we want to use the similar for the environment.
I know environments do not support it, and I wonder of there some
"nice" workaround for this ..

On Oct 11, 2012, at 1:43 PM, Mike miketheman@gmail.com wrote:

I guess I'd be curious to understand the "versioning" of an
environment - is the app code currently version1 on dev, and now
you
want a version2 dev environment? Or is the versioning for
chef-specific code?

If it is for chef cookbooks and such, you can version your
cookbooks
in metadata.rb, and have specific versions of your cookbook
available
for a given environment.

i.e.:
"prod" => cookbook "myapplication", "= 0.1.0"
"dev" => cookbook "myapplication", "= 0.2.0"

So any changes to the cookbook code (as long as you increment the
version in metadata.rb) will not be applied to an environment that
does not match the version constraints.

(Read more on version constraints:
http://wiki.opscode.com/display/chef/Version+Constraints )

On Thu, Oct 11, 2012 at 7:27 AM, Michael Leikind <bigmyx@gmail.com

wrote:

Hi All,

I am looking for the best way for versioning the multiple
environments.
For instance, we have now 3 main environments (like dev, staging
and
production) Now we want to have multiple environment versions per
each of
these three (dev/ver1, production/ver2, etc.)
Although I didn't find any Chef way to achieve that, I wonder if
any
of you
have done this and what is the logic.
As a side note, we are using Git for source control.

thanks !

--

--
Michael L.

Hi,

On Sun, Oct 14, 2012 at 1:32 AM, Bryan Brandau agent462@gmail.com wrote:

It would be incredibly nice if Chef had the same versioning concept for
roles or environments that cookbooks have.

I wonder if that is really needed. As soon as you version roles is there
any real difference between them and cookbooks? Initially our
infrastructure included a heap of roles that included attributes and
recipes. As we evolved we found the need to version of the attributes and
recipes. Slowly our roles evolved to what they are today. So our "graphite"
role simply includes the "base_linux_server" role and the "fisg-graphite"
recipe and all of our configuration and recipe inclusion occurs
within "fisg-graphite". Except for a few of our windows nodes, all of our
roles have a 1-to-1 mapping to cookbooks. The role is simply a simplified
tag that includes the relevant "role cookbook".

That way we can version the role cookbooks using the same mechanism we
version the other cookbooks

--
Cheers,

Peter Donald

Fully agree. In fact there seems to be something missing inbetween
cookbooks and roles that dosen't have a name yet.

Peter calls it "role cookbooks", and the guys at riotGames call them
"application cookbooks" I believe (not to be confused with the
"application" cookbook).

However it is called it seems to be a common pattern because you typically
want to compose individual cookbooks. So you start with a role, but then
you notice that

  • roles are not versioned
  • so you can't dependency manage roles
  • so they don't live in their own git repository but rather in a specific
    chef repo
  • so they are not reusable across chef repositories
  • etc..

Initially I thought that putting version numbers in roles and extending
tools like librarian and berkshelf to support role dependency management
would be a good idea. But then I noticed that a "role cookbook" would be
way better, because:

  • its already supported with the tools we have now
  • you typically need a place where you use the LWRPs provided by other
    cookbooks - you can't do that in roles
  • having it as a cookbook it can live in its own git repo, can be tested in
    isolation, can be dependency-managed and easily reused across chef repos
  • until some days ago I also thought this would be the only way to strictly
    version dependencies (via metadata.rb), but then I learned that there is a
    syntax in roles as well that allows you to pin down cookbook (or rather
    recipe) versions (e.g. "mysql@1.0.0"), so this dosen't really count
  • finally, when aggregating multiple cookbooks / recipes, you typically
    want to expose only a subset of the included cookbook's attributes for
    configuration. This is the chance to explicitly define and document the
    configurable attributes in the "role cookbook" if you prefer

Once you have a "role cookbook" it typically maps 1:1 to a role, but I
could also imagine roles which have a "role cookbook" and some extra
recipes in their runlist.

I haven't seen this pattern documented anywhere, except that it comes up on
the mailing list every now an then. Wouldn't this be something for the
Opscode Wiki?

And what would be a good name for it, e.g. "application cookbook", "role
cookbook", "fancy cookbook", or something like "aggregation cookbook"?

Cheers, Torben

Am 14.10.2012 23:38 schrieb "Peter Donald" peter@realityforge.org:

Hi,

On Sun, Oct 14, 2012 at 1:32 AM, Bryan Brandau agent462@gmail.com wrote:

It would be incredibly nice if Chef had the same versioning concept for
roles or environments that cookbooks have.

I wonder if that is really needed. As soon as you version roles is there
any real difference between them and cookbooks? Initially our
infrastructure included a heap of roles that included attributes and
recipes. As we evolved we found the need to version of the attributes and
recipes. Slowly our roles evolved to what they are today. So our "graphite"
role simply includes the "base_linux_server" role and the "fisg-graphite"
recipe and all of our configuration and recipe inclusion occurs
within "fisg-graphite". Except for a few of our windows nodes, all of our
roles have a 1-to-1 mapping to cookbooks. The role is simply a simplified
tag that includes the relevant "role cookbook".

That way we can version the role cookbooks using the same mechanism we
version the other cookbooks

--
Cheers,

Peter Donald

Roles are data, not code.

Code is often packaged-up and redistributed, but data typically isn't. A
code package will have a version, and will depend on other code packages,
but data won't.

The goal should be to minimize the input data, which is roles. You can do
this by moving as much as you can into code, using sensible defaults,
computing derived values from given values, writing infrastructure-specific
non-redistributable cookbooks, etc. That way you can pull the
implementation details out of your roles as much as possible, since roles
are not data. That way your roles are just there to group related nodes
under the same name, but not really to do the heavy lifting, and your input
data is minimized.

Cheers,
Jay

On Mon, Oct 15, 2012 at 3:16 AM, Torben Knerr ukio@gmx.de wrote:

Fully agree. In fact there seems to be something missing inbetween
cookbooks and roles that dosen't have a name yet.

Peter calls it "role cookbooks", and the guys at riotGames call them
"application cookbooks" I believe (not to be confused with the
"application" cookbook).

However it is called it seems to be a common pattern because you typically
want to compose individual cookbooks. So you start with a role, but then
you notice that

  • roles are not versioned
  • so you can't dependency manage roles
  • so they don't live in their own git repository but rather in a specific
    chef repo
  • so they are not reusable across chef repositories
  • etc..

Initially I thought that putting version numbers in roles and extending
tools like librarian and berkshelf to support role dependency management
would be a good idea. But then I noticed that a "role cookbook" would be
way better, because:

  • its already supported with the tools we have now
  • you typically need a place where you use the LWRPs provided by other
    cookbooks - you can't do that in roles
  • having it as a cookbook it can live in its own git repo, can be tested
    in isolation, can be dependency-managed and easily reused across chef repos
  • until some days ago I also thought this would be the only way to
    strictly version dependencies (via metadata.rb), but then I learned that
    there is a syntax in roles as well that allows you to pin down cookbook (or
    rather recipe) versions (e.g. "mysql@1.0.0"), so this dosen't really count
  • finally, when aggregating multiple cookbooks / recipes, you typically
    want to expose only a subset of the included cookbook's attributes for
    configuration. This is the chance to explicitly define and document the
    configurable attributes in the "role cookbook" if you prefer

Once you have a "role cookbook" it typically maps 1:1 to a role, but I
could also imagine roles which have a "role cookbook" and some extra
recipes in their runlist.

I haven't seen this pattern documented anywhere, except that it comes up
on the mailing list every now an then. Wouldn't this be something for the
Opscode Wiki?

And what would be a good name for it, e.g. "application cookbook", "role
cookbook", "fancy cookbook", or something like "aggregation cookbook"?

Cheers, Torben

Am 14.10.2012 23:38 schrieb "Peter Donald" peter@realityforge.org:

Hi,

On Sun, Oct 14, 2012 at 1:32 AM, Bryan Brandau agent462@gmail.com
wrote:

It would be incredibly nice if Chef had the same versioning concept for
roles or environments that cookbooks have.

I wonder if that is really needed. As soon as you version roles is there
any real difference between them and cookbooks? Initially our
infrastructure included a heap of roles that included attributes and
recipes. As we evolved we found the need to version of the attributes and
recipes. Slowly our roles evolved to what they are today. So our "graphite"
role simply includes the "base_linux_server" role and the "fisg-graphite"
recipe and all of our configuration and recipe inclusion occurs
within "fisg-graphite". Except for a few of our windows nodes, all of our
roles have a 1-to-1 mapping to cookbooks. The role is simply a simplified
tag that includes the relevant "role cookbook".

That way we can version the role cookbooks using the same mechanism we
version the other cookbooks

--
Cheers,

Peter Donald

On Oct 14, 2012, at 2:38 PM, Peter Donald <peter@realityforge.orgmailto:peter@realityforge.org> wrote:
On Sun, Oct 14, 2012 at 1:32 AM, Bryan Brandau <agent462@gmail.commailto:agent462@gmail.com> wrote:
It would be incredibly nice if Chef had the same versioning concept for roles or environments that cookbooks have.

I wonder if that is really needed. As soon as you version roles is there any real difference between them and cookbooks? Initially our infrastructure included a heap of roles that included attributes and recipes. As we evolved we found the need to version of the attributes and recipes. Slowly our roles evolved to what they are today. So our “graphite” role simply includes the “base_linux_server” role and the “fisg-graphite” recipe and all of our configuration and recipe inclusion occurs within “fisg-graphite”. Except for a few of our windows nodes, all of our roles have a 1-to-1 mapping to cookbooks. The role is simply a simplified tag that includes the relevant “role cookbook”.

That way we can version the role cookbooks using the same mechanism we version the other cookbooks

This is what my experience has been as well. You have great places for dynamism in Chef - it’s in the cookbooks themselves, and they need to be aware of the various states the infrastructure should be in. Trying to manage that evolution (“I have 3 different desired states”) purely through the application of ever more intricate version pinnings is a game that ends with disaster (ask anyone who tries to manage packages this way).

What I’ve seen work in the past six months or so, more than once:

  • Have environments that are pinned to equality for every cookbook
  • Have any logic about what needs to happen dynamically embedded in the cookbooks

Best,
Adam

+1!

Adam

On Oct 15, 2012, at 4:18 AM, Jay Feldblum <y_feldblum@yahoo.commailto:y_feldblum@yahoo.com> wrote:

Roles are data, not code.

Code is often packaged-up and redistributed, but data typically isn't. A code package will have a version, and will depend on other code packages, but data won't.

The goal should be to minimize the input data, which is roles. You can do this by moving as much as you can into code, using sensible defaults, computing derived values from given values, writing infrastructure-specific non-redistributable cookbooks, etc. That way you can pull the implementation details out of your roles as much as possible, since roles are not data. That way your roles are just there to group related nodes under the same name, but not really to do the heavy lifting, and your input data is minimized.

Cheers,
Jay

On Mon, Oct 15, 2012 at 3:16 AM, Torben Knerr <ukio@gmx.demailto:ukio@gmx.de> wrote:

Fully agree. In fact there seems to be something missing inbetween cookbooks and roles that dosen't have a name yet.

Peter calls it "role cookbooks", and the guys at riotGames call them "application cookbooks" I believe (not to be confused with the "application" cookbook).

However it is called it seems to be a common pattern because you typically want to compose individual cookbooks. So you start with a role, but then you notice that

  • roles are not versioned
  • so you can't dependency manage roles
  • so they don't live in their own git repository but rather in a specific chef repo
  • so they are not reusable across chef repositories
  • etc..

Initially I thought that putting version numbers in roles and extending tools like librarian and berkshelf to support role dependency management would be a good idea. But then I noticed that a "role cookbook" would be way better, because:

  • its already supported with the tools we have now
  • you typically need a place where you use the LWRPs provided by other cookbooks - you can't do that in roles
  • having it as a cookbook it can live in its own git repo, can be tested in isolation, can be dependency-managed and easily reused across chef repos
  • until some days ago I also thought this would be the only way to strictly version dependencies (via metadata.rb), but then I learned that there is a syntax in roles as well that allows you to pin down cookbook (or rather recipe) versions (e.g. "mysql@1.0.0mailto:mysql@1.0.0"), so this dosen't really count
  • finally, when aggregating multiple cookbooks / recipes, you typically want to expose only a subset of the included cookbook's attributes for configuration. This is the chance to explicitly define and document the configurable attributes in the "role cookbook" if you prefer

Once you have a "role cookbook" it typically maps 1:1 to a role, but I could also imagine roles which have a "role cookbook" and some extra recipes in their runlist.

I haven't seen this pattern documented anywhere, except that it comes up on the mailing list every now an then. Wouldn't this be something for the Opscode Wiki?

And what would be a good name for it, e.g. "application cookbook", "role cookbook", "fancy cookbook", or something like "aggregation cookbook"?

Cheers, Torben

Am 14.10.2012 23:38 schrieb "Peter Donald" <peter@realityforge.orgmailto:peter@realityforge.org>:

Hi,

On Sun, Oct 14, 2012 at 1:32 AM, Bryan Brandau <agent462@gmail.commailto:agent462@gmail.com> wrote:

It would be incredibly nice if Chef had the same versioning concept for roles or environments that cookbooks have.

I wonder if that is really needed. As soon as you version roles is there any real difference between them and cookbooks? Initially our infrastructure included a heap of roles that included attributes and recipes. As we evolved we found the need to version of the attributes and recipes. Slowly our roles evolved to what they are today. So our "graphite" role simply includes the "base_linux_server" role and the "fisg-graphite" recipe and all of our configuration and recipe inclusion occurs within "fisg-graphite". Except for a few of our windows nodes, all of our roles have a 1-to-1 mapping to cookbooks. The role is simply a simplified tag that includes the relevant "role cookbook".

That way we can version the role cookbooks using the same mechanism we version the other cookbooks

--
Cheers,

Peter Donald

AMEN. If only I could unsee some of the
things I've seen.

Sascha Bates
| sascha.bates@gmail.com | 612 850 0444 | sascha.bates@skype |
sascha_bates@yahoo |
On 10/15/12 12:43 PM, Adam Jacob wrote:

On Oct 14, 2012, at 2:38 PM, Peter Donald <peter@realityforge.org> wrote:
On Sun, Oct 14, 2012 at 1:32 AM, Bryan Brandau <agent462@gmail.com> wrote:
It would be incredibly nice if Chef had the same versioning concept for roles or environments that cookbooks have.

I wonder if that is really needed. As soon as you version
roles is there any real difference between them and
cookbooks? Initially our infrastructure included a heap of
roles that included attributes and recipes. As we evolved we
found the need to version of the attributes and recipes.
Slowly our roles evolved to what they are today. So our
"graphite" role simply includes the "base_linux_server" role
and the "fisg-graphite" recipe and all of our configuration
and recipe inclusion occurs within "fisg-graphite". Except
for a few of our windows nodes, all of our roles have a
1-to-1 mapping to cookbooks. The role is simply a simplified
tag that includes the relevant "role cookbook".

That way we can version the role cookbooks using the same
mechanism we version the other cookbooks

This is what my experience has been as well. You have great
places for dynamism in Chef - it's in the cookbooks themselves,
and they need to be aware of the various states the
infrastructure should be in. Trying to manage that evolution ("I
have 3 different desired states") purely through the application
of ever more intricate version pinnings is a game that ends with
disaster (ask anyone who tries to manage packages this way).

What I've seen work in the past six months or so, more than
once:

  • Have environments that are pinned to equality for every
    cookbook* Have any logic about what needs to happen dynamically
    embedded in the cookbooks

Best,Adam