| Class | Puppet::SSLCertificates::Certificate |
| In: |
lib/puppet/sslcertificates/certificate.rb
|
| Parent: | Object |
| SSLCertificates | = | Puppet::SSLCertificates |
| cacert | [RW] | |
| cert | [RW] | |
| certfile | [RW] | |
| csr | [RW] | |
| dir | [RW] | |
| hash | [RW] | |
| key | [RW] | |
| keyfile | [RW] | |
| name | [RW] | |
| type | [RW] |
# File lib/puppet/sslcertificates/certificate.rb, line 55
55: def initialize(hash)
56: unless hash.include?(:name)
57: raise Puppet::Error, "You must specify the common name for the certificate"
58: end
59: @name = hash[:name]
60:
61: # init a few variables
62: @cert = @key = @csr = nil
63:
64: if hash.include?(:cert)
65: @certfile = hash[:cert]
66: @dir = File.dirname(@certfile)
67: else
68: @dir = hash[:dir] || Puppet[:certdir]
69: @certfile = File.join(@dir, @name)
70: end
71:
72: @cacertfile ||= File.join(Puppet[:certdir], "ca.pem")
73:
74: unless FileTest.directory?(@dir)
75: Puppet.recmkdir(@dir)
76: end
77:
78: unless @certfile =~ /\.pem$/
79: @certfile += ".pem"
80: end
81: @keyfile = hash[:key] || File.join(
82: Puppet[:privatekeydir], [@name,"pem"].join(".")
83: )
84: unless FileTest.directory?(@dir)
85: Puppet.recmkdir(@dir)
86: end
87:
88: [@keyfile].each { |file|
89: dir = File.dirname(file)
90:
91: unless FileTest.directory?(dir)
92: Puppet.recmkdir(dir)
93: end
94: }
95:
96: @ttl = hash[:ttl] || 365 * 24 * 60 * 60
97: @selfsign = hash[:selfsign] || false
98: @encrypt = hash[:encrypt] || false
99: @replace = hash[:replace] || false
100: @issuer = hash[:issuer] || nil
101:
102: if hash.include?(:type)
103: case hash[:type]
104: when :ca, :client, :server: @type = hash[:type]
105: else
106: raise "Invalid Cert type %s" % hash[:type]
107: end
108: else
109: @type = :client
110: end
111:
112: @params = {:name => @name}
113: [:state, :country, :email, :org, :ou].each { |param|
114: if hash.include?(param)
115: @params[param] = hash[param]
116: end
117: }
118:
119: if @encrypt
120: if @encrypt =~ /^\//
121: File.open(@encrypt) { |f|
122: @password = f.read.chomp
123: }
124: else
125: raise Puppet::Error, ":encrypt must be a path to a pass phrase file"
126: end
127: else
128: @password = nil
129: end
130:
131: if hash.include?(:selfsign)
132: @selfsign = hash[:selfsign]
133: else
134: @selfsign = false
135: end
136: end
# File lib/puppet/sslcertificates/certificate.rb, line 17
17: def certname
18: OpenSSL::X509::Name.new self.subject
19: end
# File lib/puppet/sslcertificates/certificate.rb, line 21
21: def delete
22: [@certfile,@keyfile].each { |file|
23: if FileTest.exists?(file)
24: File.unlink(file)
25: end
26: }
27:
28: if defined? @hash and @hash
29: if FileTest.symlink?(@hash)
30: File.unlink(@hash)
31: end
32: end
33: end
# File lib/puppet/sslcertificates/certificate.rb, line 35
35: def exists?
36: return FileTest.exists?(@certfile)
37: end
# File lib/puppet/sslcertificates/certificate.rb, line 39
39: def getkey
40: unless FileTest.exists?(@keyfile)
41: self.mkkey()
42: end
43: if @password
44: @key = OpenSSL::PKey::RSA.new(
45: File.read(@keyfile),
46: @password
47: )
48: else
49: @key = OpenSSL::PKey::RSA.new(
50: File.read(@keyfile)
51: )
52: end
53: end
this only works for servers, not for users
# File lib/puppet/sslcertificates/certificate.rb, line 139
139: def mkcsr
140: unless defined? @key and @key
141: self.getkey
142: end
143:
144: name = OpenSSL::X509::Name.new self.subject
145:
146: @csr = OpenSSL::X509::Request.new
147: @csr.version = 0
148: @csr.subject = name
149: @csr.public_key = @key.public_key
150: @csr.sign(@key, OpenSSL::Digest::SHA1.new)
151:
152: #File.open(@csrfile, "w") { |f|
153: # f << @csr.to_pem
154: #}
155:
156: unless @csr.verify(@key.public_key)
157: raise Puppet::Error, "CSR sign verification failed"
158: end
159:
160: return @csr
161: end
# File lib/puppet/sslcertificates/certificate.rb, line 163
163: def mkkey
164: # @key is the file
165:
166: @key = OpenSSL::PKey::RSA.new(1024)
167: # { |p,n|
168: # case p
169: # when 0; Puppet.info "key info: ." # BN_generate_prime
170: # when 1; Puppet.info "key info: +" # BN_generate_prime
171: # when 2; Puppet.info "key info: *" # searching good prime,
172: # # n = #of try,
173: # # but also data from BN_generate_prime
174: # when 3; Puppet.info "key info: \n" # found good prime, n==0 - p, n==1 - q,
175: # # but also data from BN_generate_prime
176: # else; Puppet.info "key info: *" # BN_generate_prime
177: # end
178: # }
179:
180: if @password
181: #passwdproc = proc { @password }
182: keytext = @key.export(
183: OpenSSL::Cipher::DES.new(:EDE3, :CBC),
184: @password
185: )
186: File.open(@keyfile, "w", 0400) { |f|
187: f << keytext
188: }
189: else
190: File.open(@keyfile, "w", 0400) { |f|
191: f << @key.to_pem
192: }
193: end
194:
195: #cmd = "#{ossl} genrsa -out #{@key} 1024"
196: end
# File lib/puppet/sslcertificates/certificate.rb, line 198
198: def mkselfsigned
199: unless defined? @key and @key
200: self.getkey
201: end
202:
203: if defined? @cert and @cert
204: raise Puppet::Error, "Cannot replace existing certificate"
205: end
206:
207: args = {
208: :name => self.certname,
209: :ttl => @ttl,
210: :issuer => nil,
211: :serial => 0x0,
212: :publickey => @key.public_key
213: }
214: if @type
215: args[:type] = @type
216: else
217: args[:type] = :server
218: end
219: @cert = SSLCertificates.mkcert(args)
220:
221: @cert.sign(@key, OpenSSL::Digest::SHA1.new) if @selfsign
222:
223: return @cert
224: end
# File lib/puppet/sslcertificates/certificate.rb, line 226
226: def subject(string = false)
227: subj = @@params2names.collect { |param, name|
228: if @params.include?(param)
229: [name, @params[param]]
230: end
231: }.reject { |ary| ary.nil? }
232:
233: if string
234: return "/" + subj.collect { |ary|
235: "%s=%s" % ary
236: }.join("/") + "/"
237: else
238: return subj
239: end
240: end
# File lib/puppet/sslcertificates/certificate.rb, line 247
247: def write
248: files = {
249: @certfile => @cert,
250: @keyfile => @key,
251: }
252: if defined? @cacert
253: files[@cacertfile] = @cacert
254: end
255:
256: files.each { |file,thing|
257: if defined? thing and thing
258: if FileTest.exists?(file)
259: next
260: end
261:
262: text = nil
263:
264: if thing.is_a?(OpenSSL::PKey::RSA) and @password
265: text = thing.export(
266: OpenSSL::Cipher::DES.new(:EDE3, :CBC),
267: @password
268: )
269: else
270: text = thing.to_pem
271: end
272:
273: File.open(file, "w", 0660) { |f| f.print text }
274: end
275: }
276:
277: if defined? @cacert
278: SSLCertificates.mkhash(Puppet[:certdir], @cacert, @cacertfile)
279: end
280: end