diff --git a/changelog/20125.txt b/changelog/20125.txt new file mode 100644 index 000000000000..07dd8201dba8 --- /dev/null +++ b/changelog/20125.txt @@ -0,0 +1,3 @@ +```release-note:improvement +ui: updates clients configuration edit form state based on census reporting configuration +``` \ No newline at end of file diff --git a/ui/app/components/clients/config.js b/ui/app/components/clients/config.js index b84494b41372..f8f28af23706 100644 --- a/ui/app/components/clients/config.js +++ b/ui/app/components/clients/config.js @@ -18,9 +18,11 @@ import { task } from 'ember-concurrency'; export default class ConfigComponent extends Component { @service router; + @tracked mode = 'show'; @tracked modalOpen = false; - error = null; + @tracked validations; + @tracked error = null; get infoRows() { return [ @@ -38,38 +40,36 @@ export default class ConfigComponent extends Component { } get modalTitle() { - let content = 'Turn usage tracking off?'; - if (this.args.model && this.args.model.enabled === 'On') { - content = 'Turn usage tracking on?'; - } - return content; + return `Turn usage tracking ${this.args.model.enabled.toLowerCase()}?`; } @(task(function* () { try { yield this.args.model.save(); + this.router.transitionTo('vault.cluster.clients.config'); } catch (err) { this.error = err.message; - return; + this.modalOpen = false; } - this.router.transitionTo('vault.cluster.clients.config'); }).drop()) save; @action - updateBooleanValue(attr, value) { - let valueToSet = value === true ? attr.options.trueValue : attr.options.falseValue; - this.args.model[attr.name] = valueToSet; + toggleEnabled(event) { + this.args.model.enabled = event.target.checked ? 'On' : 'Off'; } @action onSaveChanges(evt) { evt.preventDefault(); + const { isValid, state } = this.args.model.validate(); const changed = this.args.model.changedAttributes(); - if (!changed.enabled) { + if (!isValid) { + this.validations = state; + } else if (changed.enabled) { + this.modalOpen = true; + } else { this.save.perform(); - return; } - this.modalOpen = true; } } diff --git a/ui/app/decorators/model-validations.js b/ui/app/decorators/model-validations.js index 1db84446d1e4..c4ae494bfbe2 100644 --- a/ui/app/decorators/model-validations.js +++ b/ui/app/decorators/model-validations.js @@ -108,9 +108,11 @@ export function withModelValidations(validations) { : validator(get(this, key), options); // dot notation may be used to define key for nested property if (!passedValidation) { + // message can also be a function + const validationMessage = typeof message === 'function' ? message(this) : message; // consider setting a prop like validationErrors directly on the model // for now return an errors object - state[key].errors.push(message); + state[key].errors.push(validationMessage); if (isValid) { isValid = false; } diff --git a/ui/app/models/clients/config.js b/ui/app/models/clients/config.js index 49c83a3597c3..bbc91723e662 100644 --- a/ui/app/models/clients/config.js +++ b/ui/app/models/clients/config.js @@ -1,30 +1,43 @@ import Model, { attr } from '@ember-data/model'; -import { computed } from '@ember/object'; -import attachCapabilities from 'vault/lib/attach-capabilities'; -import { expandAttributeMeta } from 'vault/utils/field-to-attrs'; -import { apiPath } from 'vault/macros/lazy-capabilities'; - -const M = Model.extend({ - queriesAvailable: attr('boolean'), - retentionMonths: attr('number', { +import lazyCapabilities, { apiPath } from 'vault/macros/lazy-capabilities'; +import { withFormFields } from 'vault/decorators/model-form-fields'; +import { withModelValidations } from 'vault/decorators/model-validations'; + +const validations = { + retentionMonths: [ + { + validator: (model) => parseInt(model.retentionMonths) >= model.minimumRetentionMonths, + message: (model) => + `Retention period must be greater than or equal to ${model.minimumRetentionMonths}.`, + }, + ], +}; + +@withModelValidations(validations) +@withFormFields(['enabled', 'retentionMonths']) +export default class ClientsConfigModel extends Model { + @attr('boolean') queriesAvailable; // true only if historical data exists, will be false if there is only current month data + + @attr('number', { label: 'Retention period', subText: 'The number of months of activity logs to maintain for client tracking.', - }), - enabled: attr('string', { - editType: 'boolean', - trueValue: 'On', - falseValue: 'Off', - label: 'Enable usage data collection', - helpText: - 'Enable or disable client tracking. Keep in mind that disabling tracking will delete the data for the current month.', - }), - - configAttrs: computed(function () { - let keys = ['enabled', 'retentionMonths']; - return expandAttributeMeta(this, keys); - }), -}); - -export default attachCapabilities(M, { - configPath: apiPath`sys/internal/counters/config`, -}); + }) + retentionMonths; + + @attr('number') minimumRetentionMonths; + + @attr('string') enabled; + + @attr('boolean') reportingEnabled; + + @attr('date') billingStartTimestamp; + + @lazyCapabilities(apiPath`sys/internal/counters/config`) configPath; + + get canRead() { + return this.configPath.get('canRead') !== false; + } + get canEdit() { + return this.configPath.get('canUpdate') !== false; + } +} diff --git a/ui/app/templates/components/clients/config.hbs b/ui/app/templates/components/clients/config.hbs index 5bee8ae24bc5..f87f7659185e 100644 --- a/ui/app/templates/components/clients/config.hbs +++ b/ui/app/templates/components/clients/config.hbs @@ -1,80 +1,38 @@ {{#if (eq @mode "edit")}} -
++
Vault will start tracking data starting from today’s date, - {{date-format (now) "d MMMM yyyy"}}. You will not be able to see or query usage until the end of the month. + {{date-format (now) "MMMM d, yyyy"}}. If you’ve previously enabled usage tracking, that historical data will still + be available to you.
-If you’ve previously enabled usage tracking, that historical data will still be available to you.
{{else}} -+
Turning usage tracking off means that all data for the current month will be deleted. You will still be able to query previous months.
@@ -106,24 +65,26 @@ {{/if}}