Commit ab996b3e authored by Andrew Fontaine's avatar Andrew Fontaine

Merge branch 'refactor-sidebar-reference-widget' into 'master'

Use copyable_field component in sidebar_reference_widget.vue

See merge request gitlab-org/gitlab!56826
parents 3c7fea32 85d79a4f
<script>
import { GlLoadingIcon } from '@gitlab/ui';
import { __ } from '~/locale';
import { referenceQueries } from '~/sidebar/constants';
import ClipboardButton from '~/vue_shared/components/clipboard_button.vue';
import CopyableField from '~/vue_shared/components/sidebar/copyable_field.vue';
export default {
i18n: {
copyReference: __('Copy reference'),
text: __('Reference'),
},
components: {
ClipboardButton,
GlLoadingIcon,
CopyableField,
},
inject: ['fullPath', 'iid'],
props: {
......@@ -56,31 +50,10 @@ export default {
</script>
<template>
<div class="sub-block">
<clipboard-button
v-if="!isLoading"
:title="$options.i18n.copyReference"
:text="reference"
category="tertiary"
css-class="sidebar-collapsed-icon dont-change-state"
tooltip-placement="left"
/>
<div
class="gl-display-flex gl-align-items-center gl-justify-content-space-between gl-mb-2 hide-collapsed"
>
<span class="gl-overflow-hidden gl-text-overflow-ellipsis gl-white-space-nowrap">
{{ $options.i18n.text }}: {{ reference }}
<gl-loading-icon v-if="isLoading" inline :label="$options.i18n.text" />
</span>
<clipboard-button
v-if="!isLoading"
:title="$options.i18n.copyReference"
:text="reference"
size="small"
category="tertiary"
css-class="gl-mr-1"
tooltip-placement="left"
/>
</div>
</div>
<copyable-field
class="sub-block"
:is-loading="isLoading"
:name="__('Reference')"
:value="reference"
/>
</template>
......@@ -67,7 +67,7 @@ export default {
<div>
<clipboard-button
v-if="!isLoading"
css-class="sidebar-collapsed-icon dont-change-state"
css-class="sidebar-collapsed-icon dont-change-state gl-rounded-0! gl-hover-bg-transparent"
v-bind="clipboardProps"
/>
......
import { GlLoadingIcon } from '@gitlab/ui';
import { shallowMount } from '@vue/test-utils';
import Vue from 'vue';
import VueApollo from 'vue-apollo';
......@@ -8,18 +7,21 @@ import { IssuableType } from '~/issue_show/constants';
import SidebarReferenceWidget from '~/sidebar/components/reference/sidebar_reference_widget.vue';
import issueReferenceQuery from '~/sidebar/queries/issue_reference.query.graphql';
import mergeRequestReferenceQuery from '~/sidebar/queries/merge_request_reference.query.graphql';
import ClipboardButton from '~/vue_shared/components/clipboard_button.vue';
import CopyableField from '~/vue_shared/components/sidebar/copyable_field.vue';
import { issueReferenceResponse } from '../../mock_data';
describe('Sidebar Reference Widget', () => {
let wrapper;
let fakeApollo;
const referenceText = 'reference';
const mockReferenceValue = 'reference-1234';
const findCopyableField = () => wrapper.findComponent(CopyableField);
const createComponent = ({
issuableType,
issuableType = IssuableType.Issue,
referenceQuery = issueReferenceQuery,
referenceQueryHandler = jest.fn().mockResolvedValue(issueReferenceResponse(referenceText)),
referenceQueryHandler = jest.fn().mockResolvedValue(issueReferenceResponse(mockReferenceValue)),
} = {}) => {
Vue.use(VueApollo);
......@@ -39,14 +41,20 @@ describe('Sidebar Reference Widget', () => {
afterEach(() => {
wrapper.destroy();
wrapper = null;
});
describe('when reference is loading', () => {
it('sets CopyableField `is-loading` prop to `true`', () => {
createComponent({ referenceQueryHandler: jest.fn().mockReturnValue(new Promise(() => {})) });
expect(findCopyableField().props('isLoading')).toBe(true);
});
});
describe.each([
[IssuableType.Issue, issueReferenceQuery],
[IssuableType.MergeRequest, mergeRequestReferenceQuery],
])('when issuableType is %s', (issuableType, referenceQuery) => {
it('displays the reference text', async () => {
it('sets CopyableField `value` prop to reference value', async () => {
createComponent({
issuableType,
referenceQuery,
......@@ -54,40 +62,32 @@ describe('Sidebar Reference Widget', () => {
await waitForPromises();
expect(wrapper.text()).toContain(referenceText);
expect(findCopyableField().props('value')).toBe(mockReferenceValue);
});
it('displays loading icon while fetching and hides clipboard icon', async () => {
createComponent({
issuableType,
referenceQuery,
});
describe('when error occurs', () => {
it('calls createFlash with correct parameters', async () => {
const mockError = new Error('mayday');
expect(wrapper.find(GlLoadingIcon).exists()).toBe(true);
expect(wrapper.find(ClipboardButton).exists()).toBe(false);
});
createComponent({
issuableType,
referenceQuery,
referenceQueryHandler: jest.fn().mockRejectedValue(mockError),
});
it('calls createFlash with correct parameters', async () => {
const mockError = new Error('mayday');
await waitForPromises();
createComponent({
issuableType,
referenceQuery,
referenceQueryHandler: jest.fn().mockRejectedValue(mockError),
const [
[
{
message,
error: { networkError },
},
],
] = wrapper.emitted('fetch-error');
expect(message).toBe('An error occurred while fetching reference');
expect(networkError).toEqual(mockError);
});
await waitForPromises();
const [
[
{
message,
error: { networkError },
},
],
] = wrapper.emitted('fetch-error');
expect(message).toBe('An error occurred while fetching reference');
expect(networkError).toEqual(mockError);
});
});
});
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