fingerpuppet 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/LICENSE +20 -0
- data/README.md +56 -0
- data/bin/fingerpuppet +216 -0
- data/lib/fingerpuppet/restapi.rb +331 -0
- metadata +65 -0
data/LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2013 Puppet Labs, info@puppetlabs.com
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,56 @@
|
|
1
|
+
Usage : fingerpuppet <commandstring>
|
2
|
+
|
3
|
+
Steps for using the API:
|
4
|
+
1:) fingerpuppet --init --certname my.cert.name --server my.server.name
|
5
|
+
Builds the config file
|
6
|
+
Generates the certificate and CSR
|
7
|
+
Submits the CSR to the Puppetmaster
|
8
|
+
|
9
|
+
2:) On puppetmaster: puppet cert sign my.cert.name
|
10
|
+
|
11
|
+
3:) restapi.rb --install
|
12
|
+
Downloads the signed certificate and installs it
|
13
|
+
|
14
|
+
4:) ...
|
15
|
+
|
16
|
+
5:) Profit!
|
17
|
+
|
18
|
+
Your Puppetmaster must be configured to allow requests other than certificate requests.
|
19
|
+
See http://docs.puppetlabs.com/guides/rest_auth_conf.html for more information.
|
20
|
+
|
21
|
+
The certname can be specified with --certname or with optional CERTNAME argument to many options.
|
22
|
+
|
23
|
+
You may want to use the '-dcn' options to print the cURL equivalent command.
|
24
|
+
|
25
|
+
-d, --debug runs in debug mode
|
26
|
+
-h, --help Displays this help
|
27
|
+
-c, --curl Use commandline curl rather than Net::HTTP.
|
28
|
+
-n, --nop No-Op mode. Don't perform action, just output debugging data. Implies --debug.
|
29
|
+
|
30
|
+
--server SERVER The server address of your Puppetmaster.
|
31
|
+
--certname CERTNAME The certname you wish to use when connecting to your Puppetmaster
|
32
|
+
--file FILENAME The file to send to the Puppetmaster.
|
33
|
+
--output FILENAME The file to save any output to.
|
34
|
+
--state STATE The desired state you want to set.
|
35
|
+
|
36
|
+
--init Initialize application. Generate config file, certificate and submit CSR. Requires --certname and --server.
|
37
|
+
--install Download and install signed certificate.
|
38
|
+
|
39
|
+
--catalog Download the catalog compiled for your app's certname. Quite often just the default Node.
|
40
|
+
--delete [CERTNAME] Remove certificate and facts about a node from Puppetmaster.
|
41
|
+
--facts [CERTNAME] Retrieve the facts known about a given certname.
|
42
|
+
--insert [CERTNAME] Send facts for a given certname to the Puppetmaster. Requires --file.
|
43
|
+
--node [CERTNAME] Retrieve the node information (including facts) known about a given certname.
|
44
|
+
--search QUERY Retrieve the nodes matching a comma separated query string (e.g. kernel=Linux,virtual=vmware)
|
45
|
+
|
46
|
+
--certificate [CERTNAME] Retrieve the certificate for a given certname or 'ca'.
|
47
|
+
--cert_status [CERTNAME] Retrieve the certificate status for a given certname. Set the status by using --state.
|
48
|
+
--cert_revocation_list Retrieve and display the certifiacte revocation list from the master.
|
49
|
+
--sign [CERTNAME] Instruct the Puppetmaster to sign a certificate. Requires significate privileges in auth.conf.
|
50
|
+
|
51
|
+
--file_metadata PATH Retrieve the metadata for a file.
|
52
|
+
--getfile PATH Download a file from the Puppetmaster. Save to --file or output on stdout.
|
53
|
+
|
54
|
+
--resource RESOURCE Returns a list of resources (e.g. user) or information about a resource (e.g. 'user/elvis')
|
55
|
+
--report [CERTNAME] Sends a YAML report to the Puppetmaster. Requires --file or --state.
|
56
|
+
--status Check to make sure the Puppetmaster is alive and well.
|
data/bin/fingerpuppet
ADDED
@@ -0,0 +1,216 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'optparse'
|
4
|
+
require 'fingerpuppet/restapi.rb'
|
5
|
+
|
6
|
+
options = {}
|
7
|
+
optparse = OptionParser.new { |opts|
|
8
|
+
opts.banner = "Usage : restapi.rb <commandstring>
|
9
|
+
|
10
|
+
Steps for using the API:
|
11
|
+
1:) fingerpuppet --init --certname my.cert.name --server my.server.name
|
12
|
+
Builds the config file
|
13
|
+
Generates the certificate and CSR
|
14
|
+
Submits the CSR to the Puppetmaster
|
15
|
+
|
16
|
+
2:) On puppetmaster: puppet cert sign my.cert.name
|
17
|
+
|
18
|
+
3:) restapi.rb --install
|
19
|
+
Downloads the signed certificate and installs it
|
20
|
+
|
21
|
+
4:) ...
|
22
|
+
|
23
|
+
5:) Profit!
|
24
|
+
|
25
|
+
Your Puppetmaster must be configured to allow requests other than certificate requests.
|
26
|
+
See http://docs.puppetlabs.com/guides/rest_auth_conf.html for more information.
|
27
|
+
|
28
|
+
The certname can be specified with --certname or with optional CERTNAME argument to many options.
|
29
|
+
|
30
|
+
You may want to use the '-dcn' options to print the cURL equivalent command.
|
31
|
+
|
32
|
+
"
|
33
|
+
|
34
|
+
options[:show]=false
|
35
|
+
opts.on("-d", "--debug", "runs in debug mode") do
|
36
|
+
options[:debug] = true
|
37
|
+
#restAPI.debug
|
38
|
+
end
|
39
|
+
|
40
|
+
opts.on("-h", "--help", "Displays this help") do
|
41
|
+
puts opts
|
42
|
+
exit
|
43
|
+
end
|
44
|
+
|
45
|
+
opts.on("-c", "--curl", "Use commandline curl rather than Net::HTTP.") do
|
46
|
+
options[:curl] = true
|
47
|
+
end
|
48
|
+
|
49
|
+
opts.on("-n", "--nop", "No-Op mode. Don't perform action, just output debugging data. Implies --debug.") do
|
50
|
+
options[:nop] = true
|
51
|
+
options[:debug] = true
|
52
|
+
end
|
53
|
+
|
54
|
+
opts.separator('')
|
55
|
+
|
56
|
+
opts.on("--server SERVER", "The server address of your Puppetmaster.") do |server|
|
57
|
+
options[:server] = server
|
58
|
+
end
|
59
|
+
|
60
|
+
opts.on("--certname CERTNAME", "The certname you wish to use when connecting to your Puppetmaster") do |certname|
|
61
|
+
options[:certname] = certname
|
62
|
+
end
|
63
|
+
|
64
|
+
opts.on("--file FILENAME", "The file to send to the Puppetmaster.") do |filename|
|
65
|
+
options[:filename] = filename
|
66
|
+
end
|
67
|
+
|
68
|
+
opts.on("--output FILENAME", "The file to save any output to.") do |filename|
|
69
|
+
options[:output] = filename
|
70
|
+
end
|
71
|
+
|
72
|
+
opts.on("--state STATE", "The desired state you want to set.") do |state|
|
73
|
+
options[:state] = state
|
74
|
+
end
|
75
|
+
|
76
|
+
opts.separator('')
|
77
|
+
|
78
|
+
opts.on("--init", "Initialize application. Generate config file, certificate and submit CSR. Requires --certname and --server.") do
|
79
|
+
options[:action] = 'init'
|
80
|
+
end
|
81
|
+
|
82
|
+
opts.on("--install", "Download and install signed certificate.") do
|
83
|
+
options[:action] = 'install'
|
84
|
+
end
|
85
|
+
|
86
|
+
opts.separator('')
|
87
|
+
|
88
|
+
opts.on("--catalog", "Download the catalog compiled for your app's certname. Quite often just the default Node.") do
|
89
|
+
options[:action] = 'catalog'
|
90
|
+
end
|
91
|
+
|
92
|
+
opts.on("--delete [CERTNAME]", "Remove certificate and facts about a node from Puppetmaster.") do |certname|
|
93
|
+
options[:action] = 'delete'
|
94
|
+
options[:certname] ||= certname
|
95
|
+
end
|
96
|
+
|
97
|
+
opts.on("--facts [CERTNAME]", "Retrieve the facts known about a given certname.") do |certname|
|
98
|
+
options[:action] = 'facts'
|
99
|
+
options[:certname] ||= certname
|
100
|
+
end
|
101
|
+
|
102
|
+
opts.on("--insert [CERTNAME]", "Send facts for a given certname to the Puppetmaster. Requires --file.") do |certname|
|
103
|
+
options[:action] = 'insert'
|
104
|
+
options[:certname] ||= certname
|
105
|
+
end
|
106
|
+
|
107
|
+
opts.on("--node [CERTNAME]", "Retrieve the node information (including facts) known about a given certname.") do |certname|
|
108
|
+
options[:action] = 'node'
|
109
|
+
options[:certname] ||= certname
|
110
|
+
end
|
111
|
+
|
112
|
+
opts.on("--search QUERY", Array, "Retrieve the nodes matching a comma separated query string (e.g. kernel=Linux,virtual=vmware)") do |query|
|
113
|
+
options[:action] = 'search'
|
114
|
+
options[:query] = query
|
115
|
+
end
|
116
|
+
|
117
|
+
opts.separator('')
|
118
|
+
|
119
|
+
opts.on("--certificate [CERTNAME]", "Retrieve the certificate for a given certname or 'ca'.") do |certname|
|
120
|
+
options[:action] = 'certificate'
|
121
|
+
options[:certname] ||= certname
|
122
|
+
end
|
123
|
+
|
124
|
+
opts.on("--cert_status [CERTNAME]", "Retrieve the certificate status for a given certname. Set the status by using --state.") do |certname|
|
125
|
+
options[:action] = 'certificate_status'
|
126
|
+
options[:certname] ||= certname
|
127
|
+
end
|
128
|
+
|
129
|
+
opts.on("--cert_revocation_list", "Retrieve and display the certifiacte revocation list from the master.") do
|
130
|
+
options[:action] = 'certificate_revocation_list'
|
131
|
+
end
|
132
|
+
|
133
|
+
opts.on("--sign [CERTNAME]", "Instruct the Puppetmaster to sign a certificate. Requires significate privileges in auth.conf.") do |certname|
|
134
|
+
options[:action] = 'sign'
|
135
|
+
options[:certname] ||= certname
|
136
|
+
end
|
137
|
+
|
138
|
+
opts.separator('')
|
139
|
+
|
140
|
+
opts.on("--file_metadata PATH", "Retrieve the metadata for a file.") do |path|
|
141
|
+
options[:action] = 'file_metadata'
|
142
|
+
options[:argument] = path
|
143
|
+
end
|
144
|
+
|
145
|
+
opts.on("--getfile PATH", "Download a file from the Puppetmaster. Save to --file or output on stdout.") do |path|
|
146
|
+
options[:action] = 'getfile'
|
147
|
+
options[:argument] = path
|
148
|
+
end
|
149
|
+
|
150
|
+
opts.separator('')
|
151
|
+
|
152
|
+
opts.on("--resource RESOURCE", "Returns a list of resources (e.g. user) or information about a resource (e.g. 'user/elvis')") do |resource|
|
153
|
+
options[:action] = 'resource'
|
154
|
+
options[:argument] = resource
|
155
|
+
end
|
156
|
+
|
157
|
+
opts.on("--report [CERTNAME]", "Sends a YAML report to the Puppetmaster. Requires --file or --state.") do |certname|
|
158
|
+
options[:action] = 'report'
|
159
|
+
options[:certname] ||= certname
|
160
|
+
end
|
161
|
+
|
162
|
+
opts.on("--status", "Check to make sure the Puppetmaster is alive and well.") do
|
163
|
+
options[:action] = 'status'
|
164
|
+
end
|
165
|
+
}
|
166
|
+
|
167
|
+
begin
|
168
|
+
optparse.parse!
|
169
|
+
|
170
|
+
restAPI = Fingerpuppet::RestAPI.new( options )
|
171
|
+
# if certname isn't specified, let's default to our certname, except for init
|
172
|
+
if options[:action] != 'init'
|
173
|
+
options[:certname] ||= restAPI.certname
|
174
|
+
end
|
175
|
+
|
176
|
+
case options[:action]
|
177
|
+
when 'init'
|
178
|
+
restAPI.init(options[:certname], options[:server])
|
179
|
+
when 'install'
|
180
|
+
restAPI.install
|
181
|
+
when 'catalog'
|
182
|
+
restAPI.catalog
|
183
|
+
when 'status'
|
184
|
+
restAPI.status
|
185
|
+
when 'facts'
|
186
|
+
restAPI.facts(options[:certname])
|
187
|
+
when 'node'
|
188
|
+
restAPI.node(options[:certname])
|
189
|
+
when 'search'
|
190
|
+
restAPI.search(options[:query])
|
191
|
+
when 'insert'
|
192
|
+
restAPI.insert(options[:certname], options[:filename])
|
193
|
+
when 'delete'
|
194
|
+
restAPI.delete(options[:certname])
|
195
|
+
when 'file_metadata'
|
196
|
+
restAPI.file_metadata(options[:argument])
|
197
|
+
when 'getfile'
|
198
|
+
restAPI.getfile(options[:argument])
|
199
|
+
when 'certificate'
|
200
|
+
restAPI.certificate(options[:certname])
|
201
|
+
when 'sign'
|
202
|
+
restAPI.sign(options[:certname])
|
203
|
+
when 'certificate_status'
|
204
|
+
restAPI.certificate_status(options[:certname], options[:state])
|
205
|
+
when 'certificate_revocation_list'
|
206
|
+
restAPI.certificate_revocation_list
|
207
|
+
when 'resource'
|
208
|
+
restAPI.resource(options[:argument])
|
209
|
+
when 'report'
|
210
|
+
restAPI.report(options[:certname], options[:filename], options[:state])
|
211
|
+
else
|
212
|
+
puts 'Use -h/--help for usage documentation.'
|
213
|
+
end
|
214
|
+
rescue Exception => e
|
215
|
+
puts e
|
216
|
+
end
|
@@ -0,0 +1,331 @@
|
|
1
|
+
require 'yaml'
|
2
|
+
require "net/https"
|
3
|
+
|
4
|
+
module Fingerpuppet
|
5
|
+
class RestAPI
|
6
|
+
attr_accessor :server, :certname
|
7
|
+
|
8
|
+
def initialize( options={} )
|
9
|
+
@debug = options[:debug]
|
10
|
+
@curl = options[:curl]
|
11
|
+
@nop = options[:nop]
|
12
|
+
@output = options[:output]
|
13
|
+
@configdir = File.expand_path('~/.fingerpuppet')
|
14
|
+
|
15
|
+
begin
|
16
|
+
config = YAML.load_file("#{@configdir}/config.yaml")
|
17
|
+
@server = config['server']
|
18
|
+
@certname = config['certname']
|
19
|
+
rescue Exception => e
|
20
|
+
puts 'Initializing API...'
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
# a helper that allows one to use either commandline curl or Net::HTTP
|
25
|
+
# this is useful mostly with -dcn to just print out the curl commandline
|
26
|
+
# you would use to accomplish what you're trying to do
|
27
|
+
def command( opts={} )
|
28
|
+
# this allows a global @output var, but to also override that per call
|
29
|
+
opts[:output] ||= @output
|
30
|
+
|
31
|
+
if @curl
|
32
|
+
curl(opts)
|
33
|
+
else
|
34
|
+
data = rest(opts)
|
35
|
+
|
36
|
+
if opts[:output]
|
37
|
+
save(opts[:output], data)
|
38
|
+
else
|
39
|
+
# When using the API, you will probably want to consume this data rather than just printing it.
|
40
|
+
# You might use YAML::load(data) or JSON::parse(data) depending on what's being returned
|
41
|
+
puts data
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
def save(path, data)
|
47
|
+
file = File.new(path, 'w')
|
48
|
+
file.syswrite(data)
|
49
|
+
file.close
|
50
|
+
end
|
51
|
+
|
52
|
+
def rest( opts={} )
|
53
|
+
opts[:type] ||= 'yaml'
|
54
|
+
uri = "/production/#{opts[:action]}/#{opts[:argument]}"
|
55
|
+
|
56
|
+
http = Net::HTTP.new(@server, 8140)
|
57
|
+
http.use_ssl = true
|
58
|
+
|
59
|
+
unless opts[:noauth]
|
60
|
+
http.verify_mode = OpenSSL::SSL::VERIFY_PEER
|
61
|
+
|
62
|
+
store = OpenSSL::X509::Store.new
|
63
|
+
store.add_cert(OpenSSL::X509::Certificate.new(File.read("#{@configdir}/ca_crt.pem")))
|
64
|
+
http.cert_store = store
|
65
|
+
|
66
|
+
http.key = OpenSSL::PKey::RSA.new(File.read("#{@configdir}/#{@certname}.key"))
|
67
|
+
http.cert = OpenSSL::X509::Certificate.new(File.read("#{@configdir}/#{@certname}.pem"))
|
68
|
+
end
|
69
|
+
|
70
|
+
case opts[:method]
|
71
|
+
when 'PUT'
|
72
|
+
request = Net::HTTP::Put.new(uri)
|
73
|
+
request["Content-Type"] = "text/#{opts[:type]}"
|
74
|
+
|
75
|
+
if opts[:file]
|
76
|
+
# set the body to the binary contents of :file
|
77
|
+
file = File.open(opts[:file], 'rb')
|
78
|
+
request.body = file.read
|
79
|
+
else
|
80
|
+
# set the body to the string value of :data
|
81
|
+
request.body = opts[:data]
|
82
|
+
end
|
83
|
+
|
84
|
+
when 'DELETE'
|
85
|
+
request = Net::HTTP::Delete.new(uri)
|
86
|
+
when 'HEAD'
|
87
|
+
request = Net::HTTP::Head.new(uri)
|
88
|
+
else
|
89
|
+
# default to a GET request
|
90
|
+
request = Net::HTTP::Get.new(uri)
|
91
|
+
end
|
92
|
+
|
93
|
+
request["Accept"] = opts[:type]
|
94
|
+
|
95
|
+
if @debug
|
96
|
+
puts '------ HTTP Request ------'
|
97
|
+
puts request.to_yaml
|
98
|
+
puts '--------------------------'
|
99
|
+
end
|
100
|
+
|
101
|
+
return @nop ? '' : http.request(request).body
|
102
|
+
end
|
103
|
+
|
104
|
+
#def command(action, argument='', method='GET', type='yaml', output=false, file=false, data=false)
|
105
|
+
def curl( opts={} )
|
106
|
+
opts[:type] ||= 'yaml'
|
107
|
+
|
108
|
+
if opts[:noauth]
|
109
|
+
auth = '-k '
|
110
|
+
else
|
111
|
+
auth = "--cert #{@configdir}/#{@certname}.pem --key #{@configdir}/#{@certname}.key --cacert #{@configdir}/ca_crt.pem"
|
112
|
+
end
|
113
|
+
|
114
|
+
output = opts[:output] ? "-o #{opts[:output]}" : ''
|
115
|
+
header = "-H 'Accept: #{opts[:type]}'"
|
116
|
+
|
117
|
+
case opts[:method]
|
118
|
+
when 'PUT'
|
119
|
+
methodstr = '-X PUT'
|
120
|
+
header = "-H 'Content-Type: text/#{opts[:type]}'"
|
121
|
+
|
122
|
+
if opts[:file]
|
123
|
+
filestr = "--data-binary @#{opts[:file]}"
|
124
|
+
end
|
125
|
+
|
126
|
+
if opts[:data]
|
127
|
+
datastr = "--data '#{opts[:data]}'"
|
128
|
+
end
|
129
|
+
|
130
|
+
when 'DELETE'
|
131
|
+
methodstr = '-X DELETE'
|
132
|
+
when 'HEAD'
|
133
|
+
methodstr = '-I'
|
134
|
+
else
|
135
|
+
# default to a GET request
|
136
|
+
methodstr = ''
|
137
|
+
end
|
138
|
+
|
139
|
+
uri = "https://#{@server}:8140/production/#{opts[:action]}/#{opts[:argument]}"
|
140
|
+
cmd = "curl #{auth} #{methodstr} #{output} #{filestr} #{datastr} #{header} \"#{uri}\"" #quoted uri for fact ampersands
|
141
|
+
if @debug
|
142
|
+
puts cmd
|
143
|
+
else
|
144
|
+
if not system(cmd)
|
145
|
+
raise StandardError, 'cURL execution failed.'
|
146
|
+
end
|
147
|
+
puts # newline after curl output
|
148
|
+
end
|
149
|
+
end
|
150
|
+
|
151
|
+
def init(certname, server)
|
152
|
+
if certname == nil || server == nil
|
153
|
+
puts "Must set server and certname to initialize API"
|
154
|
+
exit
|
155
|
+
end
|
156
|
+
|
157
|
+
@certname = certname
|
158
|
+
@server = server
|
159
|
+
|
160
|
+
if File::directory?( @configdir )
|
161
|
+
require 'fileutils'
|
162
|
+
FileUtils.rm_rf( @configdir )
|
163
|
+
end
|
164
|
+
|
165
|
+
Dir.mkdir( @configdir )
|
166
|
+
configfile = File.new("#{@configdir}/config.yaml", 'w')
|
167
|
+
configfile.syswrite("version: 0.1\n")
|
168
|
+
configfile.syswrite("certname: #{@certname}\n")
|
169
|
+
configfile.syswrite("server: #{@server}\n")
|
170
|
+
configfile.close
|
171
|
+
|
172
|
+
begin
|
173
|
+
if not system("openssl genrsa -out #{@configdir}/#{@certname}.key 1024")
|
174
|
+
raise StandardError, 'Certificate generation failed.'
|
175
|
+
end
|
176
|
+
|
177
|
+
if not system("openssl req -new -key #{@configdir}/#{@certname}.key -subj '/CN=#{@certname}' -out #{@configdir}/#{@certname}.csr")
|
178
|
+
raise StandardError, 'CSR generation failed.'
|
179
|
+
end
|
180
|
+
|
181
|
+
self.command( { :action => 'certificate_request',
|
182
|
+
:argument => @certname,
|
183
|
+
:file => "#{@configdir}/#{@certname}.csr",
|
184
|
+
:type => 'plain',
|
185
|
+
:method => 'PUT',
|
186
|
+
:noauth => true } )
|
187
|
+
|
188
|
+
puts "CSR submitted. Now go sign it on the server and rerun this with --install."
|
189
|
+
rescue Exception => e
|
190
|
+
puts "Failure: #{e.message}"
|
191
|
+
end
|
192
|
+
end
|
193
|
+
|
194
|
+
def install
|
195
|
+
begin
|
196
|
+
self.command( { :action => 'certificate',
|
197
|
+
:argument => @certname,
|
198
|
+
:output => "#{@configdir}/#{@certname}.pem",
|
199
|
+
:type => 's',
|
200
|
+
:noauth => true } )
|
201
|
+
|
202
|
+
self.command( { :action => 'certificate',
|
203
|
+
:argument => 'ca',
|
204
|
+
:output => "#{@configdir}/ca_crt.pem",
|
205
|
+
:type => 's',
|
206
|
+
:noauth => true } )
|
207
|
+
|
208
|
+
puts "Certificate installed. API ready for use."
|
209
|
+
rescue Exception => e
|
210
|
+
puts "Failure: #{e.message}"
|
211
|
+
end
|
212
|
+
end
|
213
|
+
|
214
|
+
def catalog
|
215
|
+
self.command( { :action => 'catalog',
|
216
|
+
:argument => @certname } )
|
217
|
+
end
|
218
|
+
|
219
|
+
def status
|
220
|
+
self.command( { :action => 'status',
|
221
|
+
:argument => 'no_key' } )
|
222
|
+
end
|
223
|
+
|
224
|
+
def facts(node)
|
225
|
+
self.command( { :action => 'facts',
|
226
|
+
:argument => node } )
|
227
|
+
end
|
228
|
+
|
229
|
+
def search(query)
|
230
|
+
query.map!{ |item| "facts.#{item}"}
|
231
|
+
self.command( { :action => 'facts_search',
|
232
|
+
:argument => "search?#{query.join('&')}" } )
|
233
|
+
end
|
234
|
+
|
235
|
+
def node(node)
|
236
|
+
self.command( { :action => 'node',
|
237
|
+
:argument => node } )
|
238
|
+
end
|
239
|
+
|
240
|
+
def insert(node, path)
|
241
|
+
self.command( { :action => 'facts',
|
242
|
+
:argument => node,
|
243
|
+
:method => 'PUT',
|
244
|
+
:file => path } )
|
245
|
+
end
|
246
|
+
|
247
|
+
def file_metadata(path)
|
248
|
+
self.command( { :action => 'file_content',
|
249
|
+
:argument => path,
|
250
|
+
:type => 'yaml' } )
|
251
|
+
end
|
252
|
+
|
253
|
+
def getfile(path)
|
254
|
+
self.command( { :action => 'file_content',
|
255
|
+
:argument => path,
|
256
|
+
:type => 'raw' } )
|
257
|
+
end
|
258
|
+
|
259
|
+
def delete(node)
|
260
|
+
self.certificate_status(node, 'revoked')
|
261
|
+
self.command( { :action => 'certificate_status',
|
262
|
+
:argument => node,
|
263
|
+
:method => 'DELETE',
|
264
|
+
:type => 'pson' } )
|
265
|
+
end
|
266
|
+
|
267
|
+
def certificate(node)
|
268
|
+
self.command( { :action => 'certificate',
|
269
|
+
:argument => node,
|
270
|
+
:type => 's' } )
|
271
|
+
end
|
272
|
+
|
273
|
+
def sign(node)
|
274
|
+
self.command( { :action => 'certificate_status',
|
275
|
+
:argument => node,
|
276
|
+
:method => 'PUT',
|
277
|
+
:type => 'pson',
|
278
|
+
:noauth => true,
|
279
|
+
:data => "{\"desired_state\":\"signed\"}" } )
|
280
|
+
end
|
281
|
+
|
282
|
+
def certificate_revocation_list
|
283
|
+
self.command( { :action => 'certificate_revocation_list',
|
284
|
+
:argument => 'ca',
|
285
|
+
:type => 's' } )
|
286
|
+
end
|
287
|
+
|
288
|
+
def certificate_status(node, state=nil)
|
289
|
+
if node == nil
|
290
|
+
self.command( { :action => 'certificate_statuses',
|
291
|
+
:action => 'no_key',
|
292
|
+
:type => 'pson' } )
|
293
|
+
elsif state == nil
|
294
|
+
self.command( { :action => 'certificate_status',
|
295
|
+
:argument => node,
|
296
|
+
:type => 'pson' } )
|
297
|
+
else
|
298
|
+
self.command( { :action => 'certificate_status',
|
299
|
+
:argument => node,
|
300
|
+
:method => 'PUT',
|
301
|
+
:type => 'pson',
|
302
|
+
:data => "{\"desired_state\":\"#{state}\"}" } )
|
303
|
+
end
|
304
|
+
end
|
305
|
+
|
306
|
+
def resource(resource)
|
307
|
+
self.command( { :action => 'resource',
|
308
|
+
:argument => resource } )
|
309
|
+
end
|
310
|
+
|
311
|
+
def report(node, file, data=nil)
|
312
|
+
if data
|
313
|
+
self.command( { :action => 'report',
|
314
|
+
:argument => node,
|
315
|
+
:method => 'PUT',
|
316
|
+
:data => data } )
|
317
|
+
else
|
318
|
+
self.command( { :action => 'report',
|
319
|
+
:argument => node,
|
320
|
+
:method => 'PUT',
|
321
|
+
:file => file } )
|
322
|
+
end
|
323
|
+
end
|
324
|
+
|
325
|
+
def debug
|
326
|
+
puts "@configdir: #{@configdir}"
|
327
|
+
puts " @server: #{@server}"
|
328
|
+
puts " @certname: #{@certname}"
|
329
|
+
end
|
330
|
+
end
|
331
|
+
end
|
metadata
ADDED
@@ -0,0 +1,65 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: fingerpuppet
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
prerelease: false
|
5
|
+
segments:
|
6
|
+
- 0
|
7
|
+
- 0
|
8
|
+
- 1
|
9
|
+
version: 0.0.1
|
10
|
+
platform: ruby
|
11
|
+
authors:
|
12
|
+
- Ben Ford
|
13
|
+
autorequire:
|
14
|
+
bindir: bin
|
15
|
+
cert_chain: []
|
16
|
+
|
17
|
+
date: 2013-03-28 00:00:00 -07:00
|
18
|
+
default_executable:
|
19
|
+
dependencies: []
|
20
|
+
|
21
|
+
description: " A simple library and tool to interact with Puppet's REST API without needing Puppet itself installed.\n"
|
22
|
+
email: binford2k@gmail.com
|
23
|
+
executables:
|
24
|
+
- fingerpuppet
|
25
|
+
extensions: []
|
26
|
+
|
27
|
+
extra_rdoc_files: []
|
28
|
+
|
29
|
+
files:
|
30
|
+
- README.md
|
31
|
+
- LICENSE
|
32
|
+
- bin/fingerpuppet
|
33
|
+
- lib/fingerpuppet/restapi.rb
|
34
|
+
has_rdoc: true
|
35
|
+
homepage: http://github.com/binford2k/fingerpuppet
|
36
|
+
licenses: []
|
37
|
+
|
38
|
+
post_install_message:
|
39
|
+
rdoc_options: []
|
40
|
+
|
41
|
+
require_paths:
|
42
|
+
- lib
|
43
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ">="
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
segments:
|
48
|
+
- 0
|
49
|
+
version: "0"
|
50
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - ">="
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
segments:
|
55
|
+
- 0
|
56
|
+
version: "0"
|
57
|
+
requirements: []
|
58
|
+
|
59
|
+
rubyforge_project:
|
60
|
+
rubygems_version: 1.3.6
|
61
|
+
signing_key:
|
62
|
+
specification_version: 3
|
63
|
+
summary: A simple library and tool to interact with Puppet's REST API without needing Puppet itself installed.
|
64
|
+
test_files: []
|
65
|
+
|