mirror of
				https://github.com/optim-enterprises-bv/vault.git
				synced 2025-10-31 02:28:09 +00:00 
			
		
		
		
	UI: Add 'disable' to CRL config (#17153)
* add disable to crl attrs * add changelog * change styling per design * update tests and fix default setting of buildCrl * cleanup + refactor
This commit is contained in:
		
							
								
								
									
										2
									
								
								changelog/17153.txt
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										2
									
								
								changelog/17153.txt
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,2 @@ | |||||||
|  | ```release-note:improvement | ||||||
|  | ui: add 'disable' param to pki crl configuration | ||||||
| @@ -37,6 +37,10 @@ export default Component.extend({ | |||||||
|   loading: false, |   loading: false, | ||||||
|  |  | ||||||
|   actions: { |   actions: { | ||||||
|  |     handleCrlTtl({ enabled, goSafeTimeString }) { | ||||||
|  |       this.config.disable = !enabled; // when TTL enabled, config disable=false | ||||||
|  |       this.config.expiry = goSafeTimeString; | ||||||
|  |     }, | ||||||
|     save(section) { |     save(section) { | ||||||
|       this.set('loading', true); |       this.set('loading', true); | ||||||
|       const config = this.config; |       const config = this.config; | ||||||
|   | |||||||
| @@ -47,12 +47,10 @@ export default Model.extend({ | |||||||
|   }), |   }), | ||||||
|  |  | ||||||
|   crlAttrs: computed(function () { |   crlAttrs: computed(function () { | ||||||
|     let keys = ['expiry']; |     let keys = ['expiry', 'disable']; | ||||||
|     return this.attrList(keys); |     return this.attrList(keys); | ||||||
|   }), |   }), | ||||||
|   //crl |   //crl | ||||||
|   expiry: attr({ |   expiry: attr('string', { defaultValue: '72h' }), | ||||||
|     defaultValue: '72h', |   disable: attr('boolean', { defaultValue: false }), | ||||||
|     editType: 'ttl', |  | ||||||
|   }), |  | ||||||
| }); | }); | ||||||
|   | |||||||
| @@ -16,10 +16,22 @@ | |||||||
|  |  | ||||||
| <MessageError @model={{this.config}} @errors={{this.errors}} /> | <MessageError @model={{this.config}} @errors={{this.errors}} /> | ||||||
| <form {{action "save" this.section on="submit"}} class="box is-shadowless is-marginless is-fullwidth has-slim-padding"> | <form {{action "save" this.section on="submit"}} class="box is-shadowless is-marginless is-fullwidth has-slim-padding"> | ||||||
|  |   {{#if (eq this.section "crl")}} | ||||||
|  |     <TtlPicker2 | ||||||
|  |       data-test-input="expiry" | ||||||
|  |       @onChange={{action "handleCrlTtl"}} | ||||||
|  |       @label={{if (get this.config "disable") "CRL building disabled" "CRL building enabled"}} | ||||||
|  |       @helperTextDisabled="The CRL will not be built." | ||||||
|  |       @helperTextEnabled="The CRL will expire after" | ||||||
|  |       @initialValue={{get this.config "expiry"}} | ||||||
|  |       @initialEnabled={{not (get this.config "disable")}} | ||||||
|  |     /> | ||||||
|  |   {{else}} | ||||||
|     {{#each (get this.config (concat this.section "Attrs")) as |attr|}} |     {{#each (get this.config (concat this.section "Attrs")) as |attr|}} | ||||||
|       <FormField @attr={{attr}} @model={{this.config}} @data-test-field={{attr.name}} /> |       <FormField @attr={{attr}} @model={{this.config}} @data-test-field={{attr.name}} /> | ||||||
|     {{/each}} |     {{/each}} | ||||||
|   <div class="field is-grouped box is-fullwidth is-bottomless"> |   {{/if}} | ||||||
|  |   <div class="field has-top-margin-m is-grouped box is-fullwidth is-bottomless"> | ||||||
|     <div class="control"> |     <div class="control"> | ||||||
|       <button |       <button | ||||||
|         data-test-submit |         data-test-submit | ||||||
|   | |||||||
| @@ -1,7 +1,7 @@ | |||||||
| import { resolve } from 'rsvp'; | import { resolve } from 'rsvp'; | ||||||
| import { module, test } from 'qunit'; | import { module, test } from 'qunit'; | ||||||
| import { setupRenderingTest } from 'ember-qunit'; | import { setupRenderingTest } from 'ember-qunit'; | ||||||
| import { render } from '@ember/test-helpers'; | import { click, render } from '@ember/test-helpers'; | ||||||
| import hbs from 'htmlbars-inline-precompile'; | import hbs from 'htmlbars-inline-precompile'; | ||||||
| import { create } from 'ember-cli-page-object'; | import { create } from 'ember-cli-page-object'; | ||||||
| import configPki from 'vault/tests/pages/components/pki/config-pki'; | import configPki from 'vault/tests/pages/components/pki/config-pki'; | ||||||
| @@ -11,71 +11,78 @@ const component = create(configPki); | |||||||
| module('Integration | Component | config pki', function (hooks) { | module('Integration | Component | config pki', function (hooks) { | ||||||
|   setupRenderingTest(hooks); |   setupRenderingTest(hooks); | ||||||
|  |  | ||||||
|   hooks.beforeEach(function () { |   hooks.beforeEach(async function () { | ||||||
|     this.owner.lookup('service:flash-messages').registerTypes(['success']); |     this.owner.lookup('service:flash-messages').registerTypes(['success']); | ||||||
|   }); |     this.store = this.owner.lookup('service:store'); | ||||||
|  |     this.config = await this.store.createRecord('pki/pki-config'); | ||||||
|   const config = function (saveFn) { |     this.mockConfigSave = function (saveFn) { | ||||||
|  |       const { tidyAttrs, crlAttrs, urlsAttrs } = this.config; | ||||||
|       return { |       return { | ||||||
|         save: saveFn, |         save: saveFn, | ||||||
|         rollbackAttributes: () => {}, |         rollbackAttributes: () => {}, | ||||||
|       tidyAttrs: [ |         tidyAttrs, | ||||||
|         { |         crlAttrs, | ||||||
|           type: 'boolean', |         urlsAttrs, | ||||||
|           name: 'tidyCertStore', |         set: () => {}, | ||||||
|         }, |  | ||||||
|         { |  | ||||||
|           type: 'string', |  | ||||||
|           name: 'anotherAttr', |  | ||||||
|         }, |  | ||||||
|       ], |  | ||||||
|       crlAttrs: [ |  | ||||||
|         { |  | ||||||
|           type: 'string', |  | ||||||
|           name: 'crl', |  | ||||||
|         }, |  | ||||||
|       ], |  | ||||||
|       urlsAttrs: [ |  | ||||||
|         { |  | ||||||
|           type: 'string', |  | ||||||
|           name: 'urls', |  | ||||||
|         }, |  | ||||||
|       ], |  | ||||||
|       }; |       }; | ||||||
|     }; |     }; | ||||||
|  |   }); | ||||||
|  |  | ||||||
|   const setupAndRender = async function (context, section = 'tidy') { |   const setupAndRender = async function (context, config, section = 'tidy') { | ||||||
|     context.set('config', config()); |     context.set('config', config); | ||||||
|     context.set('section', section); |     context.set('section', section); | ||||||
|     await context.render(hbs`<Pki::ConfigPki @section={{section}} @config={{config}} />`); |     await context.render(hbs`<Pki::ConfigPki @section={{section}} @config={{config}} />`); | ||||||
|   }; |   }; | ||||||
|  |  | ||||||
|   test('it renders tidy section', async function (assert) { |   test('it renders tidy section', async function (assert) { | ||||||
|     await setupAndRender(this); |     await setupAndRender(this, this.config); | ||||||
|     assert.ok(component.text.startsWith('You can tidy up the backend')); |     assert.ok(component.text.startsWith('You can tidy up the backend')); | ||||||
|     assert.notOk(component.hasTitle, 'No title for tidy section'); |     assert.notOk(component.hasTitle, 'No title for tidy section'); | ||||||
|     assert.equal(component.fields.length, 2); |     assert.equal(component.fields.length, 3, 'renders all three tidy fields'); | ||||||
|     assert.ok(component.fields.objectAt(0).labelText, 'Tidy cert store'); |     assert.ok(component.fields.objectAt(0).labelText, 'Tidy the Certificate Store'); | ||||||
|     assert.ok(component.fields.objectAt(1).labelText, 'Another attr'); |     assert.ok(component.fields.objectAt(1).labelText, 'Tidy the Revocation List (CRL)'); | ||||||
|  |     assert.ok(component.fields.objectAt(1).labelText, 'Safety buffer'); | ||||||
|   }); |   }); | ||||||
|  |  | ||||||
|   test('it renders crl section', async function (assert) { |   test('it renders crl section', async function (assert) { | ||||||
|     await setupAndRender(this, 'crl'); |     await setupAndRender(this, this.config, 'crl'); | ||||||
|     assert.ok(component.hasTitle, 'renders the title'); |     assert.false(this.config.disable, 'CRL config defaults disable=false'); | ||||||
|  |     assert.ok(component.hasTitle, 'renders form title'); | ||||||
|     assert.equal(component.title, 'Certificate Revocation List (CRL) config'); |     assert.equal(component.title, 'Certificate Revocation List (CRL) config'); | ||||||
|     assert.ok(component.text.startsWith('Set the duration for which the generated CRL')); |     assert.ok( | ||||||
|     assert.equal(component.fields.length, 1); |       component.text.startsWith('Set the duration for which the generated CRL'), | ||||||
|     assert.ok(component.fields.objectAt(0).labelText, 'Crl'); |       'renders form subtext' | ||||||
|  |     ); | ||||||
|  |     assert | ||||||
|  |       .dom('[data-test-toggle-label]') | ||||||
|  |       .hasText('CRL building enabled The CRL will expire after', 'renders enabled field title and subtext'); | ||||||
|  |     assert.dom('[data-test-input="expiry"] input').isChecked('defaults to enabling CRL build'); | ||||||
|  |     assert.dom('[data-test-ttl-value="CRL building enabled"]').hasValue('3', 'default value is 3 (72h)'); | ||||||
|  |     assert.dom('[data-test-select="ttl-unit"]').hasValue('d', 'default unit value is days'); | ||||||
|  |     await click('[data-test-input="expiry"] input'); | ||||||
|  |     assert | ||||||
|  |       .dom('[data-test-toggle-label]') | ||||||
|  |       .hasText('CRL building disabled The CRL will not be built.', 'renders disabled text when toggled off'); | ||||||
|  |  | ||||||
|  |     // assert 'disable' attr on pki-config model updates with toggle | ||||||
|  |     assert.true(this.config.disable, 'when toggled off, sets CRL config to disable=true'); | ||||||
|  |     await click('[data-test-input="expiry"] input'); | ||||||
|  |     assert | ||||||
|  |       .dom('[data-test-toggle-label]') | ||||||
|  |       .hasText('CRL building enabled The CRL will expire after', 'toggles back to enabled text'); | ||||||
|  |     assert.false(this.config.disable, 'CRL config toggles back to disable=false'); | ||||||
|   }); |   }); | ||||||
|  |  | ||||||
|   test('it renders urls section', async function (assert) { |   test('it renders urls section', async function (assert) { | ||||||
|     await setupAndRender(this, 'urls'); |     await setupAndRender(this, this.config, 'urls'); | ||||||
|     assert.notOk(component.hasTitle, 'No title for urls section'); |     assert.notOk(component.hasTitle, 'No title for urls section'); | ||||||
|     assert.equal(component.fields.length, 1); |     assert.equal(component.fields.length, 3); | ||||||
|     assert.ok(component.fields.objectAt(0).labelText, 'urls'); |     assert.ok(component.fields.objectAt(0).labelText, 'Issuing certificates'); | ||||||
|  |     assert.ok(component.fields.objectAt(1).labelText, 'CRL Distribution Points'); | ||||||
|  |     assert.ok(component.fields.objectAt(2).labelText, 'OCSP Servers'); | ||||||
|   }); |   }); | ||||||
|  |  | ||||||
|   test('it calls save with the correct arguments', async function (assert) { |   test('it calls save with the correct arguments for tidy', async function (assert) { | ||||||
|     assert.expect(3); |     assert.expect(3); | ||||||
|     const section = 'tidy'; |     const section = 'tidy'; | ||||||
|     this.set('onRefresh', () => { |     this.set('onRefresh', () => { | ||||||
| @@ -83,12 +90,12 @@ module('Integration | Component | config pki', function (hooks) { | |||||||
|     }); |     }); | ||||||
|     this.set( |     this.set( | ||||||
|       'config', |       'config', | ||||||
|       config((options) => { |       this.mockConfigSave((options) => { | ||||||
|         assert.equal(options.adapterOptions.method, section, 'method passed to save'); |         assert.equal(options.adapterOptions.method, section, 'method passed to save'); | ||||||
|         assert.deepEqual( |         assert.deepEqual( | ||||||
|           options.adapterOptions.fields, |           options.adapterOptions.fields, | ||||||
|           ['tidyCertStore', 'anotherAttr'], |           ['tidyCertStore', 'tidyRevocationList', 'safetyBuffer'], | ||||||
|           'fields passed to save' |           'tidy fields passed to save' | ||||||
|         ); |         ); | ||||||
|         return resolve(); |         return resolve(); | ||||||
|       }) |       }) | ||||||
| @@ -98,4 +105,38 @@ module('Integration | Component | config pki', function (hooks) { | |||||||
|  |  | ||||||
|     component.submit(); |     component.submit(); | ||||||
|   }); |   }); | ||||||
|  |  | ||||||
|  |   test('it calls save with the correct arguments for crl', async function (assert) { | ||||||
|  |     assert.expect(3); | ||||||
|  |     const section = 'crl'; | ||||||
|  |     this.set('onRefresh', () => { | ||||||
|  |       assert.ok(true, 'refresh called'); | ||||||
|  |     }); | ||||||
|  |     this.set( | ||||||
|  |       'config', | ||||||
|  |       this.mockConfigSave((options) => { | ||||||
|  |         assert.equal(options.adapterOptions.method, section, 'method passed to save'); | ||||||
|  |         assert.deepEqual(options.adapterOptions.fields, ['expiry', 'disable'], 'CRL fields passed to save'); | ||||||
|  |         return resolve(); | ||||||
|  |       }) | ||||||
|  |     ); | ||||||
|  |     this.set('section', section); | ||||||
|  |     await render(hbs`<Pki::ConfigPki @section={{section}} @config={{config}} @onRefresh={{onRefresh}} />`); | ||||||
|  |     component.submit(); | ||||||
|  |   }); | ||||||
|  |  | ||||||
|  |   test('it correctly sets toggle when initial CRL config is disable=true', async function (assert) { | ||||||
|  |     assert.expect(3); | ||||||
|  |     // change default config attrs | ||||||
|  |     let configDisabled = this.config; | ||||||
|  |     configDisabled.expiry = '1m'; | ||||||
|  |     configDisabled.disable = true; | ||||||
|  |     await setupAndRender(this, configDisabled, 'crl'); | ||||||
|  |     assert.dom('[data-test-input="expiry"] input').isNotChecked('toggle disabled when CRL config disabled'); | ||||||
|  |     await click('[data-test-input="expiry"] input'); | ||||||
|  |     assert | ||||||
|  |       .dom('[data-test-ttl-value="CRL building enabled"]') | ||||||
|  |       .hasValue('1', 'when toggled on shows last set expired value'); | ||||||
|  |     assert.dom('[data-test-select="ttl-unit"]').hasValue('m', 'when toggled back on shows last set unit'); | ||||||
|  |   }); | ||||||
| }); | }); | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 claire bontempo
					claire bontempo