]> gerrit.simantics Code Review - simantics/district.git/blob - org.simantics.maps.server/node/node-v4.8.0-win-x64/node_modules/npm/node_modules/request/node_modules/http-signature/node_modules/sshpk/lib/certificate.js
Adding integrated tile server
[simantics/district.git] / org.simantics.maps.server / node / node-v4.8.0-win-x64 / node_modules / npm / node_modules / request / node_modules / http-signature / node_modules / sshpk / lib / certificate.js
1 // Copyright 2016 Joyent, Inc.
2
3 module.exports = Certificate;
4
5 var assert = require('assert-plus');
6 var algs = require('./algs');
7 var crypto = require('crypto');
8 var Fingerprint = require('./fingerprint');
9 var Signature = require('./signature');
10 var errs = require('./errors');
11 var util = require('util');
12 var utils = require('./utils');
13 var Key = require('./key');
14 var PrivateKey = require('./private-key');
15 var Identity = require('./identity');
16
17 var formats = {};
18 formats['openssh'] = require('./formats/openssh-cert');
19 formats['x509'] = require('./formats/x509');
20 formats['pem'] = require('./formats/x509-pem');
21
22 var CertificateParseError = errs.CertificateParseError;
23 var InvalidAlgorithmError = errs.InvalidAlgorithmError;
24
25 function Certificate(opts) {
26         assert.object(opts, 'options');
27         assert.arrayOfObject(opts.subjects, 'options.subjects');
28         utils.assertCompatible(opts.subjects[0], Identity, [1, 0],
29             'options.subjects');
30         utils.assertCompatible(opts.subjectKey, Key, [1, 0],
31             'options.subjectKey');
32         utils.assertCompatible(opts.issuer, Identity, [1, 0], 'options.issuer');
33         if (opts.issuerKey !== undefined) {
34                 utils.assertCompatible(opts.issuerKey, Key, [1, 0],
35                     'options.issuerKey');
36         }
37         assert.object(opts.signatures, 'options.signatures');
38         assert.buffer(opts.serial, 'options.serial');
39         assert.date(opts.validFrom, 'options.validFrom');
40         assert.date(opts.validUntil, 'optons.validUntil');
41
42         this._hashCache = {};
43
44         this.subjects = opts.subjects;
45         this.issuer = opts.issuer;
46         this.subjectKey = opts.subjectKey;
47         this.issuerKey = opts.issuerKey;
48         this.signatures = opts.signatures;
49         this.serial = opts.serial;
50         this.validFrom = opts.validFrom;
51         this.validUntil = opts.validUntil;
52 }
53
54 Certificate.formats = formats;
55
56 Certificate.prototype.toBuffer = function (format, options) {
57         if (format === undefined)
58                 format = 'x509';
59         assert.string(format, 'format');
60         assert.object(formats[format], 'formats[format]');
61         assert.optionalObject(options, 'options');
62
63         return (formats[format].write(this, options));
64 };
65
66 Certificate.prototype.toString = function (format, options) {
67         if (format === undefined)
68                 format = 'pem';
69         return (this.toBuffer(format, options).toString());
70 };
71
72 Certificate.prototype.fingerprint = function (algo) {
73         if (algo === undefined)
74                 algo = 'sha256';
75         assert.string(algo, 'algorithm');
76         var opts = {
77                 type: 'certificate',
78                 hash: this.hash(algo),
79                 algorithm: algo
80         };
81         return (new Fingerprint(opts));
82 };
83
84 Certificate.prototype.hash = function (algo) {
85         assert.string(algo, 'algorithm');
86         algo = algo.toLowerCase();
87         if (algs.hashAlgs[algo] === undefined)
88                 throw (new InvalidAlgorithmError(algo));
89
90         if (this._hashCache[algo])
91                 return (this._hashCache[algo]);
92
93         var hash = crypto.createHash(algo).
94             update(this.toBuffer('x509')).digest();
95         this._hashCache[algo] = hash;
96         return (hash);
97 };
98
99 Certificate.prototype.isExpired = function (when) {
100         if (when === undefined)
101                 when = new Date();
102         return (!((when.getTime() >= this.validFrom.getTime()) &&
103                 (when.getTime() < this.validUntil.getTime())));
104 };
105
106 Certificate.prototype.isSignedBy = function (issuerCert) {
107         utils.assertCompatible(issuerCert, Certificate, [1, 0], 'issuer');
108
109         if (!this.issuer.equals(issuerCert.subjects[0]))
110                 return (false);
111
112         return (this.isSignedByKey(issuerCert.subjectKey));
113 };
114
115 Certificate.prototype.isSignedByKey = function (issuerKey) {
116         utils.assertCompatible(issuerKey, Key, [1, 2], 'issuerKey');
117
118         if (this.issuerKey !== undefined) {
119                 return (this.issuerKey.
120                     fingerprint('sha512').matches(issuerKey));
121         }
122
123         var fmt = Object.keys(this.signatures)[0];
124         var valid = formats[fmt].verify(this, issuerKey);
125         if (valid)
126                 this.issuerKey = issuerKey;
127         return (valid);
128 };
129
130 Certificate.prototype.signWith = function (key) {
131         utils.assertCompatible(key, PrivateKey, [1, 2], 'key');
132         var fmts = Object.keys(formats);
133         var didOne = false;
134         for (var i = 0; i < fmts.length; ++i) {
135                 if (fmts[i] !== 'pem') {
136                         var ret = formats[fmts[i]].sign(this, key);
137                         if (ret === true)
138                                 didOne = true;
139                 }
140         }
141         if (!didOne) {
142                 throw (new Error('Failed to sign the certificate for any ' +
143                     'available certificate formats'));
144         }
145 };
146
147 Certificate.createSelfSigned = function (subjectOrSubjects, key, options) {
148         var subjects;
149         if (Array.isArray(subjectOrSubjects))
150                 subjects = subjectOrSubjects;
151         else
152                 subjects = [subjectOrSubjects];
153
154         assert.arrayOfObject(subjects);
155         subjects.forEach(function (subject) {
156                 utils.assertCompatible(subject, Identity, [1, 0], 'subject');
157         });
158
159         utils.assertCompatible(key, PrivateKey, [1, 2], 'private key');
160
161         assert.optionalObject(options, 'options');
162         if (options === undefined)
163                 options = {};
164         assert.optionalObject(options.validFrom, 'options.validFrom');
165         assert.optionalObject(options.validUntil, 'options.validUntil');
166         var validFrom = options.validFrom;
167         var validUntil = options.validUntil;
168         if (validFrom === undefined)
169                 validFrom = new Date();
170         if (validUntil === undefined) {
171                 assert.optionalNumber(options.lifetime, 'options.lifetime');
172                 var lifetime = options.lifetime;
173                 if (lifetime === undefined)
174                         lifetime = 10*365*24*3600;
175                 validUntil = new Date();
176                 validUntil.setTime(validUntil.getTime() + lifetime*1000);
177         }
178         assert.optionalBuffer(options.serial, 'options.serial');
179         var serial = options.serial;
180         if (serial === undefined)
181                 serial = new Buffer('0000000000000001', 'hex');
182
183         var cert = new Certificate({
184                 subjects: subjects,
185                 issuer: subjects[0],
186                 subjectKey: key.toPublic(),
187                 issuerKey: key.toPublic(),
188                 signatures: {},
189                 serial: serial,
190                 validFrom: validFrom,
191                 validUntil: validUntil
192         });
193         cert.signWith(key);
194
195         return (cert);
196 };
197
198 Certificate.create =
199     function (subjectOrSubjects, key, issuer, issuerKey, options) {
200         var subjects;
201         if (Array.isArray(subjectOrSubjects))
202                 subjects = subjectOrSubjects;
203         else
204                 subjects = [subjectOrSubjects];
205
206         assert.arrayOfObject(subjects);
207         subjects.forEach(function (subject) {
208                 utils.assertCompatible(subject, Identity, [1, 0], 'subject');
209         });
210
211         utils.assertCompatible(key, Key, [1, 0], 'key');
212         if (PrivateKey.isPrivateKey(key))
213                 key = key.toPublic();
214         utils.assertCompatible(issuer, Identity, [1, 0], 'issuer');
215         utils.assertCompatible(issuerKey, PrivateKey, [1, 2], 'issuer key');
216
217         assert.optionalObject(options, 'options');
218         if (options === undefined)
219                 options = {};
220         assert.optionalObject(options.validFrom, 'options.validFrom');
221         assert.optionalObject(options.validUntil, 'options.validUntil');
222         var validFrom = options.validFrom;
223         var validUntil = options.validUntil;
224         if (validFrom === undefined)
225                 validFrom = new Date();
226         if (validUntil === undefined) {
227                 assert.optionalNumber(options.lifetime, 'options.lifetime');
228                 var lifetime = options.lifetime;
229                 if (lifetime === undefined)
230                         lifetime = 10*365*24*3600;
231                 validUntil = new Date();
232                 validUntil.setTime(validUntil.getTime() + lifetime*1000);
233         }
234         assert.optionalBuffer(options.serial, 'options.serial');
235         var serial = options.serial;
236         if (serial === undefined)
237                 serial = new Buffer('0000000000000001', 'hex');
238
239         var cert = new Certificate({
240                 subjects: subjects,
241                 issuer: issuer,
242                 subjectKey: key,
243                 issuerKey: issuerKey.toPublic(),
244                 signatures: {},
245                 serial: serial,
246                 validFrom: validFrom,
247                 validUntil: validUntil
248         });
249         cert.signWith(issuerKey);
250
251         return (cert);
252 };
253
254 Certificate.parse = function (data, format, options) {
255         if (typeof (data) !== 'string')
256                 assert.buffer(data, 'data');
257         if (format === undefined)
258                 format = 'auto';
259         assert.string(format, 'format');
260         if (typeof (options) === 'string')
261                 options = { filename: options };
262         assert.optionalObject(options, 'options');
263         if (options === undefined)
264                 options = {};
265         assert.optionalString(options.filename, 'options.filename');
266         if (options.filename === undefined)
267                 options.filename = '(unnamed)';
268
269         assert.object(formats[format], 'formats[format]');
270
271         try {
272                 var k = formats[format].read(data, options);
273                 return (k);
274         } catch (e) {
275                 throw (new CertificateParseError(options.filename, format, e));
276         }
277 };
278
279 Certificate.isCertificate = function (obj, ver) {
280         return (utils.isCompatible(obj, Certificate, ver));
281 };
282
283 /*
284  * API versions for Certificate:
285  * [1,0] -- initial ver
286  */
287 Certificate.prototype._sshpkApiVersion = [1, 0];
288
289 Certificate._oldVersionDetect = function (obj) {
290         return ([1, 0]);
291 };