Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add various bits of setup automation #61

Closed
wants to merge 14 commits into from
Closed
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 34 additions & 3 deletions recipes/osd.rb
Original file line number Diff line number Diff line change
Expand Up @@ -34,10 +34,39 @@
include_recipe "ceph::default"
include_recipe "ceph::conf"

if !node["ceph"]["osd_devices"].nil?
node["ceph"]["osd_devices"].each do |osd_device|
Log.info("ceph-osd device: #{osd_device}")
end
elsif node["ceph"]["osd_autoprepare"]
# set node["ceph"]["osd_autoprepare"] to true to enable automated osd disk
# discovery and preparation
osd_devices = Array.new
node['block_device'].select{|device,info| device =~ /^[hvs]d[^a]$/ and info['size'].to_i > 0}.each do |device,info|
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this regex can be quite a problem...
I don't have a chef server to check, but OHAI don't give you a device type or somethings like this?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unfortunately no - ohai gives output like this:

{
  "vda": {
    "size": "52428800",
    "removable": "0",
    "vendor": "0x1af4"
  },
  "vdb": {
    "size": "52428800",
    "removable": "0",
    "vendor": "0x1af4"
  },
  "dm-0": {
    "size": "36962304",
    "removable": "0"
  },
  "dm-1": {
    "size": "2088960",
    "removable": "0"
  }
}

My thinking was that although this regex is pretty liberal, the use of it is optional and the user can always submit a patch to improve its flexibility. For now I'm happy to scratch my own itch. :)

Of course if you can think of a way to improve it right now, then I'll gladly patch it.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We could maybe use a loop that look into /sys/block//. If inside this directory you see a . It means that the disks has partitions so we probably do not want to touch it.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How about this as a strategy?

  1. I'll make the regex an attribute of some kind so that it's easier to override through the end-user's environment.
  2. I'll add another attribute to enable zapping the disks that match the regex, regardless of what's on them. Enabling forced zap is useful in testing environments and also useful when re-purposing disks.
  3. If the forced zap is not enabled, then a check will be done for whether the disk has anything on it before preparing it. If it does, this discovery will reflect in the log as a WARN.

Log.info("ceph-osd: Candidate Device /dev/#{device} found.")
osd_devices << {"device" => "/dev/#{device}"}
end
Log.info("ceph-osd: New Candidates = #{osd_devices}")
node.set["ceph"]["osd_devices"] = osd_devices
node.save
else
Log.warn('ceph-osd: No ceph osd_devices have been set and ceph osd_autoprepare not enabled.')
end

package 'gdisk' do
action :upgrade
end

# sometimes there are partitions on the disk that interfere with
# ceph-disk-prepare, so let's make sure there's nothing on each candidate disk
if node["ceph"]["osd_autoprepare"] and !node["ceph"]["osd_devices"].nil?
node["ceph"]["osd_devices"].each do |osd_device|
Log.info("ceph-osd: Erasing #{osd_device['device']} to prepare it as an osd")
system 'sgdisk', '-oZ', "#{osd_device['device']}"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Mixlib::ShellOut

Is better than "system". ;)

.error!

raise an exception :)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, good tip - I've pushed an update.

raise "ceph-osd: erase of #{osd_device['device']} failed" unless $?.exitstatus == 0
end
end

if !search(:node,"hostname:#{node['hostname']} AND dmcrypt:true").empty?
package 'cryptsetup' do
action :upgrade
Expand All @@ -48,7 +77,7 @@
mons = get_mon_nodes("ceph_bootstrap_osd_key:*")

if mons.empty? then
puts "No ceph-mon found."
Log.info("ceph-osd: No ceph-mons found.")
else

directory "/var/lib/ceph/bootstrap-osd" do
Expand Down Expand Up @@ -104,16 +133,18 @@
# osd/$cluster-$id)
# - $cluster should always be ceph
# - The --dmcrypt option will be available starting w/ Cuttlefish
Log.info("ceph-osd: Starting setup of osd_devices.")
unless node["ceph"]["osd_devices"].nil?
node["ceph"]["osd_devices"].each_with_index do |osd_device,index|
if !osd_device["status"].nil?
Log.info("osd: osd_device #{osd_device} has already been setup.")
Log.info("ceph-osd: osd_device #{osd_device} has already been setup.")
next
end
dmcrypt = ""
if osd_device["encrypted"] == true
dmcrypt = "--dmcrypt"
end
Log.info("ceph-osd: creating osd on #{osd_device['device']}.")
execute "Creating Ceph OSD on #{osd_device['device']}" do
command "ceph-disk-prepare #{dmcrypt} #{osd_device['device']} #{osd_device['journal']}"
action :run
Expand Down Expand Up @@ -143,7 +174,7 @@
supports :restart => true
end
else
Log.info('node["ceph"]["osd_devices"] empty')
Log.info('ceph-osd: No ceph osd_devices have been set.')
end
end
end
52 changes: 52 additions & 0 deletions recipes/setup.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
#
# Cookbook Name:: ceph
# Recipe:: setup
#
# Copyright 2013, Business Connexion (Pty) Ltd
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#

# make sure we die early if there is another ceph-setup node
search_query = "roles:ceph-setup NOT name:#{node.name}"
search_result = search(:node, search_query)
if search_result.length > 0
msg = "You can only have one node with the ceph-setup role."
Chef::Application.fatal! msg
end

# This recipe creates a new ceph cluster and sets the node up as the
# mon_initial_member for the cluster. This value can be overridden if
# desired.

if node['ceph']['config']['fsid'].nil?
Log.info("ceph-setup: ceph fsid not set - generating a new fsid")
require 'securerandom'
fsid = SecureRandom.uuid
node.set['ceph']['config']['fsid'] = fsid
node.save
Log.info("ceph-setup: ceph fsid has been set to #{fsid}")
else
Log.info("ceph-setup: ceph fsid is #{node['ceph']['config']['fsid']}")
end

if node['ceph']['config']['mon_initial_members'].nil?
Log.info("ceph-setup: mon_initial_members not set - using the ceph-setup node")
node.set['ceph']['config']['mon_initial_members'] = node['hostname']
node.save
Log.info("ceph-setup: mon_initial_members has been set to #{node['hostname']}")
else
Log.info("ceph-setup: mon_initial_members is #{node['ceph']['config']['mon_initial_members']}")
end

include_recipe "ceph::default"
6 changes: 6 additions & 0 deletions roles/ceph-setup.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
name "ceph-setup"
description "Role for the setup of a Ceph cluster. Includes a mon role."
run_list(
'recipe[ceph::setup]',
'role[ceph-mon]'
)