Top Level Namespace

Defined Under Namespace

Classes: ChefRundeck, ChefRundeckCLI, MissingAttribute, PartialSearch

Constant Summary collapse

REQUIRED_ATTRS =
[ :kernel, :fqdn, :platform, :platform_version ]

Instance Method Summary collapse

Instance Method Details

#build_node(node, username, hostname, custom_attributes) ⇒ Object



169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
# File 'lib/chef-rundeck.rb', line 169

def build_node (node, username, hostname, custom_attributes)
      #--
      # Certain features in Rundeck require the osFamily value to be set to 'unix' to work appropriately. - SRK
      #++
      data = ''
      os_family = node['kernel_os'] =~ /winnt|windows/i ? 'winnt' : 'unix'
      nodeexec = node['kernel_os'] =~ /winnt|windows/i ? "node-executor=\"overthere-winrm\"" : ''
      data << <<-EOH
<node name="#{xml_escape(node['fqdn'])}" #{nodeexec} 
      type="Node" 
      description="#{xml_escape(node['name'])}"
      osArch="#{xml_escape(node['kernel_machine'])}"
      osFamily="#{xml_escape(os_family)}"
      osName="#{xml_escape(node['platform'])}"
      osVersion="#{xml_escape(node['platform_version'])}"
      roles="#{xml_escape(node['roles'].join(','))}"
      recipes="#{xml_escape(node['recipes'].join(','))}"
      tags="#{xml_escape([ node['roles'], node['recipes'], node['chef_environment'], node['tags']].flatten.join(","))}"
      environment="#{xml_escape(node['chef_environment'])}"
      username="#{xml_escape(username)}"
      hostname="#{xml_escape(node['hostname'])}"
      editUrl="#{xml_escape(ChefRundeck.web_ui_url)}/nodes/#{xml_escape(node['name'])}/edit" #{custom_attributes.nil? ? '/': ''}>
EOH
     if !custom_attributes.nil? then
       custom_attributes.each do |attr|
         attr_name = attr
         attr_value = node[attr.gsub('.','_')]
         data << <<-EOH
      <attribute name="#{attr_name}"><![CDATA[#{attr_value}]]></attribute>
EOH
       end
       data << "</node>"
     end

  return data
end

#convert_results(results, hostname, custom_attributes) ⇒ Object

Convert results to be compatiable with Chef 11 format



219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
# File 'lib/chef-rundeck.rb', line 219

def convert_results(results, hostname, custom_attributes)
 new_results = []
 results.each do |node|
   n = {}
   n['name'] = node.name
   n['chef_environment'] = node.chef_environment
   n['run_list'] = node.run_list
   n['recipes'] = !node.run_list.nil? ? node.run_list.recipes : nil
   n['roles'] = !node.run_list.nil? ? node.run_list.roles : nil
   n['fqdn'] = node['fqdn']
   n['hostname'] = node[hostname.to_sym]
   n['kernel_machine'] = !node['kernel'].nil? ? node['kernel']['machine'] : nil
   n['kernel_os'] = !node['kernel'].nil? ? node['kernel']['os'] : nil
   n['platform'] = node['platform']
   n['platform_version'] = node['platform_version']
   n['tags'] = node['tags']
   
   if !custom_attributes.nil? then
     custom_attributes.each do |attr|
       ps_name = attr.gsub('.','_')
       n[ps_name] = get_custom_attr(node, attr.split('.'))
     end
   end
   new_results << n
 end 
 return new_results
end

#get_custom_attr(obj, params) ⇒ Object



206
207
208
209
210
211
212
213
214
215
216
# File 'lib/chef-rundeck.rb', line 206

def get_custom_attr (obj, params)
  value = obj
  Chef::Log.debug("loading custom attributes for node: #{obj['name']} with #{params}")
  params.each do |p|   
    value = value[p.to_sym]
    if value.nil? then
      break
    end
  end
  return value.nil? ? "" : value.to_s
end

#node_is_valid?(node) ⇒ Boolean

Helper def to validate the node

Returns:

  • (Boolean)

Raises:

  • (ArgumentError)


249
250
251
252
253
254
255
256
257
258
259
260
261
# File 'lib/chef-rundeck.rb', line 249

def node_is_valid?(node)
  raise ArgumentError, "#{node} missing 'name'" if !node['name']
  raise ArgumentError, "#{node} missing 'chef_environment'" if !node['chef_environment']
  raise ArgumentError, "#{node} missing 'run_list'" if !node['run_list']
  raise ArgumentError, "#{node} missing 'recipes'" if !node['recipes']
  raise ArgumentError, "#{node} missing 'roles'" if !node['roles']
  raise ArgumentError, "#{node} missing 'fqdn'" if !node['fqdn']
  raise ArgumentError, "#{node} missing 'hostname'" if !node['hostname']
  raise ArgumentError, "#{node} missing 'kernel.machine'" if !node['kernel_machine']
  raise ArgumentError, "#{node} missing 'kernel.os'" if !node['kernel_os']
  raise ArgumentError, "#{node} missing 'platform'" if !node['platform']
  raise ArgumentError, "#{node} missing 'platform_version'" if !node['platform_version']
end

#partial_search(type, query = '*:*', *args, &block) ⇒ Object

partial_search(type, query, options, &block)

Searches for nodes, roles, etc. and returns the results. This method may perform more than one search request, if there are a large number of results.

Parameters

  • type: index type (:role, :node, :client, :environment, data bag name)

  • query: SOLR query. “:”, “role:blah”, “not role:blah”, etc. Defaults to ‘:

  • options: hash with options:

** :start: First row to return (:start => 50, :rows => 100 means “return the

50th through 150th result")

** :rows: Number of rows to return. Defaults to 1000. ** :sort: a SOLR sort specification. Defaults to ‘X_CHEF_id_CHEF_X asc’. ** :keys: partial search keys. If this is not specified, the search will

not be partial.

Returns

This method returns an array of search results. Partial search results will be JSON hashes with the structure specified in the keys option. Other results include Chef::Node, Chef::Role, Chef::Client, Chef::Environment, Chef::DataBag and Chef::DataBagItem objects, depending on the search type.

If a block is specified, the block will be called with each result instead of returning an array. This method will not block if it returns

If start or row is specified, and no block is given, the result will be a triple containing the list, the start and total:

[ [ row1, row2, ... ], start, total ]

Example

partial_search(:node, 'role:webserver',
               keys: {
                 name: [ 'name' ],
                 ip: [ 'amazon', 'ip', 'public' ]
               }
).each do |node|
  puts "#{node[:name]}: #{node[:ip]}"
end


306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
# File 'lib/chef-rundeck.rb', line 306

def partial_search(type, query='*:*', *args, &block)
  # Support both the old (positional args) and new (hash args) styles of calling
  if args.length == 1 && args[0].is_a?(Hash)
    args_hash = args[0]
  else
    args_hash = {}
    args_hash[:sort] = args[0] if args.length >= 1
    args_hash[:start] = args[1] if args.length >= 2
    args_hash[:rows] = args[2] if args.length >= 3
  end
  # If you pass a block, or have the start or rows arguments, do raw result parsing
  if Kernel.block_given? || args_hash[:start] || args_hash[:rows]
    PartialSearch.new.search(type, query, args_hash, &block)
 
  # Otherwise, do the iteration for the end user
  else
    results = Array.new
    PartialSearch.new.search(type, query, args_hash) do |o|
        results << o
    end
     results
  end
end