1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
| #!/usr/bin/env ruby
require 'rubygems'
require 'chef/application'
require 'chef/client'
require 'mixlib/cli'
class Client < Chef::Application
include Mixlib::CLI
banner "Usage: #{$0} (options)"
option :config_file,
:short => "-c CONFIG",
:long => "--config CONFIG",
:description => "The configuration file to use"
option :log_level,
:short => "-l LEVEL",
:long => "--log_level LEVEL",
:description => "Set the log level (debug, info, warn, error, fatal)",
:proc => lambda { |l| l.to_sym }
option :log_location,
:short => "-L LOGLOCATION",
:long => "--logfile LOGLOCATION",
:description => "Set the log file location, defaults to STDOUT",
:proc => nil
option :editor,
:short => "-e EDITOR",
:long => "--editor EDITOR",
:description => "Set the editor to use for interactive commands",
:default => ENV['EDITOR']
option :no_editor,
:short => "-n",
:long => "--no-editor",
:description => "Do not open EDITOR, just accept the data as is",
:boolean => true
option :help,
:short => "-h",
:long => "--help",
:description => "Show this message",
:on => :tail,
:boolean => true
option :node_name,
:short => "-u USER",
:long => "--user USER",
:description => "API Client Username"
option :client_key,
:short => "-k KEY",
:long => "--key KEY",
:description => "API Client Key"
option :chef_server_url,
:short => "-s URL",
:long => "--server-url URL",
:description => "Chef Server URL"
option :yes,
:short => "-y",
:long => "--yes",
:description => "Say yes to all prompts for confirmation"
option :defaults,
:long => "--defaults",
:description => "Accept default values for all questions"
option :print_after,
:short => "-p",
:long => "--print-after",
:description => "Show the data after a destructive operation"
option :format,
:short => "-F FORMAT",
:long => "--format FORMAT",
:description => "Which format to use for output",
:default => "json"
option :version,
:short => "-v",
:long => "--version",
:description => "Show chef version",
:boolean => true,
:proc => lambda {|v| puts "Chef: #{::Chef::VERSION}"},
:exit => 0
def configure_chef
unless config[:config_file]
full_path = Dir.pwd.split(File::SEPARATOR)
(full_path.length - 1).downto(0) do |i|
config_file_to_check = File.join([ full_path[0..i], ".chef", "client.rb" ].flatten)
if File.exists?(config_file_to_check)
config[:config_file] = config_file_to_check
break
end
end
# If we haven't set a config yet and $HOME is set, and the home
# knife.rb exists, use it:
if (!config[:config_file]) && ENV['HOME'] && File.exist?(File.join(ENV['HOME'], '.chef', 'client.rb'))
config[:config_file] = File.join(ENV['HOME'], '.chef', 'client.rb')
end
end
# Don't try to load a knife.rb if it doesn't exist.
if config[:config_file]
Chef::Config.from_file(config[:config_file])
else
# ...but do log a message if no config was found.
self.msg("No knife configuration file found")
end
Chef::Config[:log_level] = config[:log_level] if config[:log_level]
Chef::Config[:log_location] = config[:log_location] if config[:log_location]
Chef::Config[:node_name] = config[:node_name] if config[:node_name]
Chef::Config[:client_key] = config[:client_key] if config[:client_key]
Chef::Config[:chef_server_url] = config[:chef_server_url] if config[:chef_server_url]
Mixlib::Log::Formatter.show_time = false
Chef::Log.init(Chef::Config[:log_location])
Chef::Log.level(Chef::Config[:log_level])
Chef::Log.debug("Using configuration from #{config[:config_file]}")
if Chef::Config[:node_name].nil?
raise ArgumentError, "No user specified, pass via -u or specifiy 'node_name' in #{config[:config_file] ? config[:config_file] : "~/.chef/knife.rb"}"
end
end
def parse_options(args=[])
super
config
end
def run(args)
parse_options(args)
configure_chef
Chef::Search::Query.new.search(:node,"*:*") do |n|
## iterate on every node. You have access to every information
## chef and ohai could collect from the nodes
end
end
end
Client.new.run
|