Commit d2fcec7d authored by Phil Hughes's avatar Phil Hughes

Merge branch 'cleanup-geo_node-nodes-css' into 'master'

Cleanup styles for Geo Node Items

See merge request gitlab-org/gitlab!21269
parents c7fc256d 079d4b89
......@@ -79,53 +79,49 @@ export default {
</script>
<template>
<div class="geo-node-actions">
<div v-if="isSecondaryNode" class="node-action-container">
<a :href="node.geoProjectsUrl" class="btn btn-sm btn-node-action" target="_blank">
<icon v-if="!node.current" name="external-link" /> {{ __('Open projects') }}
</a>
</div>
<div class="d-flex align-items-center justify-content-end geo-node-actions">
<a v-if="isSecondaryNode" :href="node.geoProjectsUrl" class="btn btn-sm mx-1 " target="_blank">
<icon v-if="!node.current" name="external-link" /> {{ __('Open projects') }}
</a>
<template v-if="nodeActionsAllowed">
<div v-if="nodeMissingOauth" class="node-action-container">
<button type="button" class="btn btn-default btn-sm btn-node-action" @click="onRepairNode">
{{ s__('Repair authentication') }}
</button>
</div>
<div v-if="isToggleAllowed" class="node-action-container">
<button
:class="{
'btn-warning': node.enabled,
'btn-success': !node.enabled,
}"
type="button"
class="btn btn-sm btn-node-action"
@click="onToggleNode"
>
<icon :name="nodeToggleIcon" />
{{ nodeToggleLabel }}
</button>
</div>
<div v-if="nodeEditAllowed" class="node-action-container">
<a :href="node.editPath" class="btn btn-sm btn-node-action"> {{ __('Edit') }} </a>
</div>
<div class="node-action-container">
<button
v-if="isSecondaryNode"
type="button"
class="btn btn-sm btn-node-action btn-danger"
@click="onRemoveSecondaryNode"
>
{{ __('Remove') }}
</button>
<button
v-else
type="button"
class="btn btn-sm btn-node-action btn-danger"
@click="onRemovePrimaryNode"
>
{{ __('Remove') }}
</button>
</div>
<button
v-if="nodeMissingOauth"
type="button"
class="btn btn-sm btn-default mx-1"
@click="onRepairNode"
>
{{ s__('Repair authentication') }}
</button>
<button
v-if="isToggleAllowed"
:class="{
'btn-warning': node.enabled,
'btn-success': !node.enabled,
}"
type="button"
class="btn btn-sm mx-1"
@click="onToggleNode"
>
<icon :name="nodeToggleIcon" />
{{ nodeToggleLabel }}
</button>
<a v-if="nodeEditAllowed" :href="node.editPath" class="btn btn-sm mx-1"> {{ __('Edit') }} </a>
<button
v-if="isSecondaryNode"
type="button"
class="btn btn-sm btn-danger mx-1"
@click="onRemoveSecondaryNode"
>
{{ __('Remove') }}
</button>
<button
v-if="!isSecondaryNode"
type="button"
class="btn btn-sm btn-danger mx-1"
@click="onRemovePrimaryNode"
>
{{ __('Remove') }}
</button>
</template>
</div>
</template>
......@@ -126,19 +126,21 @@ export default {
</script>
<template>
<div v-if="!featureDisabled" class="prepend-top-15 prepend-left-10 node-detail-item">
<div class="node-detail-title">
<span>{{ itemTitle }}</span>
<div v-if="!featureDisabled" class="mt-2 ml-2 node-detail-item">
<div class="d-flex align-items-center text-secondary-700">
<span class="node-detail-title">{{ itemTitle }}</span>
<icon
v-if="hasHelpInfo"
v-popover="popoverConfig"
:size="12"
class="node-detail-help-text prepend-left-5"
class="text-primary-600 ml-1 node-detail-help-text"
name="question"
/>
</div>
<div v-if="isValueTypePlain" :class="cssClass" class="node-detail-value">{{ itemValue }}</div>
<div v-if="isValueTypeGraph" :class="{ 'd-flex': itemValueStale }" class="node-detail-value">
<div v-if="isValueTypePlain" :class="cssClass" class="mt-1 node-detail-value">
{{ itemValue }}
</div>
<div v-if="isValueTypeGraph" :class="{ 'd-flex': itemValueStale }" class="mt-1">
<stacked-progress-bar
:css-class="itemValueStale ? 'flex-fill' : ''"
:success-label="successLabel"
......@@ -153,7 +155,7 @@ export default {
v-tooltip
:title="itemValueStaleTooltip"
name="time-out"
class="prepend-left-10 detail-value-stale-icon"
class="ml-2 text-warning-500"
data-container="body"
/>
</div>
......
......@@ -66,7 +66,7 @@ export default {
</script>
<template>
<div class="card-body">
<div class="card-body p-0">
<node-details-section-main
:node="node"
:node-details="nodeDetails"
......@@ -85,8 +85,8 @@ export default {
:node-details="nodeDetails"
:node-type-primary="node.primary"
/>
<div v-if="hasError || hasVersionMismatch" class="node-health-message-container">
<p class="node-health-message">
<div v-if="hasError || hasVersionMismatch">
<p class="p-3 mb-0 bg-danger-100 text-danger-500">
{{ errorMessage }}
<gl-link :href="geoTroubleshootingHelpPath">{{
s__('Geo|Please refer to Geo Troubleshooting.')
......
......@@ -39,7 +39,7 @@ export default {
</script>
<template>
<div class="node-detail-value">
<div class="mt-1 node-detail-value">
<template v-if="eventTimeStamp">
<strong> {{ eventString }} </strong>
<span
......
......@@ -42,11 +42,10 @@ export default {
return this.isNodeHTTP || this.nodeDetailsFailed;
},
nodeStatusIconClass() {
const iconClasses = 'prepend-left-10 node-status-icon';
if (this.nodeDetailsFailed) {
return `${iconClasses} status-icon-failure`;
}
return `${iconClasses} status-icon-warning`;
return [
'ml-2',
{ 'text-danger-500': this.nodeDetailsFailed, 'text-warning-500': !this.nodeDetailsFailed },
];
},
nodeStatusIconName() {
if (this.nodeDetailsFailed) {
......@@ -70,7 +69,7 @@ export default {
<div class="card-header">
<div class="row">
<div class="col-md-8 clearfix">
<span class="d-flex float-left append-right-10">
<span class="d-flex align-items-center float-left append-right-10">
<strong class="node-url"> {{ node.url }} </strong>
<gl-loading-icon
v-if="nodeDetailsLoading || node.nodeActionActive"
......@@ -87,11 +86,17 @@ export default {
data-placement="bottom"
/>
</span>
<span class="inline node-type-badges">
<span v-if="node.current" class="node-badge current-node">
<span class="inline">
<span
v-if="node.current"
class="rounded-pill gl-font-size-12 p-1 text-white bg-success-400"
>
{{ s__('Current node') }}
</span>
<span v-if="node.primary" class="prepend-left-5 node-badge primary-node">
<span
v-if="node.primary"
class="ml-1 rounded-pill gl-font-size-12 p-1 text-white bg-primary-600"
>
{{ s__('Primary') }}
</span>
</span>
......
<script>
import icon from '~/vue_shared/components/icon.vue';
import { HEALTH_STATUS_ICON } from '../constants';
import { HEALTH_STATUS_ICON, HEALTH_STATUS_CLASS } from '../constants';
export default {
components: {
......@@ -14,7 +14,7 @@ export default {
},
computed: {
healthCssClass() {
return `geo-node-${this.status.toLowerCase()}`;
return HEALTH_STATUS_CLASS[this.status.toLowerCase()];
},
statusIconName() {
return HEALTH_STATUS_ICON[this.status.toLowerCase()];
......@@ -24,11 +24,11 @@ export default {
</script>
<template>
<div class="prepend-top-15 detail-section-item">
<div class="node-detail-title">{{ s__('GeoNodes|Health status') }}</div>
<div :class="healthCssClass" class="node-detail-value node-health-status">
<div class="mt-2 detail-section-item">
<div class="text-secondary-700 node-detail-title">{{ s__('GeoNodes|Health status') }}</div>
<div :class="healthCssClass" class="mt-1 d-flex align-items-center node-health-status">
<icon :size="16" :name="statusIconName" />
<span class="status-text prepend-left-5"> {{ status }} </span>
<span class="status-text ml-2"> {{ status }} </span>
</div>
</div>
</template>
......@@ -78,7 +78,7 @@ export default {
</script>
<template>
<div :class="{ 'node-action-active': node.nodeActionActive }" class="card geo-node-item">
<div :class="{ 'node-action-active': node.nodeActionActive }" class="card">
<geo-node-header
:node="node"
:node-details="nodeDetails"
......@@ -93,8 +93,8 @@ export default {
:node-actions-allowed="nodeActionsAllowed"
:geo-troubleshooting-help-path="geoTroubleshootingHelpPath"
/>
<div v-if="isNodeDetailsFailed" class="node-health-message-container">
<p class="node-health-message">
<div v-if="isNodeDetailsFailed">
<p class="p-3 mb-0 bg-danger-100 text-danger-500">
{{ errorMessage
}}<gl-link :href="geoTroubleshootingHelpPath">{{
s__('Geo|Please refer to Geo Troubleshooting.')
......
......@@ -108,18 +108,18 @@ export default {
</script>
<template>
<div class="node-detail-value">
<span v-if="syncStatusUnavailable" class="node-detail-value-bold"> {{ __('Unknown') }} </span>
<div class="mt-1 node-sync-settings">
<strong v-if="syncStatusUnavailable"> {{ __('Unknown') }} </strong>
<span
v-else
v-tooltip
:title="syncStatusTooltip"
class="node-sync-settings"
class="d-flex align-items-center"
data-placement="bottom"
>
<strong>{{ syncType }}</strong>
<icon name="retry" class="sync-status-icon prepend-left-5" />
<span v-if="!eventTimestampEmpty" class="sync-status-event-info prepend-left-5">
<icon name="retry" class="ml-2" />
<span v-if="!eventTimestampEmpty" class="ml-2">
{{ syncStatusEventInfo }}
</span>
</span>
......
......@@ -46,13 +46,13 @@ export default {
</script>
<template>
<div class="row-fluid clearfix node-detail-section primary-section">
<div class="col-md-8 section-items-container">
<div class="detail-section-item node-version">
<div class="node-detail-title">{{ s__('GeoNodes|GitLab version') }}</div>
<div class="row-fluid clearfix py-3 primary-section">
<div class="col-md-8">
<div>
<div class="text-secondary-700 node-detail-title">{{ s__('GeoNodes|GitLab version') }}</div>
<div
:class="{ 'node-detail-value-error': versionMismatch }"
class="node-detail-value node-detail-value-bold"
:class="{ 'text-danger-500': versionMismatch }"
class="mt-1 font-weight-bold node-detail-value"
>
{{ nodeVersion }}
</div>
......
......@@ -54,7 +54,7 @@ export default {
itemTitle: s__('GeoNodes|Replication slot WAL'),
itemValue: numberToHumanSize(this.nodeDetails.replicationSlotWAL),
itemValueType: VALUE_TYPE.PLAIN,
cssClass: 'node-detail-value-bold',
cssClass: 'font-weight-bold',
});
}
......@@ -63,7 +63,7 @@ export default {
itemTitle: s__('GeoNodes|Internal URL'),
itemValue: this.node.internalUrl,
itemValueType: VALUE_TYPE.PLAIN,
cssClass: 'node-detail-value-bold',
cssClass: 'font-weight-bold',
});
}
......@@ -76,7 +76,7 @@ export default {
itemTitle: s__('GeoNodes|Storage config'),
itemValue: this.storageShardsStatus,
itemValueType: VALUE_TYPE.PLAIN,
cssClass: this.storageShardsCssClass,
cssClass: this.storageShardsCssClass.join(' '),
},
];
},
......@@ -89,10 +89,7 @@ export default {
: s__('GeoNodes|Does not match the primary storage configuration');
},
storageShardsCssClass() {
const cssClass = 'node-detail-value-bold';
return !this.nodeDetails.storageShardsMatch
? `${cssClass} node-detail-value-error`
: cssClass;
return ['font-weight-bold', { 'text-danger-500': !this.nodeDetails.storageShardsMatch }];
},
},
methods: {
......@@ -104,17 +101,14 @@ export default {
</script>
<template>
<div class="row-fluid clearfix node-detail-section other-section">
<div class="row-fluid clearfix py-3 border-top border-color-default other-section">
<div class="col-md-12">
<section-reveal-button
:button-title="__('Other information')"
@toggleButton="handleSectionToggle"
/>
</div>
<div
v-show="showSectionItems"
class="col-md-6 prepend-left-15 prepend-top-10 section-items-container"
>
<div v-if="showSectionItems" class="col-md-6 ml-2 mt-2 section-items-container">
<geo-node-detail-item
v-for="(nodeDetailItem, index) in nodeDetailItems"
:key="index"
......
......@@ -130,17 +130,14 @@ export default {
</script>
<template>
<div class="row-fluid clearfix node-detail-section sync-section">
<div class="row-fluid clearfix py-3 border-top border-color-default sync-section">
<div class="col-md-12">
<section-reveal-button
:button-title="__('Sync information')"
@toggleButton="handleSectionToggle"
/>
</div>
<div
v-show="showSectionItems"
class="col-md-6 prepend-left-15 prepend-top-10 section-items-container"
>
<div v-if="showSectionItems" class="col-md-6 ml-2 mt-2 section-items-container">
<geo-node-detail-item
v-for="(nodeDetailItem, index) in nodeDetailItems"
:key="index"
......
......@@ -113,7 +113,7 @@ export default {
</script>
<template>
<div class="row-fluid clearfix node-detail-section verification-section">
<div class="row-fluid clearfix py-3 border-top border-color-default verification-section">
<div class="col-md-12">
<section-reveal-button
:button-title="__('Verification information')"
......@@ -121,7 +121,7 @@ export default {
/>
</div>
<template v-if="showSectionItems">
<div class="col-md-6 prepend-left-15 prepend-top-10 section-items-container">
<div class="col-md-6 ml-2 mt-2 section-items-container">
<geo-node-detail-item
v-for="(nodeDetailItem, index) in nodeDetailItems"
:key="index"
......
......@@ -31,7 +31,7 @@ export default {
</script>
<template>
<button class="btn-link btn-show-section" type="button" @click="onClickButton">
<button class="btn-link d-flex align-items-center" type="button" @click="onClickButton">
<icon :size="16" :name="toggleButtonIcon" />
<span class="prepend-left-8">{{ buttonTitle }}</span>
</button>
......
......@@ -23,6 +23,14 @@ export const HEALTH_STATUS_ICON = {
offline: 'status_canceled',
};
export const HEALTH_STATUS_CLASS = {
healthy: 'text-success-500',
unhealthy: 'text-danger-500',
disabled: 'text-secondary-950',
unknown: 'cdark',
offline: 'cdark',
};
export const TIME_DIFF = {
FIVE_MINS: 300,
HOUR: 3600,
......
.node-badge {
color: $white-light;
padding: 1px $gl-padding-8;
font-size: $label-font-size;
border-radius: $label-border-radius;
@media (max-width: map-get($grid-breakpoints, sm)) {
.geo-node-actions {
flex-direction: column;
margin: 0 1rem;
&.primary-node {
background-color: $blue-600;
}
&.current-node {
background-color: $green-400;
}
}
.geo-node-healthy {
color: $green-500;
}
.geo-node-unhealthy {
color: $red-500;
}
.geo-node-offline {
color: $gray-950;
}
.geo-node-disabled {
color: $gray-darkest;
}
.geo-node-unknown {
color: $gray-darkest;
}
.geo-node-item {
.node-status-icon {
height: 35px;
}
.status-icon-warning {
fill: $orange-500;
}
.status-icon-failure {
fill: $red-500;
}
.card-body {
padding: 0;
.node-detail-section {
padding: $gl-padding 0;
&.sync-section,
&.verification-section,
&.other-section {
border-top: 1px solid $border-color;
}
.btn-show-section {
padding: 0;
}
}
}
.node-health-message-container {
max-height: $dropdown-max-height;
overflow-y: auto;
.node-health-message {
margin-bottom: 0;
padding: $gl-padding;
background-color: $red-100;
color: $red-500;
}
}
}
.node-detail-section {
.detail-section-item,
.section-items-container {
.node-detail-title {
color: $gray-700;
.node-detail-help-text {
color: $blue-600;
}
.tooltip .tooltip-inner {
text-align: left;
}
}
.node-detail-value {
margin-top: 4px;
}
.detail-value-stale-icon {
color: $orange-500;
}
.node-detail-value-bold {
font-weight: $gl-font-weight-bold;
}
.node-detail-value-error {
color: $red-500;
}
}
.section-items-container {
display: inline-block;
.node-detail-item {
&:first-child {
margin-top: 0;
}
}
@include media-breakpoint-down(sm) {
width: 95%;
}
}
}
.node-detail-title,
.node-health-status,
.node-sync-settings,
.node-detail-section .btn-show-section {
display: flex;
align-items: center;
}
.geo-node-actions {
display: inline-flex;
justify-content: center;
float: right;
.node-action-container {
margin: 0 5px;
&:last-child {
margin-right: $gl-padding;
}
}
@include media-breakpoint-down(sm) {
display: block;
width: 100%;
.node-action-container {
width: 100%;
margin: 0;
margin-top: 10px;
padding: 0 10px;
}
.btn-node-action {
.btn-sm {
width: 100%;
margin-top: 1rem;
}
}
}
......
......@@ -16,7 +16,7 @@ describe 'admin Geo Nodes', :js, :geo do
wait_for_requests
expect(page).to have_link('New node', href: new_admin_geo_node_path)
page.within(find('.geo-node-item', match: :first)) do
page.within(find('.card', match: :first)) do
expect(page).to have_content(geo_node.url)
end
end
......@@ -86,7 +86,7 @@ describe 'admin Geo Nodes', :js, :geo do
expect(current_path).to eq admin_geo_nodes_path
wait_for_requests
page.within(find('.geo-node-item', match: :first)) do
page.within(find('.card', match: :first)) do
expect(page).to have_content(geo_node.url)
end
end
......@@ -167,7 +167,7 @@ describe 'admin Geo Nodes', :js, :geo do
expect(current_path).to eq admin_geo_nodes_path
wait_for_requests
page.within(find('.geo-node-item', match: :first)) do
page.within(find('.card', match: :first)) do
expect(page).to have_content('http://newsite.com')
expect(page).to have_content('Primary')
......@@ -196,7 +196,7 @@ describe 'admin Geo Nodes', :js, :geo do
expect(current_path).to eq admin_geo_nodes_path
wait_for_requests
expect(page).not_to have_css('.geo-node-item')
expect(page).not_to have_css('.card')
end
end
end
......@@ -125,8 +125,7 @@ describe('GeoNodeActionsComponent', () => {
describe('template', () => {
it('renders container elements correctly', () => {
expect(vm.$el.classList.contains('geo-node-actions')).toBe(true);
expect(vm.$el.querySelectorAll('.node-action-container').length).not.toBe(0);
expect(vm.$el.querySelectorAll('.btn-node-action').length).not.toBe(0);
expect(vm.$el.querySelectorAll('.btn-sm').length).not.toBe(0);
});
});
});
......@@ -75,7 +75,7 @@ describe('GeoNodeDetailItemComponent', () => {
itemValueStaleTooltip,
});
const iconEl = vm.$el.querySelector('.detail-value-stale-icon');
const iconEl = vm.$el.querySelector('.text-warning-500');
expect(iconEl).not.toBeNull();
expect(iconEl.dataset.originalTitle).toBe(itemValueStaleTooltip);
......
......@@ -87,9 +87,7 @@ describe('GeoNodeDetailsComponent', () => {
vm.errorMessage = 'Foobar';
vm.$nextTick(() => {
expect(vm.$el.querySelector('.node-health-message-container a').getAttribute('href')).toBe(
'/foo/bar',
);
expect(vm.$el.querySelector('.bg-danger-100 a').getAttribute('href')).toBe('/foo/bar');
done();
});
});
......
import Vue from 'vue';
import geoNodeHealthStatusComponent from 'ee/geo_nodes/components/geo_node_health_status.vue';
import { HEALTH_STATUS_ICON, HEALTH_STATUS_CLASS } from 'ee/geo_nodes/constants';
import mountComponent from 'spec/helpers/vue_mount_component_helper';
import { mockNodeDetails } from '../mock_data';
......@@ -16,38 +17,38 @@ describe('GeoNodeHealthStatusComponent', () => {
describe('computed', () => {
describe('healthCssClass', () => {
it('returns CSS class representing `status` prop value', () => {
const vm = createComponent('Healthy');
const vm = createComponent('healthy');
expect(vm.healthCssClass).toBe('geo-node-healthy');
expect(vm.healthCssClass).toBe(HEALTH_STATUS_CLASS.healthy);
vm.$destroy();
});
});
describe('statusIconName', () => {
it('returns icon name representing `status` prop value', () => {
let vm = createComponent('Healthy');
let vm = createComponent('healthy');
expect(vm.statusIconName).toBe('status_success');
expect(vm.statusIconName).toBe(HEALTH_STATUS_ICON.healthy);
vm.$destroy();
vm = createComponent('Unhealthy');
vm = createComponent('unhealthy');
expect(vm.statusIconName).toBe('status_failed');
expect(vm.statusIconName).toBe(HEALTH_STATUS_ICON.unhealthy);
vm.$destroy();
vm = createComponent('Disabled');
vm = createComponent('disabled');
expect(vm.statusIconName).toBe('status_canceled');
expect(vm.statusIconName).toBe(HEALTH_STATUS_ICON.disabled);
vm.$destroy();
vm = createComponent('Unknown');
vm = createComponent('unknown');
expect(vm.statusIconName).toBe('status_warning');
expect(vm.statusIconName).toBe(HEALTH_STATUS_ICON.unknown);
vm.$destroy();
vm = createComponent('Offline');
vm = createComponent('offline');
expect(vm.statusIconName).toBe('status_canceled');
expect(vm.statusIconName).toBe(HEALTH_STATUS_ICON.offline);
vm.$destroy();
});
});
......@@ -60,7 +61,7 @@ describe('GeoNodeHealthStatusComponent', () => {
expect(vm.$el.classList.contains('detail-section-item')).toBe(true);
expect(vm.$el.querySelector('.node-detail-title').innerText.trim()).toBe('Health status');
const iconContainerEl = vm.$el.querySelector('.node-detail-value.node-health-status');
const iconContainerEl = vm.$el.querySelector('.node-health-status');
expect(iconContainerEl).not.toBeNull();
expect(iconContainerEl.querySelector('svg use').getAttribute('xlink:href')).toContain(
......
......@@ -148,11 +148,9 @@ describe('GeoNodeItemComponent', () => {
vm.isNodeDetailsFailed = true;
vm.errorMessage = err;
Vue.nextTick(() => {
expect(vm.$el.querySelectorAll('p.node-health-message').length).not.toBe(0);
expect(vm.$el.querySelector('p.node-health-message').innerText.trim()).toContain(err);
expect(vm.$el.querySelector('p.node-health-message a').getAttribute('href')).toBe(
'/foo/bar',
);
expect(vm.$el.querySelectorAll('p.bg-danger-100').length).not.toBe(0);
expect(vm.$el.querySelector('p.bg-danger-100').innerText.trim()).toContain(err);
expect(vm.$el.querySelector('p.bg-danger-100 a').getAttribute('href')).toBe('/foo/bar');
done();
});
});
......
......@@ -89,18 +89,20 @@ describe('NodeDetailsSectionOther', () => {
});
describe('storageShardsCssClass', () => {
it('returns CSS class `node-detail-value-bold` when `nodeDetails.storageShardsMatch` is true', done => {
it('returns CSS class `font-weight-bold` when `nodeDetails.storageShardsMatch` is true', done => {
vm.nodeDetails.storageShardsMatch = true;
Vue.nextTick()
.then(() => {
expect(vm.storageShardsCssClass).toBe('node-detail-value-bold');
expect(vm.storageShardsCssClass[0]).toBe('font-weight-bold');
expect(vm.storageShardsCssClass[1]['text-danger-500']).toBeFalsy();
})
.then(done)
.catch(done.fail);
});
it('returns CSS class `node-detail-value-bold node-detail-value-error` when `nodeDetails.storageShardsMatch` is false', () => {
expect(vm.storageShardsCssClass).toBe('node-detail-value-bold node-detail-value-error');
it('returns CSS class `font-weight-bold text-danger-500` when `nodeDetails.storageShardsMatch` is false', () => {
expect(vm.storageShardsCssClass[0]).toBe('font-weight-bold');
expect(vm.storageShardsCssClass[1]['text-danger-500']).toBeTruthy();
});
});
});
......@@ -111,14 +113,16 @@ describe('NodeDetailsSectionOther', () => {
});
it('renders show section button element', () => {
expect(vm.$el.querySelector('.btn-show-section')).not.toBeNull();
expect(vm.$el.querySelector('.btn-show-section > span').innerText.trim()).toBe(
'Other information',
);
expect(vm.$el.querySelector('.btn-link')).not.toBeNull();
expect(vm.$el.querySelector('.btn-link > span').innerText.trim()).toBe('Other information');
});
it('renders section items container element', () => {
expect(vm.$el.querySelector('.section-items-container')).not.toBeNull();
it('renders section items container element', done => {
vm.showSectionItems = true;
Vue.nextTick(() => {
expect(vm.$el.querySelector('.section-items-container')).not.toBeNull();
done();
});
});
});
});
......@@ -89,14 +89,16 @@ describe('NodeDetailsSectionSync', () => {
});
it('renders show section button element', () => {
expect(vm.$el.querySelector('.btn-show-section')).not.toBeNull();
expect(vm.$el.querySelector('.btn-show-section > span').innerText.trim()).toBe(
'Sync information',
);
expect(vm.$el.querySelector('.btn-link')).not.toBeNull();
expect(vm.$el.querySelector('.btn-link > span').innerText.trim()).toBe('Sync information');
});
it('renders section items container element', () => {
expect(vm.$el.querySelector('.section-items-container')).not.toBeNull();
it('renders section items container element', done => {
vm.showSectionItems = true;
Vue.nextTick(() => {
expect(vm.$el.querySelector('.section-items-container')).not.toBeNull();
done();
});
});
});
});
......@@ -83,6 +83,13 @@ describe('NodeDetailsSectionVerification', () => {
expect(vm.$el.classList.contains('verification-section')).toBe(true);
});
it('renders show section button element', () => {
expect(vm.$el.querySelector('.btn-link')).not.toBeNull();
expect(vm.$el.querySelector('.btn-link > span').innerText.trim()).toBe(
'Verification information',
);
});
it('renders section items container element', done => {
vm.showSectionItems = true;
Vue.nextTick(() => {
......
......@@ -62,7 +62,7 @@ describe('SectionRevealButton', () => {
describe('template', () => {
it('renders button element', () => {
expect(vm.$el.classList.contains('btn-show-section')).toBe(true);
expect(vm.$el.classList.contains('btn-link')).toBe(true);
expect(vm.$el.querySelector('svg use').getAttribute('xlink:href')).toContain('#angle-down');
expect(vm.$el.querySelector('span').innerText.trim()).toBe('Foo button');
});
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment