mirror of
				https://github.com/optim-enterprises-bv/vault.git
				synced 2025-10-31 02:28:09 +00:00 
			
		
		
		
	UI: pki import issuer (#18634)
* create pki ca import component * add serial number to cert parser * convert to ts * remove comments * reset yarn.lock * fixed yarn lock * fix comment * add declaration for base cert
This commit is contained in:
		| @@ -21,6 +21,22 @@ export default class PkiIssuerAdapter extends ApplicationAdapter { | |||||||
|     } |     } | ||||||
|   } |   } | ||||||
|  |  | ||||||
|  |   createRecord(store, type, snapshot) { | ||||||
|  |     const { record, adapterOptions } = snapshot; | ||||||
|  |     let url = this.urlForQuery(record.backend); | ||||||
|  |     if (adapterOptions.import) { | ||||||
|  |       url = `${url}/import/bundle`; | ||||||
|  |     } else { | ||||||
|  |       // TODO WIP generate root or intermediate CSR actions from issuers index page | ||||||
|  |       // certType = 'root' || 'intermediate',   // record.type is internal or exported | ||||||
|  |       // url = ` ${url}/generate/${certType}/${record.type}`; | ||||||
|  |       throw new Error('createRecord method in adapters/pki/issuer.js is incomplete.'); | ||||||
|  |     } | ||||||
|  |     return this.ajax(url, 'POST', { data: this.serialize(snapshot) }).then((resp) => { | ||||||
|  |       return resp; | ||||||
|  |     }); | ||||||
|  |   } | ||||||
|  |  | ||||||
|   query(store, type, query) { |   query(store, type, query) { | ||||||
|     return this.ajax(this.urlForQuery(query.backend), 'GET', this.optionsForQuery()); |     return this.ajax(this.urlForQuery(query.backend), 'GET', this.optionsForQuery()); | ||||||
|   } |   } | ||||||
|   | |||||||
| @@ -1,6 +1,7 @@ | |||||||
| import { helper } from '@ember/component/helper'; | import { helper } from '@ember/component/helper'; | ||||||
| import * as asn1js from 'asn1js'; | import * as asn1js from 'asn1js'; | ||||||
| import { fromBase64, stringToArrayBuffer } from 'pvutils'; | import { fromBase64, stringToArrayBuffer } from 'pvutils'; | ||||||
|  | import { Convert } from 'pvtsutils'; | ||||||
| import { Certificate } from 'pkijs'; | import { Certificate } from 'pkijs'; | ||||||
|  |  | ||||||
| export function parseCertificate(certificateContent) { | export function parseCertificate(certificateContent) { | ||||||
| @@ -43,9 +44,13 @@ export function parseCertificate(certificateContent) { | |||||||
|   // field themselves are Time values. |   // field themselves are Time values. | ||||||
|   const expiryDate = cert?.notAfter?.value; |   const expiryDate = cert?.notAfter?.value; | ||||||
|   const issueDate = cert?.notBefore?.value; |   const issueDate = cert?.notBefore?.value; | ||||||
|  |   const serialNumber = Convert.ToHex(cert.serialNumber.valueBlock.valueHex) | ||||||
|  |     .match(/.{1,2}/g) | ||||||
|  |     .join(':'); | ||||||
|   return { |   return { | ||||||
|     can_parse: true, |     can_parse: true, | ||||||
|     common_name: commonName, |     common_name: commonName, | ||||||
|  |     serial_number: serialNumber, | ||||||
|     expiry_date: expiryDate, |     expiry_date: expiryDate, | ||||||
|     issue_date: issueDate, |     issue_date: issueDate, | ||||||
|     not_valid_after: expiryDate.valueOf(), |     not_valid_after: expiryDate.valueOf(), | ||||||
|   | |||||||
| @@ -42,6 +42,11 @@ export default class PkiCertificateBaseModel extends Model { | |||||||
|   @attr('date') notValidAfter; |   @attr('date') notValidAfter; | ||||||
|   @attr('date') notValidBefore; |   @attr('date') notValidBefore; | ||||||
|  |  | ||||||
|  |   // For importing | ||||||
|  |   @attr('string') pemBundle; | ||||||
|  |   @attr importedIssuers; | ||||||
|  |   @attr importedKeys; | ||||||
|  |  | ||||||
|   @lazyCapabilities(apiPath`${'backend'}/revoke`, 'backend') revokePath; |   @lazyCapabilities(apiPath`${'backend'}/revoke`, 'backend') revokePath; | ||||||
|   get canRevoke() { |   get canRevoke() { | ||||||
|     return this.revokePath.get('isLoading') || this.revokePath.get('canCreate') !== false; |     return this.revokePath.get('isLoading') || this.revokePath.get('canCreate') !== false; | ||||||
|   | |||||||
							
								
								
									
										36
									
								
								ui/lib/pki/addon/components/pki-ca-certificate-import.hbs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										36
									
								
								ui/lib/pki/addon/components/pki-ca-certificate-import.hbs
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,36 @@ | |||||||
|  | <div class="field"> | ||||||
|  |   <div class="form-section"> | ||||||
|  |     <label class="title has-padding-top is-5"> | ||||||
|  |       Certificate parameters | ||||||
|  |     </label> | ||||||
|  |     <form {{on "submit" (perform this.submitForm)}} data-test-pki-ca-cert-import-form> | ||||||
|  |       <MessageError @errorMessage={{this.errorBanner}} class="has-top-margin-s" /> | ||||||
|  |       <div class="box is-sideless is-fullwidth is-marginless has-top-padding-l"> | ||||||
|  |         <TextFile @onChange={{this.onFileUploaded}} @label="PEM Bundle" /> | ||||||
|  |         <p class="has-top-margin-m has-bottom-margin-l"> | ||||||
|  |           Issuer URLs (Issuing certificates, CRL distribution points, OCSP servers, and delta CRL URLs) can be specified by | ||||||
|  |           editing the individual issuer once it is uploaded to Vault. | ||||||
|  |         </p> | ||||||
|  |       </div> | ||||||
|  |       <div class="has-top-padding-s"> | ||||||
|  |         <button | ||||||
|  |           type="submit" | ||||||
|  |           class="button is-primary {{if this.submitForm.isRunning 'is-loading'}}" | ||||||
|  |           disabled={{this.submitForm.isRunning}} | ||||||
|  |           data-test-pki-ca-cert-import | ||||||
|  |         > | ||||||
|  |           Import issuer | ||||||
|  |         </button> | ||||||
|  |         <button | ||||||
|  |           type="button" | ||||||
|  |           class="button has-left-margin-s" | ||||||
|  |           disabled={{this.submitForm.isRunning}} | ||||||
|  |           {{on "click" this.cancel}} | ||||||
|  |           data-test-pki-ca-cert-cancel | ||||||
|  |         > | ||||||
|  |           Cancel | ||||||
|  |         </button> | ||||||
|  |       </div> | ||||||
|  |     </form> | ||||||
|  |   </div> | ||||||
|  | </div> | ||||||
							
								
								
									
										60
									
								
								ui/lib/pki/addon/components/pki-ca-certificate-import.ts
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										60
									
								
								ui/lib/pki/addon/components/pki-ca-certificate-import.ts
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,60 @@ | |||||||
|  | import { action } from '@ember/object'; | ||||||
|  | import Component from '@glimmer/component'; | ||||||
|  | import FlashMessageService from 'vault/services/flash-messages'; | ||||||
|  | import { inject as service } from '@ember/service'; | ||||||
|  | import { task } from 'ember-concurrency'; | ||||||
|  | import { tracked } from '@glimmer/tracking'; | ||||||
|  | import { waitFor } from '@ember/test-waiters'; | ||||||
|  | import errorMessage from 'vault/utils/error-message'; | ||||||
|  | import PkiBaseCertificateModel from 'vault/models/pki/certificate/base'; | ||||||
|  |  | ||||||
|  | /** | ||||||
|  |  * @module PkiCaCertificateImport | ||||||
|  |  * PkiCaCertificateImport components are used to import PKI CA certificates and keys via pem_bundle. | ||||||
|  |  * https://github.com/hashicorp/vault/blob/main/website/content/api-docs/secret/pki.mdx#import-ca-certificates-and-keys | ||||||
|  |  * | ||||||
|  |  * @example | ||||||
|  |  * ```js | ||||||
|  |  * <PkiCaCertificateImport @model={{this.model}} /> | ||||||
|  |  * ``` | ||||||
|  |  * | ||||||
|  |  * @param {Object} model - certificate model from route | ||||||
|  |  * @callback onCancel - Callback triggered when cancel button is clicked. | ||||||
|  |  * @callback onSubmit - Callback triggered on submit success. | ||||||
|  |  */ | ||||||
|  |  | ||||||
|  | interface Args { | ||||||
|  |   onSave: CallableFunction; | ||||||
|  |   onCancel: CallableFunction; | ||||||
|  |   model: PkiBaseCertificateModel; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | export default class PkiCaCertificateImport extends Component<Args> { | ||||||
|  |   @service declare readonly flashMessages: FlashMessageService; | ||||||
|  |  | ||||||
|  |   @tracked errorBanner = ''; | ||||||
|  |  | ||||||
|  |   @task | ||||||
|  |   @waitFor | ||||||
|  |   *submitForm(event: Event) { | ||||||
|  |     event.preventDefault(); | ||||||
|  |     try { | ||||||
|  |       yield this.args.model.save({ adapterOptions: { import: true } }); | ||||||
|  |       this.flashMessages.success('Successfully imported certificate.'); | ||||||
|  |       this.args.onSave(); | ||||||
|  |     } catch (error) { | ||||||
|  |       this.errorBanner = errorMessage(error); | ||||||
|  |     } | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   @action | ||||||
|  |   onFileUploaded({ value }: { value: string }) { | ||||||
|  |     this.args.model.pemBundle = value; | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   @action | ||||||
|  |   cancel() { | ||||||
|  |     this.args.model.unloadRecord(); | ||||||
|  |     this.args.onCancel(); | ||||||
|  |   } | ||||||
|  | } | ||||||
| @@ -1,6 +1,15 @@ | |||||||
| import PkiIssuersIndexRoute from '.'; | import PkiIssuersIndexRoute from '.'; | ||||||
|  | import { inject as service } from '@ember/service'; | ||||||
|  | import { withConfirmLeave } from 'core/decorators/confirm-leave'; | ||||||
|  |  | ||||||
|  | @withConfirmLeave() | ||||||
| export default class PkiIssuersImportRoute extends PkiIssuersIndexRoute { | export default class PkiIssuersImportRoute extends PkiIssuersIndexRoute { | ||||||
|  |   @service store; | ||||||
|  |  | ||||||
|  |   model() { | ||||||
|  |     return this.store.createRecord('pki/issuer'); | ||||||
|  |   } | ||||||
|  |  | ||||||
|   setupController(controller, resolvedModel) { |   setupController(controller, resolvedModel) { | ||||||
|     super.setupController(controller, resolvedModel); |     super.setupController(controller, resolvedModel); | ||||||
|     controller.breadcrumbs.push({ label: 'import' }); |     controller.breadcrumbs.push({ label: 'import' }); | ||||||
|   | |||||||
| @@ -1,2 +1,16 @@ | |||||||
| {{! https://github.com/hashicorp/vault/blob/main/website/content/api-docs/secret/pki.mdx#import-ca-certificates-and-keys }} | <PageHeader as |p|> | ||||||
| route: issuers.import POST /pki/issuers/import/bundle POST /pki/issuers/import/cert |   <p.top> | ||||||
|  |     <Page::Breadcrumbs @breadcrumbs={{this.breadcrumbs}} /> | ||||||
|  |   </p.top> | ||||||
|  |   <p.levelLeft> | ||||||
|  |     <h1 class="title is-3" data-test-pki-issuer-page-title> | ||||||
|  |       Import a CA | ||||||
|  |     </h1> | ||||||
|  |   </p.levelLeft> | ||||||
|  | </PageHeader> | ||||||
|  |  | ||||||
|  | <PkiCaCertificateImport | ||||||
|  |   @model={{this.model}} | ||||||
|  |   @onCancel={{transition-to "vault.cluster.secrets.backend.pki.issuers.index"}} | ||||||
|  |   @onSave={{transition-to "vault.cluster.secrets.backend.pki.issuers.index"}} | ||||||
|  | /> | ||||||
| @@ -254,6 +254,7 @@ | |||||||
|     "highlight.js": "^10.4.1", |     "highlight.js": "^10.4.1", | ||||||
|     "js-yaml": "^3.13.1", |     "js-yaml": "^3.13.1", | ||||||
|     "lodash": "^4.17.13", |     "lodash": "^4.17.13", | ||||||
|     "node-notifier": "^8.0.1" |     "node-notifier": "^8.0.1", | ||||||
|  |     "pvtsutils": "^1.3.2" | ||||||
|   } |   } | ||||||
| } | } | ||||||
|   | |||||||
							
								
								
									
										141
									
								
								ui/tests/integration/components/pki/pki-issuer-import-test.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										141
									
								
								ui/tests/integration/components/pki/pki-issuer-import-test.js
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,141 @@ | |||||||
|  | import { module, test } from 'qunit'; | ||||||
|  | import { setupRenderingTest } from 'ember-qunit'; | ||||||
|  | import { render, click, fillIn } from '@ember/test-helpers'; | ||||||
|  | import { hbs } from 'ember-cli-htmlbars'; | ||||||
|  | import { setupEngine } from 'ember-engines/test-support'; | ||||||
|  | import { setupMirage } from 'ember-cli-mirage/test-support'; | ||||||
|  |  | ||||||
|  | module('Integration | Component | pki issuer import', function (hooks) { | ||||||
|  |   setupRenderingTest(hooks); | ||||||
|  |   setupMirage(hooks); | ||||||
|  |   setupEngine(hooks, 'pki'); // https://github.com/ember-engines/ember-engines/pull/653 | ||||||
|  |  | ||||||
|  |   hooks.beforeEach(function () { | ||||||
|  |     this.store = this.owner.lookup('service:store'); | ||||||
|  |     this.model = this.store.createRecord('pki/issuer'); | ||||||
|  |     this.backend = 'pki-test'; | ||||||
|  |     this.secretMountPath = this.owner.lookup('service:secret-mount-path'); | ||||||
|  |     this.secretMountPath.currentPath = this.backend; | ||||||
|  |     this.pemBundle = ` | ||||||
|  |     -----BEGIN CERTIFICATE----- | ||||||
|  |     MIIDRTCCAi2gAwIBAgIUdKagCL6TnN5xLkwhPbNY8JEcY0YwDQYJKoZIhvcNAQEL | ||||||
|  |     BQAwGzEZMBcGA1UEAxMQd3d3LnRlc3QtaW50LmNvbTAeFw0yMzAxMDkxOTA1NTBa | ||||||
|  |     Fw0yMzAyMTAxOTA2MjBaMBsxGTAXBgNVBAMTEHd3dy50ZXN0LWludC5jb20wggEi | ||||||
|  |     MA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCfd5o9JfyRAXH+E1vE2U0xjSqs | ||||||
|  |     A/cxDqsDXRHBnNJvzAa+7gPKXCDQZbr6chjxLXpP6Bv2/O+dZHq1fo/f6q9PDDGW | ||||||
|  |     JYIluwbACpe7W1UB7q9xFkZg85yQsNYokGZlwv/AMGpFBxDwVlNGL+4fxvFTv7uF | ||||||
|  |     mIlDzSIPrzByyCrqAFMNNqNwlAerDt/C6DMZae/rTGXIXsTfUpxPy21bzkeA+70I | ||||||
|  |     YCV1ffK8UnAeBYNUJ+v8+XgTQ5KhRyQ+fscUkO3T2s6f3O9Q2sWxswkf2YmZB+V1 | ||||||
|  |     cTZ5w6hqiuFdBXz7GRnACi1/gbWbaExQTJRplArFwIHka7dqJh8tYkXDjai3AgMB | ||||||
|  |     AAGjgYAwfjAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4E | ||||||
|  |     FgQU68/xXIgvsleKkuA8clK/6YslB/IwHwYDVR0jBBgwFoAU68/xXIgvsleKkuA8 | ||||||
|  |     clK/6YslB/IwGwYDVR0RBBQwEoIQd3d3LnRlc3QtaW50LmNvbTANBgkqhkiG9w0B | ||||||
|  |     AQsFAAOCAQEAWSff0BH3SJv/XqwN/flqc1CVzOios72/IJ+KBBv0AzFCZ8wJPi+c | ||||||
|  |     hH1bw7tqi01Bgh595TctogDFN1b6pjN+jrlIP4N+FF9Moj79Q+jHQMnuJomyPuI7 | ||||||
|  |     i07vqUcxgSmvEBBWOWS+/vxe6TfWDg18nyPf127CWQN8IHTo1f/GavX+XmRve6XT | ||||||
|  |     EWoqcQshEk9i87oqCbaT7B40jgjTAd1r4Cc6P4s1fAGPt9e9eqMj13kTyVDNuCoD | ||||||
|  |     FSZYalrlkASpg+c9oDQIh2MikGQINXHv/zIEHOW93siKMWeA4ni6phHtMg/p5eJt | ||||||
|  |     SxnVZsSzj8QLy2uwX1AADR0QUvJzMxptyA== | ||||||
|  |     -----END CERTIFICATE----- | ||||||
|  |     -----BEGIN RSA PRIVATE KEY----- | ||||||
|  |     MIIEowIBAAKCAQEAn3eaPSX8kQFx/hNbxNlNMY0qrAP3MQ6rA10RwZzSb8wGvu4D | ||||||
|  |     ylwg0GW6+nIY8S16T+gb9vzvnWR6tX6P3+qvTwwxliWCJbsGwAqXu1tVAe6vcRZG | ||||||
|  |     YPOckLDWKJBmZcL/wDBqRQcQ8FZTRi/uH8bxU7+7hZiJQ80iD68wcsgq6gBTDTaj | ||||||
|  |     cJQHqw7fwugzGWnv60xlyF7E31KcT8ttW85HgPu9CGAldX3yvFJwHgWDVCfr/Pl4 | ||||||
|  |     E0OSoUckPn7HFJDt09rOn9zvUNrFsbMJH9mJmQfldXE2ecOoaorhXQV8+xkZwAot | ||||||
|  |     f4G1m2hMUEyUaZQKxcCB5Gu3aiYfLWJFw42otwIDAQABAoIBADC+vZ4Ne4vTtkWl | ||||||
|  |     Izsj9Y29Chs0xx3uzuWjUGcvib/0zOcWGICF8t3hCuu9btRiQ24jlFDGdnRVH5FV | ||||||
|  |     E6OtuFLgdlPgOU1RQzn2wvTZcT26+VQHLBI8xVIRTBVwNmzK06Sq6AEbrNjaenAM | ||||||
|  |     /KwoAuLHzAmFXAgmr0++DIA5oayPWyi5IoyFO7EoRv79Xz5LWfu5j8CKOFXmI5MT | ||||||
|  |     vEVYM6Gb2xHRa2Ng0SJ4VzwC09GcXlHKRAz+CubJuncvjbcM/EryvexozKkUq4XA | ||||||
|  |     KqGr9xxdZ4XDlo3Rj9S9P9JaOin0I1mwwz6p+iwMF0zr+/ldjE4oPBdB1PUgSJ7j | ||||||
|  |     2CZcS1kCgYEAwIZ3UsMIXqkMlkMz/7nu2sqzV3EgQjY5QRoz98ligKg4fhYKz+K4 | ||||||
|  |     yXvJrRyLkwEBaPdLppCZbs4xsuuv3jiqUHV5n7sfpUA5HVKkKh6XY7jnszbqV732 | ||||||
|  |     iB1mQVEjzM92/amew2hDKLGQDW0nglrg6uV+bx0Lnp6Glahr8NOAyk0CgYEA1Ar3 | ||||||
|  |     jTqTkU+NQX7utlxx0HPVL//JH/erp/Gnq9fN8dZhK/yjwX5savUlNHpgePoXf1pE | ||||||
|  |     lgi21/INQsvp7O2AUKuj96k+jBHQ0SS58AQGFv8iNDkLE57N74vCO6+Xdi1rHj/Y | ||||||
|  |     7jglr00box/7SOmvb4SZz2o0jm0Ejsg2M0aBuRMCgYEAgTB6F34qOqMDgD1eQka5 | ||||||
|  |     QfXs/Es8E1Ihf08e+jIXuC+poOoXnUINL56ySUizXBS7pnzzNbUoUFNqxB4laF/r | ||||||
|  |     4YvC7m15ocED0mpnIKBghBlK2VaLUA93xAS+XiwdcszwkuzkTUnEbyUfffL2JSHo | ||||||
|  |     dZdEDTmXV3wW4Ywfyn2Sma0CgYAeNNG/FLEg6iw9QE/ROqob/+RGyjFklGunqQ0x | ||||||
|  |     tbRo1xlQotTRI6leMz3xk91aXoYqZjmPBf7GFH0/Hr1cOxkkZM8e4MVAPul4Ybr7 | ||||||
|  |     LheP/xhoSBgD24OKtGYfCoyRETdJP98vUGBN8LYXLt8lK+UKBeHDYmXKRE156ZuP | ||||||
|  |     AmRIcQKBgFvp+xMoyAsBeOlTjVDZ0mTnFh1yp8f7N3yXdHPpFShwjXjlqLmLO5RH | ||||||
|  |     mZAvaH0Ux/wCfvwHhdC46jBrs9S4zLBvj3+44NYOzvz2dBWP/5MuXgzFe30h9Yd0 | ||||||
|  |     zUlyEaWm0jY2Ylzax8ECKRL0td2bv36vxOYtTax8MSB15szsnPJ+ | ||||||
|  |     -----END RSA PRIVATE KEY----- | ||||||
|  |     `; | ||||||
|  |   }); | ||||||
|  |  | ||||||
|  |   test('it renders import and updates model', async function (assert) { | ||||||
|  |     assert.expect(3); | ||||||
|  |     await render( | ||||||
|  |       hbs` | ||||||
|  |       <PkiCaCertificateImport | ||||||
|  |          @model={{this.model}} | ||||||
|  |          @onCancel={{this.onCancel}} | ||||||
|  |          @onSave={{this.onSave}} | ||||||
|  |        /> | ||||||
|  |       `, | ||||||
|  |       { owner: this.engine } | ||||||
|  |     ); | ||||||
|  |  | ||||||
|  |     assert.dom('[data-test-pki-ca-cert-import-form]').exists('renders form'); | ||||||
|  |     assert.dom('[data-test-component="text-file"]').exists('renders text file input'); | ||||||
|  |     await click('[data-test-text-toggle]'); | ||||||
|  |     await fillIn('[data-test-text-file-textarea]', this.pemBundle); | ||||||
|  |     assert.strictEqual(this.model.pemBundle, this.pemBundle); | ||||||
|  |   }); | ||||||
|  |  | ||||||
|  |   test('it sends correct payload to import endpoint', async function (assert) { | ||||||
|  |     assert.expect(3); | ||||||
|  |     this.server.post(`/${this.backend}/issuers/import/bundle`, (schema, req) => { | ||||||
|  |       assert.ok(true, 'Request made to the correct endpoint to import issuer'); | ||||||
|  |       const request = JSON.parse(req.requestBody); | ||||||
|  |       assert.propEqual( | ||||||
|  |         request, | ||||||
|  |         { | ||||||
|  |           pem_bundle: `${this.pemBundle}`, | ||||||
|  |         }, | ||||||
|  |         'sends params in correct type' | ||||||
|  |       ); | ||||||
|  |       return {}; | ||||||
|  |     }); | ||||||
|  |  | ||||||
|  |     this.onSave = () => assert.ok(true, 'onSave callback fires on save success'); | ||||||
|  |  | ||||||
|  |     await render( | ||||||
|  |       hbs` | ||||||
|  |       <PkiCaCertificateImport | ||||||
|  |          @model={{this.model}} | ||||||
|  |          @onCancel={{this.onCancel}} | ||||||
|  |          @onSave={{this.onSave}} | ||||||
|  |        /> | ||||||
|  |       `, | ||||||
|  |       { owner: this.engine } | ||||||
|  |     ); | ||||||
|  |  | ||||||
|  |     await click('[data-test-text-toggle]'); | ||||||
|  |     await fillIn('[data-test-text-file-textarea]', this.pemBundle); | ||||||
|  |     assert.strictEqual(this.model.pemBundle, this.pemBundle); | ||||||
|  |     await click('[data-test-pki-ca-cert-import]'); | ||||||
|  |   }); | ||||||
|  |  | ||||||
|  |   test('it should unload record on cancel', async function (assert) { | ||||||
|  |     assert.expect(2); | ||||||
|  |     this.onCancel = () => assert.ok(true, 'onCancel callback fires'); | ||||||
|  |     await render( | ||||||
|  |       hbs` | ||||||
|  |         <PkiCaCertificateImport | ||||||
|  |           @model={{this.model}} | ||||||
|  |           @onCancel={{this.onCancel}} | ||||||
|  |           @onSave={{this.onSave}} | ||||||
|  |         /> | ||||||
|  |       `, | ||||||
|  |       { owner: this.engine } | ||||||
|  |     ); | ||||||
|  |  | ||||||
|  |     await click('[data-test-pki-ca-cert-cancel]'); | ||||||
|  |     assert.true(this.model.isDestroyed, 'new model is unloaded on cancel'); | ||||||
|  |   }); | ||||||
|  | }); | ||||||
							
								
								
									
										5
									
								
								ui/types/generate-declaration.md
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										5
									
								
								ui/types/generate-declaration.md
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,5 @@ | |||||||
|  | To generate a declaration file run `yarn tsc <javascript file to declare>  --declaration --allowJs --emitDeclarationOnly --outDir <type file location>` | ||||||
|  |  | ||||||
|  | For example, the following command generates a declaration file called base.d.ts for the pki certificate base.js model: | ||||||
|  |  | ||||||
|  | `yarn tsc ./app/models/pki/certificate/base.js  --declaration --allowJs --emitDeclarationOnly --outDir types/vault/models/pki/certificate` | ||||||
							
								
								
									
										22
									
								
								ui/types/vault/models/pki/certificate/base.d.ts
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										22
									
								
								ui/types/vault/models/pki/certificate/base.d.ts
									
									
									
									
										vendored
									
									
										Normal file
									
								
							| @@ -0,0 +1,22 @@ | |||||||
|  | import Model from '@ember-data/model'; | ||||||
|  | export default class PkiCertificateBaseModel extends Model { | ||||||
|  |   secretMountPath: class; | ||||||
|  |   get useOpenAPI(): boolean; | ||||||
|  |   get backend(): string; | ||||||
|  |   getHelpUrl(): void; | ||||||
|  |   commonName: string; | ||||||
|  |   caChain: string; | ||||||
|  |   certificate: string; | ||||||
|  |   expiration: number; | ||||||
|  |   issuingCa: string; | ||||||
|  |   privateKey: string; | ||||||
|  |   privateKeyType: string; | ||||||
|  |   serialNumber: string; | ||||||
|  |   notValidAfter: date; | ||||||
|  |   notValidBefore: date; | ||||||
|  |   pemBundle: string; | ||||||
|  |   importedIssuers: string[]; | ||||||
|  |   importedKeys: string[]; | ||||||
|  |   revokePath: string; | ||||||
|  |   get canRevoke(): boolean; | ||||||
|  | } | ||||||
| @@ -15994,6 +15994,13 @@ punycode@^2.1.0, punycode@^2.1.1: | |||||||
|   resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.1.1.tgz#b58b010ac40c22c5657616c8d2c2c02c7bf479ec" |   resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.1.1.tgz#b58b010ac40c22c5657616c8d2c2c02c7bf479ec" | ||||||
|   integrity sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A== |   integrity sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A== | ||||||
|  |  | ||||||
|  | pvtsutils@^1.3.2: | ||||||
|  |   version "1.3.2" | ||||||
|  |   resolved "https://registry.yarnpkg.com/pvtsutils/-/pvtsutils-1.3.2.tgz#9f8570d132cdd3c27ab7d51a2799239bf8d8d5de" | ||||||
|  |   integrity sha512-+Ipe2iNUyrZz+8K/2IOo+kKikdtfhRKzNpQbruF2URmqPtoqAs8g3xS7TJvFF2GcPXjh7DkqMnpVveRFq4PgEQ== | ||||||
|  |   dependencies: | ||||||
|  |     tslib "^2.4.0" | ||||||
|  |  | ||||||
| pvutils@^1.0.17, pvutils@latest: | pvutils@^1.0.17, pvutils@latest: | ||||||
|   version "1.0.17" |   version "1.0.17" | ||||||
|   resolved "https://registry.yarnpkg.com/pvutils/-/pvutils-1.0.17.tgz#ade3c74dfe7178944fe44806626bd2e249d996bf" |   resolved "https://registry.yarnpkg.com/pvutils/-/pvutils-1.0.17.tgz#ade3c74dfe7178944fe44806626bd2e249d996bf" | ||||||
| @@ -18218,7 +18225,7 @@ tslib@^2.0.3: | |||||||
|   resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.2.0.tgz#fb2c475977e35e241311ede2693cee1ec6698f5c" |   resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.2.0.tgz#fb2c475977e35e241311ede2693cee1ec6698f5c" | ||||||
|   integrity sha512-gS9GVHRU+RGn5KQM2rllAlR3dU6m7AcpJKdtH8gFvQiC4Otgk98XnmMU+nZenHt/+VhnBPWwgrJsyrdcw6i23w== |   integrity sha512-gS9GVHRU+RGn5KQM2rllAlR3dU6m7AcpJKdtH8gFvQiC4Otgk98XnmMU+nZenHt/+VhnBPWwgrJsyrdcw6i23w== | ||||||
|  |  | ||||||
| tslib@^2.1.0: | tslib@^2.1.0, tslib@^2.4.0: | ||||||
|   version "2.4.1" |   version "2.4.1" | ||||||
|   resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.4.1.tgz#0d0bfbaac2880b91e22df0768e55be9753a5b17e" |   resolved "https://registry.yarnpkg.com/tslib/-/tslib-2.4.1.tgz#0d0bfbaac2880b91e22df0768e55be9753a5b17e" | ||||||
|   integrity sha512-tGyy4dAjRIEwI7BzsB0lynWgOpfqjUdq91XXAlIWD2OwKBH7oCl/GZG/HT4BOHrTlPMOASlMQ7veyTqpmRcrNA== |   integrity sha512-tGyy4dAjRIEwI7BzsB0lynWgOpfqjUdq91XXAlIWD2OwKBH7oCl/GZG/HT4BOHrTlPMOASlMQ7veyTqpmRcrNA== | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 claire bontempo
					claire bontempo