diff --git a/lib/puppet/provider/ha_crm_group/crm.rb b/lib/puppet/provider/ha_crm_group/crm.rb new file mode 100644 index 0000000..9d6d65c --- /dev/null +++ b/lib/puppet/provider/ha_crm_group/crm.rb @@ -0,0 +1,46 @@ +require 'rexml/document' + +Puppet::Type.type(:ha_crm_group).provide(:crm) do + + commands :crm => "crm" + commands :crm_resource => "crm_resource" + + def create + with_rsc = resource[:resources] + + crm "-F", "configure", "group", resource[:id], with_rsc + end + + def destroy + crm "-F", "configure", "delete", resource[:id] + end + + def target_role + cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/group[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='target-role']") + if nvpair.nil? + :absent + else + nvpair.attribute(:value).value + end + end + + def target_role=(value) + if value == :absent + crm_resource "-m", "-r", resource[:id], "-d", "target-role" + else + crm_resource "-m", "-r", resource[:id], "-p", "target-role", "-v", value.to_s.capitalize + end + end + + def exists? + cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") + colocation = REXML::XPath.first(cib, "//group[@id='#{resource[:id]}']") + + if colocation + true + else + false + end + end +end diff --git a/lib/puppet/provider/ha_crm_order/crm.rb b/lib/puppet/provider/ha_crm_order/crm.rb index b989714..c173fcb 100644 --- a/lib/puppet/provider/ha_crm_order/crm.rb +++ b/lib/puppet/provider/ha_crm_order/crm.rb @@ -1,57 +1,103 @@ require 'rexml/document' -Puppet::Type.type(:ha_crm_colocation).provide(:crm) do +Puppet::Type.type(:ha_crm_order).provide(:crm) do commands :crm => "crm" - def create - if resource[:first_action] - first_rsc = "#{resource[:first]}:#{resource[:first_action]}" + def lensure + return resource[:ensure] + end + + def id + return resource[:id] + end + + def first + return resource[:first] + end + + def first_action + return resource[:first_action] + end + + def lthen + return resource[:then] + end + + def then_action + return resource[:then_action] + end + + def score + return resource[:score] + end + + def symmetrical + return resource[:symmetrical] + end + + def only_run_on_dc + return resource[:only_run_on_dc] + end + + def create + if first_action + first_rsc = "#{first}:#{first_action}" else - first_rsc = resource[:first] + first_rsc = first end - if resource[:then_action] - then_rsc = "#{resource[:then]}:#{resource[:then_action]}" + if then_action + then_rsc = "#{lthen}:#{then_action}" else - then_rsc = resource[:then] + then_rsc = lthen end - - crm "-F", "configure", "order", resource[:id], "#{resource[:score]}:", first_rsc, then_rsc, "symmetrical=#{resource[:symmetrical].to_s}" + begin + crm "-F", "configure", "delete", id + rescue + # Already deleted + end + crm "-F", "configure", "order", id, "#{score}:", first_rsc, then_rsc, "symmetrical=#{symmetrical.to_s}" end def destroy - crm "-F", "configure", "delete", resource[:id] + crm "-F", "configure", "delete", id end def exists? - if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) - resource[:ensure] == :present ? true : false + if only_run_on_dc and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) + lensure == :present ? true : false else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - colocation = REXML::XPath.first(cib, "//rsc_order[@id='#{resource[:id]}']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + rsc_order = REXML::XPath.first(cib, "//rsc_order[@id='#{id}']") + + return false if not rsc_order - if resource[:first_action] - if colocation.attribute("first-action").value != resource[:first_action] - false + if first_action + if rsc_order.attribute(:first-action).value != first_action + return false end end - if resource[:then_action] - if colocation.attribute("then-action").value != resource[:then_action] - false + if then_action + if rsc_order.attribute(:then-action).value != then_action + return false end end - - if colocation.attribute(:first).value != resource[:first] - false - elsif colocation.attribute(:then).value != resource[:then] - false - elsif colocation.attribute(:score).value != resource[:score] - false + #We use crm directly now so need to convert inf to INFINITY for the match + if score == :inf + score = 'INFINITY' + end + if rsc_order.attribute(:first).value.downcase != first.downcase + return false + elsif rsc_order.attribute(:then).value.downcase != lthen.downcase + return false + elsif rsc_order.attribute(:score).value.downcase != score.downcase + return false else - true + return true end + return true end end end diff --git a/lib/puppet/provider/ha_crm_primitive/crm.rb b/lib/puppet/provider/ha_crm_primitive/crm.rb index 9b84fd1..f215717 100644 --- a/lib/puppet/provider/ha_crm_primitive/crm.rb +++ b/lib/puppet/provider/ha_crm_primitive/crm.rb @@ -3,24 +3,40 @@ Puppet::Type.type(:ha_crm_primitive).provide(:crm) do desc "CRM shell support" - commands :crm => "crm" - commands :crm_resource => "crm_resource" - - def create - crm "-F", "configure", "primitive", resource[:id], resource[:type] + commands :crm => "crm", :crm_resource => "crm_resource" + + def ops + return resource[:ops] + end + + def create + if ops + a_ops=[] + ops.split(',').each do |this_op| + a_ops << "op #{this_op} " + end + end + crm "-F", "configure", "primitive", resource[:id], resource[:type], *a_ops end def destroy - crm "-F", "configure", "delete", resource[:id] + crm "-F", "resource", "stop", resource[:id] + crm "-F", "resource", "cleanup", resource[:id] + sleep 5 + crm "-F", "configure", "delete", resource[:id] end def exists? if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:ensure] == :present ? true : false else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - primitive = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']") - !primitive.nil? + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + primitive = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']") + if primitive.nil? + false + else + true + end end end @@ -28,8 +44,8 @@ def priority if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:priority] else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='priority']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='priority']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='priority']") if nvpair.nil? :absent else @@ -50,8 +66,8 @@ def target_role if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:target_role] else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='target-role']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='target-role']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='target-role']") if nvpair.nil? :absent else @@ -72,8 +88,8 @@ def is_managed if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:is_managed] else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='is-managed']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='is-managed']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='is-managed']") if nvpair.nil? :absent else @@ -94,8 +110,8 @@ def resource_stickiness if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:resource_stickiness] else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='resource-stickiness']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='resource-stickiness']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='resource-stickiness']") if nvpair.nil? :absent else @@ -116,8 +132,8 @@ def migration_threshold if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:migration_threshold] else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='migration-threshold']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='migration-threshold']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='migration-threshold']") if nvpair.nil? :absent else @@ -138,8 +154,8 @@ def failure_timeout if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:failure_timeout] else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='failure-timeout']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='failure-timeout']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='failure-timeout']") if nvpair.nil? :absent else @@ -160,8 +176,8 @@ def multiple_active if resource[:only_run_on_dc] and Facter.value(:ha_cluster_dc) != Facter.value(:fqdn) resource[:multiple_active] else - cib = REXML::Document.new File.open("/var/lib/heartbeat/crm/cib.xml") - nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='multiple-active']") + cib = REXML::Document.new `/usr/sbin/crm configure save xml -` + nvpair = REXML::XPath.first(cib, "//cib/configuration/resources/*/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='multiple-active']") || REXML::XPath.first(cib, "//cib/configuration/resources/primitive[@id='#{resource[:id]}']/meta_attributes/nvpair[@name='multiple-active']") if nvpair.nil? :absent else diff --git a/lib/puppet/type/ha_crm_group.rb b/lib/puppet/type/ha_crm_group.rb new file mode 100644 index 0000000..a1cb3be --- /dev/null +++ b/lib/puppet/type/ha_crm_group.rb @@ -0,0 +1,31 @@ +Puppet::Type.newtype(:ha_crm_group) do + @desc = "Manages Pacemaker resource groups." + + ensurable + + newparam(:id) do + desc "A unique name for the group" + + isnamevar + end + + newparam(:resources) do + desc "Array of resources to group. They will be started in the order they are ordered in the array." + end + + newproperty(:target_role) do + desc "What state should the cluster attempt to keep this resource in? + + Allowed values: + * stopped - Force the resource not to run + * started - Allow the resource to be started + * master - Allow the resource to be started and promoted to Master" + + newvalues(:absent, :stopped, :started, :master) + defaultto :absent + end + + validate do + raise Puppet::Error, "You must specify a list of resources" unless @parameters.include?(:resources) + end +end diff --git a/lib/puppet/type/ha_crm_order.rb b/lib/puppet/type/ha_crm_order.rb index 6b747e2..f09df8e 100644 --- a/lib/puppet/type/ha_crm_order.rb +++ b/lib/puppet/type/ha_crm_order.rb @@ -50,9 +50,9 @@ defaultto(:true) end - validate do - raise Puppet::Error, "You must specify a first resource (first)" unless @parameters.include?(:first) - raise Puppet::Error, "You must specify a second resource (then)" unless @parameters.include(:then) - raise Puppet::Error, "You must specify a score" unless @parameters.include?(:score) - end + #validate do + # defined? @parameters['first'] or raise Puppet::Error, "You must specify a first resource (first)" + # defined? @parameters['then'] or raise Puppet::Error, "You must specify a second resource (then)" + # defined? @parameters['has_key'] or raise Puppet::Error, "You must specify a score" + #end end diff --git a/lib/puppet/type/ha_crm_primitive.rb b/lib/puppet/type/ha_crm_primitive.rb index b3438ff..ccbe510 100644 --- a/lib/puppet/type/ha_crm_primitive.rb +++ b/lib/puppet/type/ha_crm_primitive.rb @@ -92,6 +92,12 @@ newvalues(:absent, :block, :stop_only, :stop_start) defaultto :absent end + + newproperty(:ops) do + desc "Array of 'op' parameters. + Example: ['stop interval=\"0\" timeout=\"30s\"', 'start interval=\"0\" timeout=\"30s\"']" + defaultto(:false) + end validate do raise Puppet::Error, "You must specify a type for this primitive" unless @parameters.include?(:type) diff --git a/manifests/crm/primitive.pp b/manifests/crm/primitive.pp index 8512f9a..8d658b1 100644 --- a/manifests/crm/primitive.pp +++ b/manifests/crm/primitive.pp @@ -1,4 +1,4 @@ -define ha::crm::primitive($resource_type, $ensure=present, $monitor_interval, $ignore_dc="false" +define ha::crm::primitive($resource_type, $ensure=present, $monitor_interval, $ignore_dc="false", $priority="", $target_role="", $is_managed="", $resource_stickiness="", $migration_threshold="", $failure_timeout="", $multiple_active="") { diff --git a/manifests/init.pp b/manifests/init.pp index 7c74052..b1c83e8 100644 --- a/manifests/init.pp +++ b/manifests/init.pp @@ -1,7 +1,7 @@ -import "primitive.pp" +import "crm/primitive.pp" import "stonith.pp" import "ip.pp" - +class ha(){} define ha::authkey($method, $key="") { if($method == "crc") { $changes = ["set ${name}/method ${method}"]