chef provisioning a chef server cluster - chefconf 2015
TRANSCRIPT
Chef Provisioning a Chef Server ClusterJoshua Timberman [email protected] @jtimberman
https://www.flickr.com/photos/jamidwyer/2844765976
Before we begin, provisioning a Chef Server:• Run chef-client... • Which talks to a different Chef Server... • Which downloads a recipe that... • Creates machines that run chef-client... • That install Chef Server packages... • Which then run chef-server-ctl reconfigure... • Which runs chef-solo to configure the Chef Server
Where are we going*?*And why are we in this handbasket?
https://www.flickr.com/photos/steevithak/6936667291
Bootstrap a Chef Server with Chef Solosudo chef-‐solo \ -‐c /etc/chef/solo.rb \ -‐j ~/chef.json \ -‐r http://s3.amazonaws.com/chef-‐solo/bootstrap-‐latest.tar.gz
chef-server-ctl reconfigurefrontend-‐chef-‐server% sudo chef-‐server-‐ctl reconfigure Starting Chef Client, version 11.18.0 Compiling Cookbooks... Recipe: private-‐chef::default .... Recipe: private-‐chef::default * file[/etc/opscode/chef-‐server-‐running.json] action create (up to date)
Running handlers: Running handlers complete Chef Client finished, 7/228 resources updated in 7.282379304 seconds opscode Reconfigured!
omnibus-ctl reconfigure...def reconfigure(exit_on_success=true) status = run_command( "chef-‐solo -‐c #{base_path}/embedded/cookbooks/solo.rb -‐j #{base_path}/embedded/cookbooks/dna.json" ) if status.success? log "#{display_name} Reconfigured!" exit! 0 if exit_on_success else exit! 1 end end
Hosted Chef... is different (and that's the problem)
• Built using Chef cookbooks • (yay! ...but) • Many forked community cookbooks • (before berkshelf/librarian) • One cookbook per component/service • (postgresql, erchef, authz, rabbitmq, solr, etc) • Growth over time • (over 10k commits) • Not the same as what customers use • (chef-server-ctl reconfigure vs "knife ssh and chef-client")
Hosted Chef's Chef
Server Cluster
Hosted Chef Is a
Chef Server Cluster
VPCOur Use Case:Hosted Chef and its Chef Server running in AWS EC2
Chef Server 12"There is One Chef Server, and it is Open Source" - Adam Jacob
https://www.chef.io/blog/2014/09/08/there-is-one-chef-server-and-it-is-open-source/
You've probably heard this by now...• Multi-tenancy - required feature for Hosted Chef • Chef Push Jobs is opened now • Remove tension between Open Source Chef and Enterprise Chef codebase
• Remove tension between Hosted Enterprise Chef and Enterprise Chef code, too
Current state: Installing Chef Server 12Or, "this is how you do it manually per the documentation at docs.chef.io"
http://docs.chef.io/server/install_server.html
Installing Chef Server 12sudo dpkg -‐i chef-‐server-‐core*.deb sudo vi /etc/opscode/chef-‐server.rb sudo chef-‐server-‐ctl reconfigure
Or there's a cookbook for that...curl -‐L https://www.chef.io/chef/install.sh | sudo bash sudo mkdir -‐p /var/chef/cache /var/chef/cookbooks wget -‐qO-‐ https://supermarket.chef.io/cookbooks/chef-‐server/download | sudo tar xvzC /var/chef/cookbooks wget -‐qO-‐ https://supermarket.chef.io/cookbooks/chef-‐server-‐ingredient/download | sudo tar xvzC /var/chef/cookbooks wget -‐qO-‐ https://supermarket.chef.io/cookbooks/packagecloud/download | sudo tar xvzC /var/chef/cookbooks
sudo chef-‐solo -‐o 'recipe[chef-‐server::default]'
But if you want a cluster...## On the first node ("bootstrap backend") sudo dpkg -‐i chef-‐server-‐core*.deb sudo vi /etc/opscode/chef-‐server.rb
## manage some server blocks for the cluster per docs sudo chef-‐server-‐ctl reconfigure sudo rsync -‐avz /etc/opscode [email protected]:/etc
## On the second node ("frontend") sudo dpkg -‐i chef-‐server-‐core*.deb sudo chef-‐server-‐ctl reconfigure
Wait. What was that?## On the first node ("bootstrap backend") sudo dpkg -‐i chef-‐server-‐core*.deb sudo vi /etc/opscode/chef-‐server.rb
## manage some server blocks according to docs.chef.io... sudo chef-‐server-‐ctl reconfigure sudo rsync -‐avz /etc/opscode [email protected]:/etc
## On the second node ("frontend") sudo dpkg -‐i chef-‐server-‐core*.deb sudo chef-‐server-‐ctl reconfigure
What is Chef Provisioning?• Previously known as "Chef Metal" • Manage machines as Chef resources • Various provisioners available • several come with ChefDK, e.g., aws, azure • Available as rubygems • Makes it easy to reason about standing up a cluster
Chef Provisioning has `machine` resourcesmachine 'database' do recipe 'example-‐postgresql::server' end
machine 'cache' do recipe 'example-‐memcached' end
machine 'www1' do recipe 'example-‐nginx' end
machine 'www2' do recipe 'example-‐nginx end
Chef Provisioning extends Chef's Recipe DSL# AWS EC2... with_driver('aws::us-‐west-‐2') with_machine_options( :bootstrap_options => { :key_name => 'hc-‐metal-‐provisioner', :image_id => 'ami-‐b99ed989', :instance_type => 'm3.medium' } )
# Microsoft Azure... with_driver('azure') with_machine_options( :image_id => 'Ubuntu-‐14_04_1-‐LTS-‐amd64-‐server-‐20140927-‐en-‐us-‐30GB', :bootstrap_options => { :vm_size => 'Standard_D1', :other_options => 'Slides are only so big...' } )
Chef Provisioning a Chef Server Clustermachine 'backend' do recipe 'chef-‐server-‐cluster::bootstrap-‐backend' end
machine 'frontend' do recipe 'chef-‐server-‐cluster::frontend' end
machine 'analytics' do recipe 'chef-‐server-‐cluster::analytics' end
Chef Server (Hosted Chef)
Provisioner (laptop)
AWS EC2
backend
analytics
frontend
chef-client
chef
/kni
fe
chef-p
rovisioning-aws
SSH
SSH
SSH
Chef Provisioning Requires a... Provisioner• What is a provisioner? • What does it provision? • What does it need on the Chef Server?
AWS Authentication% cat ~/.aws/config [default] aws_access_key_id=AN_ACCESS_KEY_FOR_YOUR_IAM_USER aws_secret_access_key=MATCHING_SECRET_KEY
SSH Access - Provisioner options{ :ssh_username => "ubuntu", :bootstrap_options => { :key_name => "hc-‐metal-‐provisioner" } }
SSH Keys - Data Bag Item{ "id": "hc-‐metal-‐provisioner", "private_ssh_key": "-‐-‐-‐-‐-‐BEGIN RSA PRIVATE KEY-‐-‐-‐-‐-‐\nSNIP-‐-‐-‐-‐-‐END RSA PRIVATE KEY-‐-‐-‐-‐-‐\n" }
setup-ssh-keys recipessh_keys = data_bag_item('secrets', 'hc-‐metal-‐provisioner') key_dir = File.join(Dir.home, '.ssh')
directory key_dir do recursive true end
file File.join(key_dir, key_name) do content ssh_keys['private_ssh_key'] sensitive true end
chef-server-cluster cookbookReference Example, repo: https://github.com/opscode-cookbooks/chef-server-cluster
https://www.flickr.com/photos/dittaeva/5605435423
Checkpoint!• ./.chef/config.rb for knife and chef-client • Uploaded cookbooks (using Policyfiles*) • Uploaded data bags • AWS authentication credentials in ~/.aws/config • SSH private key in ~/.ssh/keyname
* Due to time constraints, Policyfile discussion is not appearing in this talk
Provisioner node run list% knife node show chefconf-‐provisioner Node Name: chefconf-‐provisioner Environment: _default FQDN: IP: 10.13.37.102 Run List: recipe[chef-‐server-‐cluster::cluster-‐provision] Roles: Recipes: chef-‐server-‐cluster::cluster-‐provision, chef-‐server-‐cluster::setup-‐provisioner, chef-‐server-‐cluster::setup-‐ssh-‐keys Platform: mac_os_x 10.10.2 Tags:
chef-server-cluster cookbook attributesdefault['chef-server-cluster']['topology'] = 'tier' default['chef-server-cluster']['role'] = 'frontend' default['chef-server-cluster']['bootstrap']['enable'] = false default['chef-server-cluster']['chef-provisioner-key-name'] = ‘keyname’
default['chef-server-cluster']['driver'] = { 'gems' => [ { 'name' => 'chef-provisioning-aws', 'require' => 'chef/provisioning/aws_driver' } ], 'with-parameter' => 'aws::us-west-2' }
default['chef-server-cluster']['driver']['machine_options'] = { 'ssh_username' => 'ubuntu', 'use_private_ip_for_ssh' => false, 'bootstrap_options' => { 'key_name' => ‘keyname’, 'image_id' => 'ami-b99ed989', 'instance_type' => 'm3.medium' } }
chef-server-cluster::setup-provisionernode['chef-‐server-‐cluster']['driver']['gems'].each do |g| chef_gem g['name'] require g['require'] if g.has_key?('require') end
provisioner_machine_opts = node['chef-‐server-‐cluster']['driver']['machine_options'].to_hash ChefHelpers.symbolize_keys_deep!(provisioner_machine_opts)
with_driver(node['chef-‐server-‐cluster']['driver']['with-‐parameter']) with_machine_options(provisioner_machine_opts)
What that actually looks like...chef_gem 'chef-‐provisioning-‐aws' require 'chef/provisioning/aws'
with_driver('aws::us-‐west-‐2') with_machine_options({ :ssh_username => 'ubuntu', :use_private_ip_for_ssh => false, :bootstrap_options => { :key_name => 'hc-‐metal-‐provisioner', :image_id => 'ami-‐b99ed989', :instance_type =>'m3.medium' } })
So in theory...{ "id": "azure-‐provisioner", "default_attributes": { "chef-‐server-‐cluster": { "driver": { "gems": [{ "name": "chef-‐provisioning-‐azure", "require": "chef/provisioning/azure_driver" }], "with-‐parameter": "azure", "machine_options": { "bootstrap_options": { "cloud_service_name": "chef-‐provisioner", "storage_aaccount_name": "chef-‐provisioner", "vm_size": "Standard_D1", "location": "West US", "tcp_endpoints": "80:80" }, "image_id": "b39f27a8b8c64d52b05eac6a62ebad85__Ubuntu-‐14_04_1-‐LTS-‐amd64-‐server-‐20140927-‐en-‐us-‐30GB", "password": "SshKeysArentSupportedYet" } } } } }
chef-server-cluster::cluster-provisioninclude_recipe 'chef-‐server-‐cluster::setup-‐provisioner' include_recipe 'chef-‐server-‐cluster::setup-‐ssh-‐keys'
directory '/tmp/stash' do recursive true end
machine 'bootstrap-‐backend' do recipe 'chef-‐server-‐cluster::bootstrap' action :converge converge true end # machine files in here... machine 'frontend' do recipe 'chef-‐server-‐cluster::frontend' action :converge converge true # files property... end
machine 'analytics' do recipe 'chef-‐server-‐cluster::analytics' action :converge converge true end
machine resource<machine[bootstrap-‐backend] @name: "bootstrap-‐backend" @allowed_actions: [:nothing, :allocate, :ready, :setup, :converge, :converge_only, :destroy, :stop] @action: [:converge] @chef_server: { :chef_server_url=>"https://api.opscode.com/organizations/jtimberman-‐chefconf", :options=>{ :client_name=>"jtimberman", :signing_key_filename=>"/Users/jtimberman/.chef/jtimberman.pem" } }
machine resource continued @driver: "aws::us-‐west-‐2" @machine_options: { "ssh_username"=>"ubuntu", "use_private_ip_for_ssh"=>false, "bootstrap_options"=>{ "key_name"=>"hc-‐metal-‐provisioner", "image_id"=>"ami-‐b99ed989", "instance_type"=>"m3.medium" } } @run_list_modifiers: [#<Chef::RunList::RunListItem:0x007f8cbe394d90 @version=nil, @type=:recipe, @name="chef-‐server-‐cluster::bootstrap">] @ohai_hints: {"ec2"=>"{}"} @converge: true >
Data bagschef_server/topology.json { "id": "topology", "topology": "tier", "disabled_svcs": [], "enabled_svcs": [], "vips": [], "dark_launch": { "actions": true }, "api_fqdn": "chef.jtimberman.name", "analytics_fqdn": "analytics.jtimberman.name", "notification_email": "[email protected]" }
Configuring the Cluster - bootstrap recipechef_server_config = data_bag_item('chef_server', 'topology').to_hash chef_server_config.delete('id')
chef_servers = search('node', 'chef-‐server-‐cluster_role:backend').map do |server| { :fqdn => server['fqdn'], :ipaddress => server['ipaddress'], :bootstrap => server['chef-‐server-‐cluster']['bootstrap']['enable'], :role => server['chef-‐server-‐cluster']['role'] } end
if chef_servers.empty? chef_servers = [ { :fqdn => node['fqdn'], :ipaddress => node['ipaddress'], :bootstrap => true, :role => 'backend' } ] end
chef_server_config['vips'] = { 'rabbitmq' => node['ipaddress'] } chef_server_config['rabbitmq'] = { 'node_ip_address' => '0.0.0.0' }
Merge the configuration# Merge the attributes with the data bag values, and the search # results for other servers.
node.default['chef-‐server-‐cluster'].merge!(chef_server_config)
Configuration templatetemplate '/etc/opscode/chef-server.rb' do source 'chef-server.rb.erb' variables(:chef_server_config => node['chef-server-cluster'], :chef_servers => chef_servers) notifies :reconfigure, 'chef_server_ingredient[chef-server-core]' end
Render configuration: /etc/opscode/chef-server.rbtopology '<%= @chef_server_config['topology'] %>' api_fqdn '<%= @chef_server_config['api_fqdn'] %>'
# Analytics configuration dark_launch['actions'] = <%= @chef_server_config['dark_launch']['actions'] %> <% if @chef_server_config.has_key?('vips') -‐%> <% @chef_server_config['vips'].each do |vip_name, vip_add| -‐%> <%= vip_name %>['vip'] = '<%= vip_add %>' <% end -‐%> <% end -‐%> <% if @chef_server_config.has_key?('rabbitmq') && @chef_server_config['rabbitmq'].has_key?('node_ip_address') -‐%> rabbitmq['node_ip_address'] = '<%= @chef_server_config['rabbitmq']['node_ip_address'] %>' <% end -‐%>
oc_id['applications'] = { 'analytics' => { 'redirect_uri' => 'https://<%= @chef_server_config['analytics_fqdn'] %>' } }
/etc/opscode/chef-server.rb# Server blocks <% @chef_servers.each do |server| -‐%> server '<%= server[:fqdn] %>', :ipaddress => '<%= server[:ipaddress] %>', <% if server[:bootstrap] -‐%> :bootstrap => true, <% end -‐%> :role => '<%= server[:role] %>' <% if server[:role] == 'backend' -‐%> backend_vip '<%= server[:fqdn] %>', :ipaddress => '<%= server[:ipaddress] %>' <% end -‐%>
<% end -‐%>
`server` blocks describe frontend and backend nodes
Rendered: backendtopology 'tier' api_fqdn 'chef.jtimberman.name'
dark_launch['actions'] = true rabbitmq['vip'] = '172.31.12.241' rabbitmq['node_ip_address'] = '0.0.0.0'
oc_id['applications'] = { 'analytics' => { 'redirect_uri' => 'https://analytics.jtimberman.name' } }
server 'ip-‐172-‐31-‐12-‐241.us-‐west-‐2.compute.internal', :ipaddress => '172.31.12.241', :bootstrap => true, :role => 'backend' backend_vip 'ip-‐172-‐31-‐12-‐241.us-‐west-‐2.compute.internal', :ipaddress => '172.31.12.241'
Rendered: frontendtopology 'tier' api_fqdn 'chef.jtimberman.name'
dark_launch['actions'] = true
oc_id['applications'] = { 'analytics' => { 'redirect_uri' => 'https://analytics.jtimberman.name' } }
server 'ip-‐172-‐31-‐12-‐241.us-‐west-‐2.compute.internal', :ipaddress => '172.31.12.241', :bootstrap => true, :role => 'backend' backend_vip 'ip-‐172-‐31-‐12-‐241.us-‐west-‐2.compute.internal', :ipaddress => '172.31.12.241'
server 'ip-‐172-‐31-‐11-‐8.us-‐west-‐2.compute.internal', :ipaddress => '172.31.11.8', :role => 'frontend'
Rendered: analyticstopology 'standalone' analytics_fqdn 'analytics.jtimberman.name'
Analytics config for the Chef Server is in:
/etc/opscode/analytics/actions-source.json
/etc/opscode-analytics/actions-source.json{ "private_chef": { "api_fqdn": "chef.jtimberman.name", "oc_id_application": { "name": "analytics", "uid": "56d493b4ef2290cb29d9e73d34bd89688667b9f0d4583ac273e6e9de79ba3cb7", "secret": "Generated-‐long-‐secret", "redirect_uri": "https://analytics.jtimberman.name" }, "rabbitmq_host": "172.31.10.165", "rabbitmq_port": "5672", "rabbitmq_vhost": "/analytics", "rabbitmq_exchange": "actions", "rabbitmq_user": "actions", "rabbitmq_password": "generated-‐long-‐secret" }
the bootstrap backend node
Configuration templatetemplate '/etc/opscode/chef-server.rb' do source 'chef-server.rb.erb' variables(:chef_server_config => node['chef-server-cluster'], :chef_servers => chef_servers) notifies :reconfigure, 'chef_server_ingredient[chef-server-core]' end
What is chef_server_ingredient??
chef-server-ingredient cookbook• What is an ingredient? • Clever, what's an addon? • What does the cookbook do? • How does the resource work?
• Primitive resource for installing/managing Chef Server add-ons
This automates these manual steps% sudo chef-‐server-‐ctl install opscode-‐manage % sudo opscode-‐manage-‐ctl reconfigure
chef_server_ingredient resources...chef_server_ingredient 'chef-‐server-‐core' do notifies :reconfigure, 'chef_server_ingredient[chef-‐server-‐core]' end
chef_server_ingredient 'opscode-‐reporting' do notifies :reconfigure, 'chef_server_ingredient[opscode-‐reporting]' end
chef_server_ingredient 'opscode-‐manage' do notifies :reconfigure, 'chef_server_ingredient[opscode-‐manage]' end
chef_server_ingredient 'opscode-‐analytics' do notifies :reconfigure, 'chef_server_ingredient[opscode-‐analytics]' end
chef_server_ingredientaction :install do packagecloud_repo 'chef/stable' do type value_for_platform_family(:debian => 'deb', :rhel => 'rpm') end
package new_resource.package_name do options new_resource.options version new_resource.version end end
action :reconfigure do ctl_cmd = ctl_command execute "#{new_resource.package_name}-‐reconfigure" do command "#{ctl_cmd} reconfigure" end end
Omnibus package pattern is consistent:• Install the package • Write the configuration* • Run the reconfigure command
• Configuration can happen first - and does with the Chef Provisioning recipes
* or rsync it from a node, RIGHT?
Remember this?sudo rsync -‐avz /etc/opscode [email protected]:/etc
Hint: No one wants to remember this
Hello, machine_file!%w{ actions-‐source.json webui_priv.pem }.each do |analytics_file| machine_file "/etc/opscode-‐analytics/#{analytics_file}" do local_path "/tmp/stash/#{analytics_file}" machine 'bootstrap-‐backend' action :download end end
%w{ pivotal.pem webui_pub.pem }.each do |opscode_file| machine_file "/etc/opscode/#{opscode_file}" do local_path "/tmp/stash/#{opscode_file}" machine 'bootstrap-‐backend' action :download end end
And the 'files' property of machine resourcemachine 'frontend' do recipe 'chef-‐server-‐cluster::frontend' action :converge converge true files('/etc/opscode/webui_priv.pem' => '/tmp/stash/webui_priv.pem', '/etc/opscode/webui_pub.pem' => '/tmp/stash/webui_pub.pem', '/etc/opscode/pivotal.pem' => '/tmp/stash/pivotal.pem') end
machine 'analytics' do recipe 'chef-‐server-‐cluster::analytics' action :converge converge true files('/etc/opscode-‐analytics/actions-‐source.json' => '/tmp/stash/actions-‐source.json', '/etc/opscode-‐analytics/webui_priv.pem' => '/tmp/stash/webui_priv.pem') end
Sure, we could rsync in the recipe...• But then we have to setup SSH keys between the nodes
• And all files in /etc/opscode, including ones put there by someone that shouldn't be there...
chef-client on the provisioner% CHEF_NODE=chefconf-‐provisioner chef-‐client -‐c .chef/config.rb Starting Chef Client, version 12.0.3 [2015-‐02-‐18T14:28:12-‐07:00] WARN: Using experimental Policyfile feature resolving cookbooks for run list: ["chef-‐server-‐cluster::cluster-‐[email protected] (e1e803c)"] Synchronizing Cookbooks: -‐ chef-‐server-‐ingredient -‐ chef-‐server-‐cluster -‐ apt -‐ packagecloud -‐ chef-‐vault Compiling Cookbooks... ... SNIP converging 3 machines ... Chef Client finished, 11/16 resources updated in 1248.519725 seconds
machine resources converging* machine[bootstrap-‐backend] action converge -‐ Create bootstrap-‐backend with AMI ami-‐b99ed989 in us-‐west-‐2 -‐ create node bootstrap-‐backend at https://api.opscode.com/organizations/jtimberman-‐chefconf -‐ update run_list from [] to ["recipe[chef-‐server-‐cluster::bootstrap]"] -‐ waiting for bootstrap-‐backend (i-‐553a519c on aws::us-‐west-‐2) to be connectable -‐ bootstrap-‐backend is now connectable
-‐ generate private key (2048 bits) -‐ create directory /etc/chef on bootstrap-‐backend -‐ write file /etc/chef/client.pem on bootstrap-‐backend -‐ create client bootstrap-‐backend at clients -‐ add public_key = "-‐-‐-‐-‐-‐BEGIN PUBLIC KEY-‐-‐-‐-‐-‐\n...SNIP...-‐-‐-‐-‐-‐END PUBLIC KEY-‐-‐-‐-‐-‐\n" -‐ Add bootstrap-‐backend to client read ACLs -‐ Add bootstrap-‐backend to client update ACLs -‐ create directory /etc/chef/ohai/hints on bootstrap-‐backend -‐ write file /etc/chef/ohai/hints/ec2.json on bootstrap-‐backend -‐ write file /etc/chef/client.rb on bootstrap-‐backend -‐ write file /tmp/chef-‐install.sh on bootstrap-‐backend -‐ run 'bash -‐c ' bash /tmp/chef-‐install.sh'' on bootstrap-‐backend [bootstrap-‐backend] Starting Chef Client, version 12.1.1 Chef Client finished, 25/32 resources updated in 453.570204517 seconds -‐ run 'chef-‐client -‐l auto' on bootstrap-‐backend
Create and connect to EC2 instance* machine[bootstrap-‐backend] action converge -‐ Create bootstrap-‐backend with AMI ami-‐b99ed989 in us-‐west-‐2 -‐ create node bootstrap-‐backend at https://api.opscode.com/organizations/jtimberman-‐chefconf -‐ update run_list from [] to ["recipe[chef-‐server-‐cluster::bootstrap]"] -‐ waiting for bootstrap-‐backend (i-‐553a519c on aws::us-‐west-‐2) to be connectable -‐ bootstrap-‐backend is now connectable
Create the API client and give permission* machine[bootstrap-‐backend] action converge -‐ generate private key (2048 bits) -‐ create directory /etc/chef on bootstrap-‐backend -‐ write file /etc/chef/client.pem on bootstrap-‐backend -‐ create client bootstrap-‐backend at clients -‐ add public_key = "RSA Public key content" -‐ Add bootstrap-‐backend to client read ACLs -‐ Add bootstrap-‐backend to client update ACLs
Bootstrap like you may have seen...* machine[bootstrap-‐backend] action converge -‐ create directory /etc/chef/ohai/hints on bootstrap-‐backend -‐ write file /etc/chef/ohai/hints/ec2.json on bootstrap-‐backend -‐ write file /etc/chef/client.rb on bootstrap-‐backend -‐ write file /tmp/chef-‐install.sh on bootstrap-‐backend -‐ run 'bash -‐c ' bash /tmp/chef-‐install.sh'' on bootstrap-‐backend [bootstrap-‐backend] Starting Chef Client, version 12.1.1 Chef Client finished, 25/32 resources updated in 453.57 seconds -‐ run 'chef-‐client -‐l auto' on bootstrap-‐backend
machine files * machine_file[/etc/opscode-‐analytics/actions-‐source.json] action download -‐ download file /etc/opscode-‐analytics/actions-‐source.json on bootstrap-‐backend to /tmp/stash/actions-‐source.json * machine_file[/etc/opscode-‐analytics/webui_priv.pem] action download -‐ download file /etc/opscode-‐analytics/webui_priv.pem on bootstrap-‐backend to /tmp/stash/webui_priv.pem * machine_file[/etc/opscode/pivotal.pem] action download -‐ download file /etc/opscode/pivotal.pem on bootstrap-‐backend to /tmp/stash/pivotal.pem * machine_file[/etc/opscode/webui_pub.pem] action download -‐ download file /etc/opscode/webui_pub.pem on bootstrap-‐backend to /tmp/stash/webui_pub.pem ...SNIP -‐ upload file /tmp/stash/webui_priv.pem to /etc/opscode/webui_priv.pem on frontend -‐ upload file /tmp/stash/webui_pub.pem to /etc/opscode/webui_pub.pem on frontend -‐ upload file /tmp/stash/pivotal.pem to /etc/opscode/pivotal.pem on frontend
Wrap-up and takeaways• Chef Server 12 is totally what you want to use • Using Chef to build Chef is awesome • Chef Provisioning makes deploying to EC2 easy • chef-server-cluster is a full working example • chef-server-ingredient is a lower level primitive • (and used by chef-server cookbook, too!) • Build your own with chef-server-ingredient
Questions?Joshua Timberman [email protected], @jtimberman
Links https://www.chef.io/blog/2014/09/08/there-is-one-chef-server-and-it-is-open-source/ https://github.com/opscode-cookbooks/chef-server-cluster https://github.com/chef/chef-dk/blob/master/POLICYFILE_README.md https://github.com/jtimberman/chefconf2015-chef-repo http://jtimberman.housepub.org/blog/2014/10/07/reflecting-on-six-years-with-chef/
https://www.flickr.com/photos/debord/4932655275