From 1fcf55471da40d115ab8efe052648d16aa516d15 Mon Sep 17 00:00:00 2001 From: Vault Automation Date: Tue, 2 Sep 2025 12:57:27 -0600 Subject: [PATCH] UI: Add plugin settings route and tab to configuration page (#9031) (#9039) * adding plugin settings tab and route * updating plugin settings * removing current when for secret engine nav link * fix tab name * adding empty state Co-authored-by: Dan Rivera --- .../components/secret-engine/page-header.hbs | 12 ++ .../secret-engine/page/plugin-settings.hbs | 62 ++++++++++ .../secret-engine/page/plugin-settings.ts | 107 ++++++++++++++++++ ui/app/components/sidebar/nav/cluster.hbs | 7 +- ui/app/router.js | 3 +- .../backend/configuration/plugin-settings.hbs | 6 + 6 files changed, 190 insertions(+), 7 deletions(-) create mode 100644 ui/app/components/secret-engine/page/plugin-settings.hbs create mode 100644 ui/app/components/secret-engine/page/plugin-settings.ts create mode 100644 ui/app/templates/vault/cluster/secrets/backend/configuration/plugin-settings.hbs diff --git a/ui/app/components/secret-engine/page-header.hbs b/ui/app/components/secret-engine/page-header.hbs index 635e94293e..f341166c27 100644 --- a/ui/app/components/secret-engine/page-header.hbs +++ b/ui/app/components/secret-engine/page-header.hbs @@ -31,6 +31,18 @@ General settings + {{! If engine is not configurable, hide plugin settings link }} + {{#if (get (engines-display-data @model.secretsEngine.type) "isConfigurable")}} +
  • + + {{get (engines-display-data @model.secretsEngine.type) "displayName"}} + settings + +
  • + {{/if}} diff --git a/ui/app/components/secret-engine/page/plugin-settings.hbs b/ui/app/components/secret-engine/page/plugin-settings.hbs new file mode 100644 index 0000000000..a4a49e7a0f --- /dev/null +++ b/ui/app/components/secret-engine/page/plugin-settings.hbs @@ -0,0 +1,62 @@ +{{! + Copyright (c) HashiCorp, Inc. + SPDX-License-Identifier: BUSL-1.1 +}} + + + +{{#if @model.config}} + {{#each this.displayFields as |field|}} + {{! public key while not sensitive when editing/creating, should be hidden by default on viewing }} + {{#if (eq field "public_key")}} + + + + {{else}} + + {{/if}} + {{/each}} +{{else}} + {{#if (get (engines-display-data @model.secretsEngine.type) "isConfigurable")}} + {{! Prompt user to configure the secret engine }} + + + + + {{else}} + + + + {{/if}} +{{/if}} \ No newline at end of file diff --git a/ui/app/components/secret-engine/page/plugin-settings.ts b/ui/app/components/secret-engine/page/plugin-settings.ts new file mode 100644 index 0000000000..de69022fff --- /dev/null +++ b/ui/app/components/secret-engine/page/plugin-settings.ts @@ -0,0 +1,107 @@ +/** + * Copyright (c) HashiCorp, Inc. + * SPDX-License-Identifier: BUSL-1.1 + */ + +import Component from '@glimmer/component'; +import { toLabel } from 'core/helpers/to-label'; +import engineDisplayData from 'vault/helpers/engines-display-data'; +import SecretsEngineResource from 'vault/resources/secrets/engine'; + +/** + * @module PluginSettingsComponent is used to configure extended plugin level settings for secrets engines. + * + * @example + * ```js + * + * ``` + * + * @param {string} secretsEngine - secrets engine resource + */ + +interface Args { + model: { + secretsEngine: SecretsEngineResource; + }; +} + +export default class PluginSettingsComponent extends Component { + awsFields = [ + 'role_arn', + 'identity_token_audience', + 'identity_token_ttl', + 'access_key', + 'region', + 'iam_endpoint', + 'sts_endpoint', + 'max_retries', + 'lease', + 'lease_max', + 'issuer', + ]; + + azureFields = [ + 'subscription_id', + 'tenant_id', + 'client_id', + 'identity_token_audience', + 'identity_token_ttl', + 'root_password_ttl', + 'environment', + 'issuer', + ]; + + gcpFields = [ + 'service_account_email', + 'ttl', + 'max_ttl', + 'identity_token_audience', + 'identity_token_ttl', + 'issuer', + ]; + + sshFields = ['public_key', 'generate_signing_key']; + + get displayFields() { + switch (engineDisplayData(this.args.model.secretsEngine.type)?.displayName) { + case 'AWS': + return this.awsFields; + case 'Azure': + return this.azureFields; + case 'Google Cloud': + return this.gcpFields; + case 'SSH': + return this.sshFields; + default: + return []; + } + } + + label = (field: string) => { + const label = toLabel([field]); + // convert words like id and ttl to uppercase + const formattedLabel = label + .split(' ') + .map((word: string) => { + const acronyms = ['id', 'ttl', 'arn', 'iam', 'sts']; + return acronyms.includes(word.toLowerCase()) ? word.toUpperCase() : word; + }) + .join(' '); + // map specific fields to custom labels + return ( + { + lease: 'Default Lease TTL', + lease_max: 'Max Lease TTL', + ttl: 'Config TTL', + }[field] || formattedLabel + ); + }; + + isDuration = (field: string) => { + return ['identity_token_ttl', 'root_password_ttl', 'lease', 'lease_max', 'ttl', 'max_ttl'].includes( + field + ); + }; +} diff --git a/ui/app/components/sidebar/nav/cluster.hbs b/ui/app/components/sidebar/nav/cluster.hbs index b2435eea86..bc409fc454 100644 --- a/ui/app/components/sidebar/nav/cluster.hbs +++ b/ui/app/components/sidebar/nav/cluster.hbs @@ -7,12 +7,7 @@ Vault - + {{#if this.showSecretsSync}} \ No newline at end of file