UI: HDS adoption replace Breadcrumbs (#24387)

* upgrade to 3.1.0

* VAULT-22471 upgrade to latest version

* fix other selectors

* fix pki tests

* fix copy dropdown

* generated breadcrumbs

* mfa crumbs

* oidc crumbs

* identity crumbs

* use hds crumbs in page::breadcrumbs file

* rename selectors to be consistent

* remaining oidc

* update empty state link style to match hds

* repl empty state

* rep empty state 2

* policy and secret error template

* replace yielded KeyValueHeader elements directly with HDS breadcrumbs

* remove yield from KeyValueHeader

* use key value header in secret header

* update pki header

* kmip breadcrumbs

* replace key-value-header classes

* ssh sign

* replace key value with breadcrumbs

* update selectors part 1

* add a tags

* policy tests

* add crumb index back

* add current route to generated item

* another round of test updates

* remove root link test selector

* secrets/secrete test

* add changelog

* trailing icon

* delete breadcrumb css

* consistently change to sentence case

* titlsecase!
This commit is contained in:
claire bontempo
2023-12-06 10:56:01 -08:00
committed by GitHub
parent 5bb1451f94
commit 3403203471
69 changed files with 385 additions and 647 deletions

3
changelog/24387.txt Normal file
View File

@@ -0,0 +1,3 @@
```release-note:improvement
ui: Implement Helios Design System Breadcrumbs
```

View File

@@ -53,9 +53,6 @@
a, a,
.link, .link,
a:not(.button):not(.file-delete-button):not(.tag) { a:not(.button):not(.file-delete-button):not(.tag) {
color: $blue;
font-size: $size-8;
font-weight: $font-weight-semibold;
text-decoration: none; text-decoration: none;
} }

View File

@@ -26,7 +26,7 @@
} }
.title { .title {
margin-top: $spacing-36; margin-top: $spacing-16;
} }
.title-with-icon { .title-with-icon {

View File

@@ -21,7 +21,6 @@
// Core Styles: each file styles a class that is not associated with a component. Ex: box and not box-label. // Core Styles: each file styles a class that is not associated with a component. Ex: box and not box-label.
@import './core/box'; @import './core/box';
@import './core/breadcrumb';
@import './core/buttons'; @import './core/buttons';
@import './core/charts'; @import './core/charts';
@import './core/checkbox-and-radio'; @import './core/checkbox-and-radio';

View File

@@ -1,75 +0,0 @@
/**
* Copyright (c) HashiCorp, Inc.
* SPDX-License-Identifier: BUSL-1.1
*/
.breadcrumb {
display: flex;
user-select: text;
min-height: 1.5rem;
margin: 0;
overflow-x: auto;
white-space: nowrap;
&:not(:last-child) {
margin: 0;
}
ul,
ol {
align-items: center;
display: flex;
flex-grow: 1;
flex-shrink: 0;
justify-content: flex-start;
}
li {
align-items: center;
display: flex;
& + li::before {
display: none;
}
&:first-child {
.sep {
margin-left: 0;
}
}
&.is-active a {
color: $grey-darkest;
cursor: default;
pointer-events: none;
}
}
a {
align-items: center;
display: flex;
justify-content: center;
line-height: 1;
padding: 0 $size-11 0 0;
text-decoration: none;
&:hover {
color: $blue;
}
}
.sep {
display: inline-block;
color: transparent;
margin: 0.15rem 0.4rem 0 0.5rem;
overflow: hidden;
width: 0.5rem;
&::before {
color: $blue;
content: '';
font-size: 1rem;
line-height: 1;
opacity: 0.33;
}
}
}

View File

@@ -5,16 +5,14 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text={{@backendPath}}
<span class="sep">&#x0002f;</span> @route="vault.cluster.secrets.backend.overview"
<LinkTo @route="vault.cluster.secrets.backend.overview" @model={{@backendPath}}> @model={{@backendPath}}
{{@backendPath}} />
</LinkTo> <Hds::Breadcrumb::Item @text={{@roleName}} @current={{true}} />
</li> </Hds::Breadcrumb>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 data-test-title class="title is-3"> <h1 data-test-title class="title is-3">
@@ -33,18 +31,12 @@
@bottomBorder={{true}} @bottomBorder={{true}}
@message={{@model.errorMessage}} @message={{@model.errorMessage}}
> >
<nav class="breadcrumb" aria-label="help breadcrumb"> <Hds::Link::Standalone
<ul class="is-grouped-split"> @iconPosition="trailing"
<li> @icon="docs-link"
{{! Empty because they can't go "back" anywhere }} @text="Database documentation"
</li> @href={{doc-link "/vault/docs/secrets/databases"}}
<li> />
<DocLink @path="/vault/docs/secrets/databases" @class="has-text-grey">
Need help?
</DocLink>
</li>
</ul>
</nav>
</EmptyState> </EmptyState>
{{/unless}} {{/unless}}
{{#if (and (not @model.errorMessage) (eq @roleType "dynamic"))}} {{#if (and (not @model.errorMessage) (eq @roleType "dynamic"))}}

View File

@@ -5,28 +5,17 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text={{this.backendPath}}
<span class="sep">&#x0002f;</span> @route="vault.cluster.secrets.backend"
<LinkTo @route="vault.cluster.secrets.backend" @model={{this.backendPath}} data-test-link="role-list"> @model={{this.backendPath}}
{{this.backendPath}} data-test-link="role-list"
</LinkTo> />
</li> <Hds::Breadcrumb::Item @text="Credentials" @route="vault.cluster.secrets.backend" @model={{this.backendPath}} />
<li class="is-active"> <Hds::Breadcrumb::Item @text={{this.roleName}} @route="vault.cluster.secrets.backend.show" @model={{this.roleName}} />
<span class="sep">&#x0002f;</span> <Hds::Breadcrumb::Item @text={{this.options.title}} @current={{true}} />
<LinkTo @route="vault.cluster.secrets.backend" @model={{this.backendPath}}> </Hds::Breadcrumb>
creds
</LinkTo>
</li>
<li>
<span class="sep">&#x0002f;</span>
<LinkTo @route="vault.cluster.secrets.backend.show" @model={{this.roleName}}>
{{this.roleName}}
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 data-test-title class="title is-3"> <h1 data-test-title class="title is-3">

View File

@@ -5,16 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KeyValueHeader @path="vault.cluster.access.methods"> <Hds::Breadcrumb>
<li> <Hds::Breadcrumb::Item @text="Auth Methods" @route="vault.cluster.access.methods" data-test-access-methods />
<span class="sep"> <Hds::Breadcrumb::Item @text={{@methodModel.id}} @current={{true}} />
/ </Hds::Breadcrumb>
</span>
<LinkTo @route="vault.cluster.access.methods" data-test-access-methods>
methods
</LinkTo>
</li>
</KeyValueHeader>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,18 +5,14 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text={{pluralize this.itemType}}
<span class="sep"> @route="vault.cluster.access.method.item.list"
/ @model={{this.itemType}}
</span> />
<LinkTo @route="vault.cluster.access.method.item.list" @model={{this.itemType}}> <Hds::Breadcrumb::Item @text={{if (eq this.mode "show") this.model.id (capitalize this.mode)}} @current={{true}} />
{{pluralize this.itemType}} </Hds::Breadcrumb>
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
{{#if (eq this.mode "show")}} {{#if (eq this.mode "show")}}

View File

@@ -8,16 +8,10 @@
{{else}} {{else}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Enforcements" @route="vault.cluster.access.mfa.enforcements.index" />
<li> <Hds::Breadcrumb::Item @text={{@heading}} @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.access.mfa.enforcements.index">
Enforcements
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-mleh-title> <h1 class="title is-3" data-test-mleh-title>

View File

@@ -5,22 +5,18 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<ul> {{#if @model.isNew}}
<li> <Hds::Breadcrumb::Item @text="Applications" @route="vault.cluster.access.oidc.clients" />
<span class="sep">&#x0002f;</span> {{else}}
{{#if @model.isNew}} <Hds::Breadcrumb::Item
<LinkTo @route="vault.cluster.access.oidc.clients"> @text="Details"
Applications @route="vault.cluster.access.oidc.clients.client.details"
</LinkTo> @model={{@model.name}}
{{else}} />
<LinkTo @route="vault.cluster.access.oidc.clients.client.details" @model={{@model.name}}> {{/if}}
Details <Hds::Breadcrumb::Item @text="{{if @model.isNew 'Create' 'Edit'}} Application" @current={{true}} />
</LinkTo> </Hds::Breadcrumb>
{{/if}}
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-client-title> <h1 class="title is-3" data-test-oidc-client-title>

View File

@@ -5,22 +5,14 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<ul> {{#if @model.isNew}}
<li> <Hds::Breadcrumb::Item @text="Keys" @route="vault.cluster.access.oidc.keys" />
<span class="sep">&#x0002f;</span> {{else}}
{{#if @model.isNew}} <Hds::Breadcrumb::Item @text="Details" @route="vault.cluster.access.oidc.keys.key.details" @model={{@model.name}} />
<LinkTo @route="vault.cluster.access.oidc.keys"> {{/if}}
Keys <Hds::Breadcrumb::Item @text="{{if @model.isNew 'Create' 'Edit'}} Key" @current={{true}} />
</LinkTo> </Hds::Breadcrumb>
{{else}}
<LinkTo @route="vault.cluster.access.oidc.keys.key.details" @model={{@model.name}}>
Details
</LinkTo>
{{/if}}
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-key-title> <h1 class="title is-3" data-test-oidc-key-title>

View File

@@ -5,22 +5,18 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<ul> {{#if @model.isNew}}
<li> <Hds::Breadcrumb::Item @text="Providers" @route="vault.cluster.access.oidc.providers" />
<span class="sep">&#x0002f;</span> {{else}}
{{#if @model.isNew}} <Hds::Breadcrumb::Item
<LinkTo @route="vault.cluster.access.oidc.providers"> @text="Details"
Providers @route="vault.cluster.access.oidc.providers.provider.details"
</LinkTo> @model={{@model.name}}
{{else}} />
<LinkTo @route="vault.cluster.access.oidc.providers.provider.details" @model={{@model.name}}> {{/if}}
Details <Hds::Breadcrumb::Item @text="{{if @model.isNew 'Create' 'Edit'}} Provider" @current={{true}} />
</LinkTo> </Hds::Breadcrumb>
{{/if}}
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-provider-title> <h1 class="title is-3" data-test-oidc-provider-title>

View File

@@ -5,23 +5,18 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> {{#if @model.isNew}}
<li> <Hds::Breadcrumb::Item @text="Scopes" @route="vault.cluster.access.oidc.scopes" />
<span class="sep">&#x0002f;</span> {{else}}
{{#if @model.isNew}} <Hds::Breadcrumb::Item
<LinkTo @route={{"vault.cluster.access.oidc.scopes"}}> @text="Details"
Scopes @route="vault.cluster.access.oidc.scopes.scope.details"
</LinkTo> @model={{@model.name}}
{{else}} />
{{! You're editing in this view }} {{/if}}
<LinkTo @route={{"vault.cluster.access.oidc.scopes.scope.details"}} @model={{@model.name}}> <Hds::Breadcrumb::Item @text="{{if @model.isNew 'Create' 'Edit'}} Scope" @current={{true}} />
Details </Hds::Breadcrumb>
</LinkTo>
{{/if}}
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-scope-title> <h1 class="title is-3" data-test-oidc-scope-title>

View File

@@ -5,16 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="key-value-header breadcrumb"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Raft Storage" @route="vault.cluster.storage" />
<li> <Hds::Breadcrumb::Item @text="Restore Snapshot" @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.storage">
Raft Storage
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,16 +5,13 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text={{capitalize (pluralize (humanize this.model.identityType))}}
<span class="sep">&#x0002f;</span> @route="vault.cluster.access.identity.aliases"
<LinkTo @route="vault.cluster.access.identity.aliases"> />
{{pluralize (humanize this.model.identityType)}} <Hds::Breadcrumb::Item @text={{this.model.name}} @current={{true}} />
</LinkTo> </Hds::Breadcrumb>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,16 +5,13 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text={{capitalize (pluralize this.model.identityType)}}
<span class="sep">&#x0002f;</span> @route="vault.cluster.access.identity.index"
<LinkTo @route="vault.cluster.access.identity.index"> />
{{capitalize (pluralize this.model.identityType)}} <Hds::Breadcrumb::Item @text={{this.model.name}} @current={{true}} />
</LinkTo> </Hds::Breadcrumb>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,16 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KeyValueHeader @path="vault.cluster.access.methods"> <Hds::Breadcrumb>
<li> <Hds::Breadcrumb::Item @text="Auth Methods" @route="vault.cluster.access.methods" />
<span class="sep"> <Hds::Breadcrumb::Item @text={{this.model.id}} @current={{true}} />
/ </Hds::Breadcrumb>
</span>
<LinkTo @route="vault.cluster.access.methods">
methods
</LinkTo>
</li>
</KeyValueHeader>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,16 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumb"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Enforcements" @route="vault.cluster.access.mfa.enforcements.index" />
<li> <Hds::Breadcrumb::Item @text={{this.model.name}} @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.access.mfa.enforcements.index">
Enforcements
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -4,6 +4,12 @@
~}} ~}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top>
<Hds::Breadcrumb>
<Hds::Breadcrumb::Item @text="Methods" @route="vault.cluster.access.mfa.methods.index" />
<Hds::Breadcrumb::Item @text="Configure MFA Method" @current={{true}} />
</Hds::Breadcrumb>
</p.top>
<p.levelLeft class="has-border-bottom-light"> <p.levelLeft class="has-border-bottom-light">
<h1 class="title is-3"> <h1 class="title is-3">
{{#if this.method}} {{#if this.method}}
@@ -15,18 +21,6 @@
{{/if}} {{/if}}
</h1> </h1>
</p.levelLeft> </p.levelLeft>
<p.top>
<nav class="breadcrumb">
<ul>
<li>
<span class="sep">&#x0002f;</span>
<LinkTo @route="vault.cluster.access.mfa.methods.index">
Methods
</LinkTo>
</li>
</ul>
</nav>
</p.top>
</PageHeader> </PageHeader>
<div class="has-border-top-light has-top-padding-l"> <div class="has-border-top-light has-top-padding-l">
{{#if this.showForms}} {{#if this.showForms}}

View File

@@ -5,16 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Methods" @route="vault.cluster.access.mfa.methods.index" />
<li> <Hds::Breadcrumb::Item @text={{this.model.method.name}} @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.access.mfa.methods.index">
Methods
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -6,12 +6,10 @@
{{#if (has-feature "Namespaces")}} {{#if (has-feature "Namespaces")}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<div class="breadcrumb"> <Hds::Breadcrumb>
<LinkTo @route="vault.cluster.access.namespaces.index"> <Hds::Breadcrumb::Item @text="Namespaces" @route="vault.cluster.access.namespaces.index" />
<span class="sep">&#x0002f;</span> <Hds::Breadcrumb::Item @text="Create" @current={{true}} />
Namespaces </Hds::Breadcrumb>
</LinkTo>
</div>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,16 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Assignments" @route="vault.cluster.access.oidc.assignments" />
<li> <Hds::Breadcrumb::Item @text={{@model.name}} @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.access.oidc.assignments">
Assignments
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-assignment-title> <h1 class="title is-3" data-test-oidc-assignment-title>

View File

@@ -5,16 +5,14 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text="Details"
<span class="sep">&#x0002f;</span> @route="vault.cluster.access.oidc.assignments.assignment.details"
<LinkTo @route={{"vault.cluster.access.oidc.assignments.assignment.details"}} @model={{this.model.name}}> @model={{this.model.name}}
Details />
</LinkTo> <Hds::Breadcrumb::Item @text="Edit Assignment" @current={{true}} />
</li> </Hds::Breadcrumb>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-assignment-title> <h1 class="title is-3" data-test-oidc-assignment-title>

View File

@@ -5,16 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Assignments" @route="vault.cluster.access.oidc.assignments" />
<li> <Hds::Breadcrumb::Item @text="Create Assignment" @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route={{"vault.cluster.access.oidc.assignments"}}>
Assignments
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-assignment-title> <h1 class="title is-3" data-test-oidc-assignment-title>

View File

@@ -6,16 +6,10 @@
{{#if this.showHeader}} {{#if this.showHeader}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Applications" @route="vault.cluster.access.oidc.clients" />
<li> <Hds::Breadcrumb::Item @text={{this.model.name}} @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.access.oidc.clients">
Applications
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-client-header> <h1 class="title is-3" data-test-oidc-client-header>

View File

@@ -6,16 +6,10 @@
{{#if this.showHeader}} {{#if this.showHeader}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Keys" @route="vault.cluster.access.oidc.keys" data-test-breadcrumb-link="oidc-keys" />
<li> <Hds::Breadcrumb::Item @text={{this.model.name}} @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.access.oidc.keys" data-test-breadcrumb-link="oidc-keys">
Keys
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -6,16 +6,14 @@
{{#if this.showHeader}} {{#if this.showHeader}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text="Providers"
<span class="sep">&#x0002f;</span> @route="vault.cluster.access.oidc.providers"
<LinkTo @route="vault.cluster.access.oidc.providers" data-test-breadcrumb-link="oidc-providers"> data-test-breadcrumb-link="oidc-providers"
Providers />
</LinkTo> <Hds::Breadcrumb::Item @text={{this.model.name}} @current={{true}} />
</li> </Hds::Breadcrumb>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,16 +5,14 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item
<li> @text="Scopes"
<span class="sep">&#x0002f;</span> @route="vault.cluster.access.oidc.scopes"
<LinkTo @route="vault.cluster.access.oidc.scopes" data-test-breadcrumb-link="oidc-scopes"> data-test-breadcrumb-link="oidc-scopes"
Scopes />
</LinkTo> <Hds::Breadcrumb::Item @text={{this.model.name}} @current={{true}} />
</li> </Hds::Breadcrumb>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-oidc-scope-header> <h1 class="title is-3" data-test-oidc-scope-header>

View File

@@ -5,13 +5,15 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<div class="breadcrumb"> <Hds::Breadcrumb>
<LinkTo @route="vault.cluster.policies" @model={{this.policyType}} data-test-policy-list-link={{true}}> <Hds::Breadcrumb::Item
<span class="sep">&#x0002f;</span> @text="{{uppercase this.policyType}} policies"
{{uppercase this.policyType}} @route="vault.cluster.policies"
Policies @model={{this.policyType}}
</LinkTo> data-test-policy-list-link
</div> />
<Hds::Breadcrumb::Item @text="Create" @current={{true}} />
</Hds::Breadcrumb>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,15 +5,16 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<li> <Hds::Breadcrumb::Item
<LinkTo @route="vault.cluster.policies" @model={{this.policyType}} data-test-policy-list-link={{true}}> @text="{{uppercase this.policyType}} policies"
<span class="sep">&#x0002f;</span> @route="vault.cluster.policies"
{{uppercase this.policyType}} @model={{this.policyType}}
policies data-test-policy-list-link
</LinkTo> />
</li> <Hds::Breadcrumb::Item @text={{this.model.id}} @route="vault.cluster.policy.show" @model={{this.model.id}} />
</nav> <Hds::Breadcrumb::Item @text="Edit" @current={{true}} />
</Hds::Breadcrumb>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,15 +5,15 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<li> <Hds::Breadcrumb::Item
<LinkTo @route="vault.cluster.policies" @model={{this.policyType}} data-test-policy-list-link={{true}}> @text="{{uppercase this.policyType}} policies"
<span class="sep">&#x0002f;</span> @route="vault.cluster.policies"
{{uppercase this.policyType}} @model={{this.policyType}}
policies data-test-policy-list-link
</LinkTo> />
</li> <Hds::Breadcrumb::Item @text={{this.model.id}} @current={{true}} />
</nav> </Hds::Breadcrumb>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-policy-name="true"> <h1 class="title is-3" data-test-policy-name="true">

View File

@@ -13,22 +13,18 @@
@message={{Page.message}} @message={{Page.message}}
@icon="alert-circle" @icon="alert-circle"
@bottomBorder={{true}} @bottomBorder={{true}}
class="is-shadowless"
> >
<nav class="breadcrumb"> <Hds::ButtonSet>
<ul class="is-grouped-split"> <Hds::Link::Standalone @icon="chevron-left" @text="Go back" @route="vault.cluster.secrets.backends" />
<li> <Hds::Link::Standalone
<LinkTo @route="vault.cluster.secrets.backends"> @icon="learn-link"
<span class="sep"></span> @iconPosition="trailing"
Go back @color="secondary"
</LinkTo> @text="Disaster recovery tutorial"
</li> @href={{doc-link "/vault/tutorials/enterprise/disaster-recovery"}}
<li> />
<DocLink @path="/vault/tutorials/enterprise/disaster-recovery" @class="has-text-grey"> </Hds::ButtonSet>
Need help?
</DocLink>
</li>
</ul>
</nav>
</EmptyState> </EmptyState>
{{else}} {{else}}
<Page.dashboard <Page.dashboard

View File

@@ -14,21 +14,16 @@
@icon="alert-circle" @icon="alert-circle"
@bottomBorder={{true}} @bottomBorder={{true}}
> >
<nav class="breadcrumb"> <Hds::ButtonSet>
<ul class="is-grouped-split"> <Hds::Link::Standalone @icon="chevron-left" @text="Go back" @route="vault.cluster.secrets.backends" />
<li> <Hds::Link::Standalone
<LinkTo @route="vault.cluster.secrets.backends"> @icon="learn-link"
<span class="sep"></span> @iconPosition="trailing"
Go back @color="secondary"
</LinkTo> @text="Disaster recovery tutorial"
</li> @href={{doc-link "/vault/tutorials/enterprise/disaster-recovery"}}
<li> />
<DocLink @path="/vault/tutorials/enterprise/disaster-recovery" @class="has-text-grey"> </Hds::ButtonSet>
Need help?
</DocLink>
</li>
</ul>
</nav>
</EmptyState> </EmptyState>
{{else}} {{else}}
<section> <section>

View File

@@ -6,14 +6,12 @@
<div class="box is-shadowless"> <div class="box is-shadowless">
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<li> <Hds::Breadcrumb::Item
<LinkTo @route={{if this.model.backend "vault.cluster.secrets.backend.list-root" "vault.cluster.secrets"}}> @text={{if this.model.backend this.model.backend "Secrets"}}
<span class="sep">&#x0002f;</span> @route={{if this.model.backend "vault.cluster.secrets.backend.list-root" "vault.cluster.secrets"}}
{{if this.model.backend this.model.backend "secrets"}} />
</LinkTo> </Hds::Breadcrumb>
</li>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3 has-text-grey"> <h1 class="title is-3 has-text-grey">

View File

@@ -5,28 +5,16 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="SSH" @route="vault.cluster.secrets.backend" @model={{this.backend.id}} />
<li> <Hds::Breadcrumb::Item @text="Sign" @route="vault.cluster.secrets.backend" @model={{this.backend.id}} />
<span class="sep">&#x0002f;</span> <Hds::Breadcrumb::Item
<LinkTo @route="vault.cluster.secrets.backend" @model={{this.backend.id}}> @text={{this.model.role.name}}
ssh @route="vault.cluster.secrets.backend.show"
</LinkTo> @model={{this.model.role.name}}
</li> />
<li class="is-active"> <Hds::Breadcrumb::Item @text="Sign SSH Key" @current={{true}} />
<span class="sep">&#x0002f;</span> </Hds::Breadcrumb>
<LinkTo @route="vault.cluster.secrets.backend" @model={{this.backend.id}}>
sign
</LinkTo>
</li>
<li>
<span class="sep">&#x0002f;</span>
<LinkTo @route="vault.cluster.secrets.backend.show" @model={{this.model.role.name}}>
{{this.model.role.name}}
</LinkTo>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,7 +5,11 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KeyValueHeader @baseKey={{this.model}} @path="vault.cluster.access.method" @root={{this.root}} @showCurrent={{true}} /> <Hds::Breadcrumb>
<Hds::Breadcrumb::Item @text="Auth Methods" @route="vault.cluster.access.methods" />
<Hds::Breadcrumb::Item @text={{this.model.id}} @route="vault.cluster.access.method" @model={{this.model.id}} />
<Hds::Breadcrumb::Item @text="Configure" @current={{true}} />
</Hds::Breadcrumb>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -3,25 +3,17 @@
SPDX-License-Identifier: BUSL-1.1 SPDX-License-Identifier: BUSL-1.1
~}} ~}}
<nav class="key-value-header breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> {{#each this.secretPath as |path|}}
{{yield}} {{#if this.linkToPaths}}
{{#each this.secretPath as |path index|}} <Hds::Breadcrumb::Item
<li class={{if (is-active-route path.path path.model isExact=true) "is-active"}}> @text={{path.text}}
<span class="sep">&#x0002f;</span> @route={{path.path}}
{{#if this.linkToPaths}} @model={{path.model}}
<LinkTo data-test-secret-breadcrumb={{path.text}}
@route={{path.path}} />
@model={{path.model}} {{else}}
data-test-secret-root-link={{if (eq index 0) true false}} <Hds::Breadcrumb::Item @text={{path.text}} @current={{true}} />
data-test-secret-breadcrumb={{path.text}} {{/if}}
> {{/each}}
{{path.text}} </Hds::Breadcrumb>
</LinkTo>
{{else}}
<span>{{path.text}}</span>
{{/if}}
</li>
{{/each}}
</ul>
</nav>

View File

@@ -3,29 +3,19 @@
SPDX-License-Identifier: BUSL-1.1 SPDX-License-Identifier: BUSL-1.1
~}} ~}}
<nav class="breadcrumb" aria-label="breadcrumbs" data-test-breadcrumbs> <Hds::Breadcrumb data-test-breadcrumbs>
<ul> {{#each @breadcrumbs as |breadcrumb|}}
{{#each @breadcrumbs as |breadcrumb idx|}} <Hds::Breadcrumb::Item
<li data-test-crumb="{{idx}}"> data-test-breadcrumb={{breadcrumb.label}}
<span class="sep">/</span> @text={{breadcrumb.label}}
{{#if breadcrumb.linkExternal}} @icon={{breadcrumb.icon}}
<LinkToExternal @route={{breadcrumb.route}} data-test-breadcrumb={{breadcrumb.label}}> @route={{breadcrumb.route}}
{{breadcrumb.label}} @model={{breadcrumb.model}}
</LinkToExternal> @models={{breadcrumb.models}}
{{else if breadcrumb.route}} @query={{breadcrumb.query}}
{{#if breadcrumb.model}} @isRouteExternal={{breadcrumb.linkExternal}}
<LinkTo @route={{breadcrumb.route}} @model={{breadcrumb.model}} data-test-breadcrumb={{breadcrumb.label}}> {{! only generate a link for crumbs with a route, otherwise assume it's the current view }}
{{breadcrumb.label}} @current={{not breadcrumb.route}}
</LinkTo> />
{{else}} {{/each}}
<LinkTo @route={{breadcrumb.route}} data-test-breadcrumb={{breadcrumb.label}}> </Hds::Breadcrumb>
{{breadcrumb.label}}
</LinkTo>
{{/if}}
{{else}}
{{breadcrumb.label}}
{{/if}}
</li>
{{/each}}
</ul>
</nav>

View File

@@ -1,27 +0,0 @@
/**
* Copyright (c) HashiCorp, Inc.
* SPDX-License-Identifier: BUSL-1.1
*/
import Component from '@glimmer/component';
import { assert } from '@ember/debug';
/**
* @module Page::Breadcrumbs
* Page::Breadcrumbs components are used to display breadcrumb links. This is component will be replaced when HDS system is incorporated
*
* @example
* ```js
* <Page::Breadcrumbs @breadcrumbs={{this.breadcrumbs}} />
* ```
* @param {array} breadcrumbs - array of objects with a label and route to display as breadcrumbs
*/
export default class Breadcrumbs extends Component {
constructor() {
super(...arguments);
this.args.breadcrumbs.forEach((breadcrumb) => {
assert('breadcrumb must have a label key', Object.keys(breadcrumb).includes('label'));
});
}
}

View File

@@ -0,0 +1,40 @@
/**
* Copyright (c) HashiCorp, Inc.
* SPDX-License-Identifier: BUSL-1.1
*/
import Component from '@glimmer/component';
import { assert } from '@ember/debug';
interface Args {
breadcrumbs: Array<Breadcrumb>;
}
interface Breadcrumb {
label: string;
route?: string; // Do not provide for current route
icon?: string;
model?: string;
models?: string[];
linkToExternal?: boolean;
}
/**
* @module Page::Breadcrumbs
* Page::Breadcrumbs components are used to display an array of breadcrumbs at the top of the page.
*
* @example
* ```js
* <Page::Breadcrumbs @breadcrumbs={{this.breadcrumbs}} />
* ```
* @param {array} breadcrumbs - array of Breadcrumb objects, must contain a label key. If no route is provided, crumb is assumed to be the current page
*/
export default class Breadcrumbs extends Component<Args> {
constructor(owner: unknown, args: Args) {
super(owner, args);
assert(
'breadcrumb object must include a label key',
this.args.breadcrumbs.every((crumb) => Object.keys(crumb).includes('label'))
);
}
}

View File

@@ -6,16 +6,18 @@
{{#let (options-for-backend @model.engineType) as |options|}} {{#let (options-for-backend @model.engineType) as |options|}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KeyValueHeader @baseKey={{@baseKey}} @path="vault.cluster.secrets.backend.list" @root={{@backendCrumb}}> <Hds::Breadcrumb>
<li> <Hds::Breadcrumb::Item @text="Secrets" @route="vault.cluster.secrets" />
<span class="sep"> <Hds::Breadcrumb::Item
/ @text={{@model.id}}
</span> @current={{not @isConfigure}}
<LinkTo @route="vault.cluster.secrets"> @route="vault.cluster.secrets.backend.list-root"
secrets @model={{@model.id}}
</LinkTo> />
</li> {{#if @isConfigure}}
</KeyValueHeader> <Hds::Breadcrumb::Item @text="Configure" @current={{true}} />
{{/if}}
</Hds::Breadcrumb>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,19 +5,12 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
{{! template-lint-configure simple-unless "warn" }} {{#if (not (or this.isSummaryDashboard this.isSecondary))}}
{{#unless (or this.isSummaryDashboard this.isSecondary)}} <Hds::Breadcrumb>
<KeyValueHeader @baseKey={{this.baseKey}} @path="vault.cluster.replication-dr-promote" @root={{this.backendCrumb}}> <Hds::Breadcrumb::Item @text="Replication" @route="vault.cluster.replication.index" />
<li> <Hds::Breadcrumb::Item @text={{this.title}} @current={{true}} />
<span class="sep"> </Hds::Breadcrumb>
/ {{/if}}
</span>
<LinkTo @route="vault.cluster.replication.index">
Replication
</LinkTo>
</li>
</KeyValueHeader>
{{/unless}}
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-replication-title> <h1 class="title is-3" data-test-replication-title>

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb @scope={{@scope}} /> <KmipBreadcrumb @scope={{@scope}} @currentRoute={{@role}} />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb /> <KmipBreadcrumb @currentRoute={{this.secretMountPath.currentPath}} />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -3,31 +3,18 @@
SPDX-License-Identifier: BUSL-1.1 SPDX-License-Identifier: BUSL-1.1
~}} ~}}
<nav class="key-value-header breadcrumb"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Secrets" @route="secrets" @isRouteExternal={{true}} />
<li> {{#if this.shouldShowPath}}
<span class="sep">&#x0002f;</span> <Hds::Breadcrumb::Item @text={{this.secretMountPath.currentPath}} @route="scopes.index" />
<LinkToExternal @route="secrets">Secrets</LinkToExternal> {{/if}}
</li> {{#if @scope}}
{{#if this.shouldShowPath}} <Hds::Breadcrumb::Item @text={{@scope}} @route="scope.roles" @model={{@scope}} />
<li> {{/if}}
<span class="sep">&#x0002f;</span> {{#if @role}}
<LinkTo @route="scopes.index"> <Hds::Breadcrumb::Item @text={{@role}} @route="credentials.index" @models={{array @scope @role}} />
{{this.secretMountPath.currentPath}} {{/if}}
</LinkTo> {{#if @currentRoute}}
</li> <Hds::Breadcrumb::Item @text={{@currentRoute}} @current={{true}} />
{{/if}} {{/if}}
{{#if @scope}} </Hds::Breadcrumb>
<li>
<span class="sep">&#x0002f;</span>
<LinkTo @route="scope.roles" @model={{@scope}}>{{@scope}}</LinkTo>
</li>
{{/if}}
{{#if @role}}
<li>
<span class="sep">&#x0002f;</span>
<LinkTo @route="credentials.index" @models={{array @scope @role}}>{{@role}}</LinkTo>
</li>
{{/if}}
</ul>
</nav>

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb @showPath={{true}} /> <KmipBreadcrumb @showPath={{true}} @currentRoute="Configure" />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb @scope={{this.scope}} @role={{this.role}} /> <KmipBreadcrumb @scope={{this.scope}} @role={{this.role}} @currentRoute="Generate Credentials" />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb @scope={{this.scope}} @role={{this.role}} /> <KmipBreadcrumb @scope={{this.scope}} @role={{this.role}} @currentRoute="Credentials" />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb @scope={{this.scope}} @role={{this.role}} /> <KmipBreadcrumb @scope={{this.scope}} @role={{this.role}} @currentRoute="Edit Role" />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb @showPath={{true}} /> <KmipBreadcrumb @showPath={{true}} @currentRoute={{this.scope}} />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,7 +5,7 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<KmipBreadcrumb @scope={{this.scope}} /> <KmipBreadcrumb @scope={{this.scope}} @currentRoute="Create Role" />
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3"> <h1 class="title is-3">

View File

@@ -5,18 +5,10 @@
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Secrets" @route="secrets" @isRouteExternal={{true}} />
<li> <Hds::Breadcrumb::Item @text={{@backend.id}} @current={{true}} />
<span class="sep">/</span> </Hds::Breadcrumb>
<LinkToExternal @route="secrets">secrets</LinkToExternal>
</li>
<li>
<span class="sep">/</span>
<span>{{@backend.id}}</span>
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="title is-3" data-test-header-title> <h1 class="title is-3" data-test-header-title>

View File

@@ -11,20 +11,10 @@
{{#if this.model.replicationAttrs.replicationEnabled}} {{#if this.model.replicationAttrs.replicationEnabled}}
<PageHeader as |p|> <PageHeader as |p|>
<p.top> <p.top>
<nav class="key-value-header breadcrumb" aria-label="breadcrumbs"> <Hds::Breadcrumb>
<ul> <Hds::Breadcrumb::Item @text="Replication" @route="index" data-test-replication-breadcrumb />
<li> <Hds::Breadcrumb::Item @text={{this.model.replicationModeForDisplay}} @current={{true}} />
<LinkTo @route="index"> </Hds::Breadcrumb>
<span class="sep" data-test-replication-breadcrumb></span>
Replication
</LinkTo>
</li>
<li>
<span class="sep"></span>
{{this.model.replicationModeForDisplay}}
</li>
</ul>
</nav>
</p.top> </p.top>
<p.levelLeft> <p.levelLeft>
<h1 class="has-top-margin-m title is-3" data-test-replication-title={{true}}> <h1 class="has-top-margin-m title is-3" data-test-replication-title={{true}}>

View File

@@ -21,7 +21,7 @@ const SELECTORS = {
input: (attr) => `[data-test-input="${attr}"]`, input: (attr) => `[data-test-input="${attr}"]`,
password: '[data-test-textarea]', password: '[data-test-textarea]',
saveBtn: '[data-test-save-config]', saveBtn: '[data-test-save-config]',
methods: '[data-test-access-methods]', methods: '[data-test-access-methods] a',
listItem: '[data-test-list-item-content]', listItem: '[data-test-list-item-content]',
}; };
module('Acceptance | auth backend list', function (hooks) { module('Acceptance | auth backend list', function (hooks) {

View File

@@ -75,8 +75,7 @@ module('Acceptance | aws secret backend', function (hooks) {
`/vault/secrets/${path}/show/${roleName}`, `/vault/secrets/${path}/show/${roleName}`,
`$aws: navigates to the show page on creation` `$aws: navigates to the show page on creation`
); );
await click(`[data-test-secret-breadcrumb="${path}"] a`);
await click('[data-test-secret-root-link]');
assert.strictEqual(currentURL(), `/vault/secrets/${path}/list`); assert.strictEqual(currentURL(), `/vault/secrets/${path}/list`);
assert.ok(findAll(`[data-test-secret-link="${roleName}"]`).length, `aws: role shows in the list`); assert.ok(findAll(`[data-test-secret-link="${roleName}"]`).length, `aws: role shows in the list`);

View File

@@ -69,7 +69,7 @@ module('Acceptance | mfa-login-enforcement', function (hooks) {
'Cancel transitions to enforcements list' 'Cancel transitions to enforcements list'
); );
await click('[data-test-enforcement-create]'); await click('[data-test-enforcement-create]');
await click('.breadcrumb a'); await click('.hds-breadcrumb a');
assert.strictEqual( assert.strictEqual(
currentRouteName(), currentRouteName(),
'vault.cluster.access.mfa.enforcements.index', 'vault.cluster.access.mfa.enforcements.index',
@@ -121,7 +121,7 @@ module('Acceptance | mfa-login-enforcement', function (hooks) {
'vault.cluster.access.mfa.enforcements.enforcement.index', 'vault.cluster.access.mfa.enforcements.enforcement.index',
'Details more menu action transitions to enforcement route' 'Details more menu action transitions to enforcement route'
); );
await click('.breadcrumb a'); await click('.hds-breadcrumb a');
await click('[data-test-popup-menu-trigger]'); await click('[data-test-popup-menu-trigger]');
await click('[data-test-list-item-link="edit"]'); await click('[data-test-list-item-link="edit"]');
assert.strictEqual( assert.strictEqual(

View File

@@ -61,7 +61,7 @@ module('Acceptance | mfa-method', function (hooks) {
'vault.cluster.access.mfa.methods.create', 'vault.cluster.access.mfa.methods.create',
'New method link transitions to create route' 'New method link transitions to create route'
); );
await click('.breadcrumb a'); await click('.hds-breadcrumb a');
const methods = this.getMethods(); const methods = this.getMethods();
const model = this.store.peekRecord('mfa-method', methods[0].id); const model = this.store.peekRecord('mfa-method', methods[0].id);
@@ -81,7 +81,7 @@ module('Acceptance | mfa-method', function (hooks) {
'vault.cluster.access.mfa.methods.method.index', 'vault.cluster.access.mfa.methods.method.index',
'Details more menu action transitions to method route' 'Details more menu action transitions to method route'
); );
await click('.breadcrumb a'); await click('.hds-breadcrumb a');
await click('[data-test-popup-menu-trigger]'); await click('[data-test-popup-menu-trigger]');
await click('[data-test-mfa-method-menu-link="edit"]'); await click('[data-test-mfa-method-menu-link="edit"]');
assert.strictEqual( assert.strictEqual(
@@ -140,7 +140,7 @@ module('Acceptance | mfa-method', function (hooks) {
const value = typeof model[key] === 'boolean' ? (model[key] ? 'Yes' : 'No') : model[key].toString(); const value = typeof model[key] === 'boolean' ? (model[key] ? 'Yes' : 'No') : model[key].toString();
assert.dom(`[data-test-value-div="${label}"]`).hasText(value, `${label} value renders`); assert.dom(`[data-test-value-div="${label}"]`).hasText(value, `${label} value renders`);
}); });
await click('.breadcrumb a'); await click('.hds-breadcrumb a');
} }
await click('[data-test-mfa-method-list-item]'); await click('[data-test-mfa-method-list-item]');
@@ -203,7 +203,7 @@ module('Acceptance | mfa-method', function (hooks) {
'vault.cluster.access.mfa.methods.method.index', 'vault.cluster.access.mfa.methods.method.index',
`${type} method is displayed on save` `${type} method is displayed on save`
); );
await click('.breadcrumb a'); await click('.hds-breadcrumb a');
assert assert
.dom('[data-test-mfa-method-list-item]') .dom('[data-test-mfa-method-list-item]')
.exists({ count: methodCount + index + 1 }, `List updates with new ${type} method`); .exists({ count: methodCount + index + 1 }, `List updates with new ${type} method`);

View File

@@ -100,7 +100,7 @@ module('Acceptance | oidc-config clients and keys', function (hooks) {
.exists('lists correct app with default'); .exists('lists correct app with default');
// create a new key // create a new key
await click('[data-test-breadcrumb-link="oidc-keys"]'); await click('[data-test-breadcrumb-link="oidc-keys"] a');
assert.strictEqual( assert.strictEqual(
currentRouteName(), currentRouteName(),
'vault.cluster.access.oidc.keys.index', 'vault.cluster.access.oidc.keys.index',

View File

@@ -114,7 +114,7 @@ module('Acceptance | oidc-config providers and scopes', function (hooks) {
); );
// navigate to details from index page // navigate to details from index page
await click('[data-test-breadcrumb-link="oidc-scopes"]'); await click('[data-test-breadcrumb-link="oidc-scopes"] a');
await click('[data-test-popup-menu-trigger]'); await click('[data-test-popup-menu-trigger]');
await click('[data-test-oidc-scope-menu-link="details"]'); await click('[data-test-oidc-scope-menu-link="details"]');
assert.strictEqual( assert.strictEqual(
@@ -224,7 +224,7 @@ module('Acceptance | oidc-config providers and scopes', function (hooks) {
.hasText('this is an edit test', 'has correct edited description'); .hasText('this is an edit test', 'has correct edited description');
// create a provider using test-scope // create a provider using test-scope
await click('[data-test-breadcrumb-link="oidc-scopes"]'); await click('[data-test-breadcrumb-link="oidc-scopes"] a');
await click('[data-test-tab="providers"]'); await click('[data-test-tab="providers"]');
assert.dom('[data-test-tab="providers"]').hasClass('active', 'providers tab is active'); assert.dom('[data-test-tab="providers"]').hasClass('active', 'providers tab is active');
await click('[data-test-oidc-provider-create]'); await click('[data-test-oidc-provider-create]');
@@ -368,7 +368,7 @@ module('Acceptance | oidc-config providers and scopes', function (hooks) {
); );
// navigate to details from index page // navigate to details from index page
await click('[data-test-breadcrumb-link="oidc-providers"]'); await click('[data-test-breadcrumb-link="oidc-providers"] a');
assert.strictEqual( assert.strictEqual(
currentRouteName(), currentRouteName(),
'vault.cluster.access.oidc.providers.index', 'vault.cluster.access.oidc.providers.index',

View File

@@ -44,8 +44,7 @@ module('Acceptance | policies (old)', function (hooks) {
); );
assert.dom('[data-test-policy-name]').hasText(policyLower, 'displays the policy name on the show page'); assert.dom('[data-test-policy-name]').hasText(policyLower, 'displays the policy name on the show page');
assert.dom('[data-test-flash-message].is-info').doesNotExist('no flash message is displayed on save'); assert.dom('[data-test-flash-message].is-info').doesNotExist('no flash message is displayed on save');
await click('[data-test-policy-list-link]'); await click('[data-test-policy-list-link] a');
assert assert
.dom(`[data-test-policy-link="${policyLower}"]`) .dom(`[data-test-policy-link="${policyLower}"]`)
.exists({ count: 1 }, 'new policy shown in the list'); .exists({ count: 1 }, 'new policy shown in the list');

View File

@@ -281,7 +281,7 @@ module('Acceptance | secrets/secret/create, read, delete', function (hooks) {
'secret path is encoded in URL' 'secret path is encoded in URL'
); );
assert.dom('h1').hasText(secretPath, 'Path renders correctly on show page'); assert.dom('h1').hasText(secretPath, 'Path renders correctly on show page');
await click(`[data-test-secret-breadcrumb="${firstPath}"]`); await click(`[data-test-secret-breadcrumb="${firstPath}"] a`);
assert.strictEqual( assert.strictEqual(
currentURL(), currentURL(),
`/vault/secrets/${enginePath}/list/${encodeURIComponent(firstPath)}/`, `/vault/secrets/${enginePath}/list/${encodeURIComponent(firstPath)}/`,
@@ -325,7 +325,7 @@ module('Acceptance | secrets/secret/create, read, delete', function (hooks) {
await listPage.filterInput('filter/foo1'); await listPage.filterInput('filter/foo1');
assert.strictEqual(listPage.secrets.length, 1, 'renders only one secret'); assert.strictEqual(listPage.secrets.length, 1, 'renders only one secret');
await listPage.secrets.objectAt(0).click(); await listPage.secrets.objectAt(0).click();
await showPage.breadcrumbs.filterBy('text', 'filter')[0].click(); await click('[data-test-secret-breadcrumb="filter"] a');
assert.strictEqual(listPage.secrets.length, 3, 'renders three secrets'); assert.strictEqual(listPage.secrets.length, 3, 'renders three secrets');
assert.strictEqual(listPage.filterInputValue, 'filter/', 'pageFilter has been reset'); assert.strictEqual(listPage.filterInputValue, 'filter/', 'pageFilter has been reset');
}); });

View File

@@ -54,7 +54,7 @@ module('Acceptance | ldap | libraries', function (hooks) {
isURL(`libraries/test-library/${uri}`), isURL(`libraries/test-library/${uri}`),
`Transitions to ${action} route on list item action menu click` `Transitions to ${action} route on list item action menu click`
); );
await click('[data-test-breadcrumb="libraries"]'); await click('[data-test-breadcrumb="libraries"] a');
} }
}); });

View File

@@ -55,7 +55,7 @@ module('Acceptance | ldap | overview', function (hooks) {
await click('[data-test-config-cta] a'); await click('[data-test-config-cta] a');
assert.true(isURL('configure'), 'Transitions to configure route on cta link click'); assert.true(isURL('configure'), 'Transitions to configure route on cta link click');
await click('[data-test-breadcrumb="ldap-test"]'); await click('[data-test-breadcrumb="ldap-test"] a');
await click('[data-test-toolbar-action="config"]'); await click('[data-test-toolbar-action="config"]');
assert.true(isURL('configure'), 'Transitions to configure route on toolbar link click'); assert.true(isURL('configure'), 'Transitions to configure route on toolbar link click');
}); });
@@ -92,7 +92,7 @@ module('Acceptance | ldap | overview', function (hooks) {
'Transitions to role credentials route on generate credentials action' 'Transitions to role credentials route on generate credentials action'
); );
await click('[data-test-breadcrumb="ldap-test"]'); await click('[data-test-breadcrumb="ldap-test"] a');
await selectChoose('.search-select', 'dynamic-role'); await selectChoose('.search-select', 'dynamic-role');
await click('[data-test-generate-credential-button]'); await click('[data-test-generate-credential-button]');
assert.true( assert.true(

View File

@@ -42,7 +42,7 @@ module('Acceptance | ldap | roles', function (hooks) {
'Transitions to role details route on list item click' 'Transitions to role details route on list item click'
); );
await click('[data-test-breadcrumb="roles"]'); await click('[data-test-breadcrumb="roles"] a');
await click('[data-test-list-item-link]:nth-of-type(2) a'); await click('[data-test-list-item-link]:nth-of-type(2) a');
assert.true( assert.true(
isURL('roles/static/static-role/details'), isURL('roles/static/static-role/details'),
@@ -61,7 +61,7 @@ module('Acceptance | ldap | roles', function (hooks) {
isURL(`roles/dynamic/dynamic-role/${uri}`), isURL(`roles/dynamic/dynamic-role/${uri}`),
`Transitions to ${uri} route on list item action menu click` `Transitions to ${uri} route on list item action menu click`
); );
await click('[data-test-breadcrumb="roles"]'); await click('[data-test-breadcrumb="roles"] a');
} }
}); });
@@ -73,7 +73,7 @@ module('Acceptance | ldap | roles', function (hooks) {
'Transitions to credentials route from toolbar link' 'Transitions to credentials route from toolbar link'
); );
await click('[data-test-breadcrumb="dynamic-role"]'); await click('[data-test-breadcrumb="dynamic-role"] a');
await click('[data-test-edit]'); await click('[data-test-edit]');
assert.true(isURL('roles/dynamic/dynamic-role/edit'), 'Transitions to edit route from toolbar link'); assert.true(isURL('roles/dynamic/dynamic-role/edit'), 'Transitions to edit route from toolbar link');
}); });

View File

@@ -17,7 +17,7 @@ const SELECTORS = {
popupMenu: '[data-test-popup-menu-trigger]', popupMenu: '[data-test-popup-menu-trigger]',
versionsTab: '[data-test-transit-link="versions"]', versionsTab: '[data-test-transit-link="versions"]',
actionsTab: '[data-test-transit-key-actions-link]', actionsTab: '[data-test-transit-key-actions-link]',
rootCrumb: '[data-test-secret-root-link]', rootCrumb: (path) => `[data-test-secret-breadcrumb="${path}"] a`,
card: (action) => `[data-test-transit-card="${action}"]`, card: (action) => `[data-test-transit-card="${action}"]`,
infoRow: (label) => `[data-test-value-div="${label}"]`, infoRow: (label) => `[data-test-value-div="${label}"]`,
form: (item) => `[data-test-transit-key="${item}"]`, form: (item) => `[data-test-transit-key="${item}"]`,
@@ -242,7 +242,7 @@ module('Acceptance | transit (flaky)', function (hooks) {
assert.dom(SELECTORS.infoRow('Deletion allowed')).hasText('false'); assert.dom(SELECTORS.infoRow('Deletion allowed')).hasText('false');
assert.dom(SELECTORS.infoRow('Derived')).hasText('Yes'); assert.dom(SELECTORS.infoRow('Derived')).hasText('Yes');
assert.dom(SELECTORS.infoRow('Convergent encryption')).hasText('Yes'); assert.dom(SELECTORS.infoRow('Convergent encryption')).hasText('Yes');
await click(SELECTORS.rootCrumb); await click(SELECTORS.rootCrumb(this.path));
await click(SELECTORS.popupMenu); await click(SELECTORS.popupMenu);
const actions = findAll('.ember-basic-dropdown-content li'); const actions = findAll('.ember-basic-dropdown-content li');
assert.strictEqual(actions.length, 2, 'shows 2 items in popup menu'); assert.strictEqual(actions.length, 2, 'shows 2 items in popup menu');

View File

@@ -8,7 +8,7 @@ export const PAGE = {
title: '[data-test-header-title]', title: '[data-test-header-title]',
breadcrumbs: '[data-test-breadcrumbs]', breadcrumbs: '[data-test-breadcrumbs]',
breadcrumb: '[data-test-breadcrumbs] li', breadcrumb: '[data-test-breadcrumbs] li',
breadcrumbAtIdx: (idx) => `[data-test-crumb="${idx}"] a`, breadcrumbAtIdx: (idx) => `[data-test-breadcrumbs] li:nth-child(${idx + 1}) a`,
infoRow: '[data-test-component="info-table-row"]', infoRow: '[data-test-component="info-table-row"]',
infoRowValue: (label) => `[data-test-value-div="${label}"]`, infoRowValue: (label) => `[data-test-value-div="${label}"]`,
infoRowToggleMasked: (label) => `[data-test-value-div="${label}"] [data-test-button="toggle-masked"]`, infoRowToggleMasked: (label) => `[data-test-value-div="${label}"] [data-test-button="toggle-masked"]`,

View File

@@ -50,8 +50,8 @@ module('Integration | Component | kv | kv-page-header', function (hooks) {
assert.dom('[data-test-breadcrumbs] li:nth-child(2) a').hasText(this.backend, 'engine name renders'); assert.dom('[data-test-breadcrumbs] li:nth-child(2) a').hasText(this.backend, 'engine name renders');
assert.dom('[data-test-breadcrumbs] li:nth-child(3) a').hasText(this.path, 'secret path renders'); assert.dom('[data-test-breadcrumbs] li:nth-child(3) a').hasText(this.path, 'secret path renders');
assert assert
.dom('[data-test-breadcrumbs] li:nth-child(4)') .dom('[data-test-breadcrumbs] li:nth-child(4) .hds-breadcrumb__current')
.hasText('/ edit', 'final breadcrumb renders and it is not a link.'); .exists('final breadcrumb renders and it is not a link.');
}); });
test('it renders a custom title for a non engine view', async function (assert) { test('it renders a custom title for a non engine view', async function (assert) {

View File

@@ -4,13 +4,10 @@
*/ */
import { Base } from '../show'; import { Base } from '../show';
import { create, clickable, collection, isPresent, text } from 'ember-cli-page-object'; import { create, clickable, collection, isPresent } from 'ember-cli-page-object';
export default create({ export default create({
...Base, ...Base,
breadcrumbs: collection('[data-test-secret-breadcrumb]', {
text: text(),
}),
deleteBtnV1: clickable('[data-test-secret-v1-delete]'), deleteBtnV1: clickable('[data-test-secret-v1-delete]'),
confirmBtn: clickable('[data-test-confirm-button]'), confirmBtn: clickable('[data-test-confirm-button]'),
rows: collection('data-test-row-label'), rows: collection('data-test-row-label'),