@gitlab/ui 38.0.1 → 38.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (140) hide show
  1. package/CHANGELOG.md +27 -0
  2. package/README.md +1 -1
  3. package/dist/components/base/breadcrumb/breadcrumb.js +10 -5
  4. package/dist/components/base/{filtered_search/examples/filtered_search.single_unique.example.js → breadcrumb/breadcrumb_item.js} +32 -28
  5. package/dist/components/base/dropdown/dropdown.documentation.js +1 -5
  6. package/dist/components/base/dropdown/dropdown_item.documentation.js +2 -3
  7. package/dist/components/base/filtered_search/filtered_search.documentation.js +2 -66
  8. package/dist/components/base/filtered_search/filtered_search.js +51 -20
  9. package/dist/components/base/filtered_search/filtered_search_suggestion.documentation.js +2 -8
  10. package/dist/components/base/filtered_search/filtered_search_suggestion.js +5 -1
  11. package/dist/components/base/filtered_search/filtered_search_suggestion_list.documentation.js +2 -7
  12. package/dist/components/base/filtered_search/filtered_search_suggestion_list.js +4 -0
  13. package/dist/components/base/filtered_search/filtered_search_term.documentation.js +2 -44
  14. package/dist/components/base/filtered_search/filtered_search_term.js +37 -0
  15. package/dist/components/base/filtered_search/filtered_search_token.documentation.js +2 -31
  16. package/dist/components/base/filtered_search/filtered_search_token.js +80 -23
  17. package/dist/components/base/filtered_search/filtered_search_token_segment.documentation.js +2 -46
  18. package/dist/components/base/filtered_search/filtered_search_token_segment.js +48 -0
  19. package/dist/components/base/filtered_search/filtered_search_utils.js +42 -9
  20. package/dist/components/base/form/form_checkbox_tree/form_checkbox_tree.documentation.js +2 -27
  21. package/dist/components/base/form/form_checkbox_tree/form_checkbox_tree.js +16 -1
  22. package/dist/components/charts/series_label/series_label.js +6 -1
  23. package/dist/index.css +1 -1
  24. package/dist/index.css.map +1 -1
  25. package/dist/utils/use_mock_intersection_observer.js +2 -2
  26. package/documentation/components_documentation.js +0 -4
  27. package/documentation/documented_stories.js +10 -1
  28. package/package.json +11 -9
  29. package/src/components/base/avatar_link/avatar_link.stories.js +2 -2
  30. package/src/components/base/breadcrumb/breadcrumb.spec.js +24 -10
  31. package/src/components/base/breadcrumb/breadcrumb.vue +11 -6
  32. package/src/components/base/breadcrumb/breadcrumb_item.spec.js +45 -0
  33. package/src/components/base/breadcrumb/breadcrumb_item.vue +43 -0
  34. package/src/components/base/dropdown/dropdown.documentation.js +0 -3
  35. package/src/components/base/dropdown/dropdown.md +7 -2
  36. package/src/components/base/dropdown/dropdown.stories.js +487 -439
  37. package/src/components/base/dropdown/dropdown_item.documentation.js +0 -1
  38. package/src/components/base/dropdown/dropdown_item.md +0 -6
  39. package/src/components/base/dropdown/dropdown_item.stories.js +107 -35
  40. package/src/components/base/filtered_search/filtered_search.documentation.js +0 -76
  41. package/src/components/base/filtered_search/filtered_search.md +3 -4
  42. package/src/components/base/filtered_search/filtered_search.spec.js +37 -12
  43. package/src/components/base/filtered_search/filtered_search.stories.js +260 -17
  44. package/src/components/base/filtered_search/filtered_search.vue +57 -14
  45. package/src/components/base/filtered_search/filtered_search_suggestion.documentation.js +0 -6
  46. package/src/components/base/filtered_search/filtered_search_suggestion.md +1 -7
  47. package/src/components/base/filtered_search/filtered_search_suggestion.stories.js +26 -18
  48. package/src/components/base/filtered_search/filtered_search_suggestion.vue +6 -0
  49. package/src/components/base/filtered_search/filtered_search_suggestion_list.documentation.js +0 -5
  50. package/src/components/base/filtered_search/filtered_search_suggestion_list.md +1 -7
  51. package/src/components/base/filtered_search/filtered_search_suggestion_list.stories.js +33 -25
  52. package/src/components/base/filtered_search/filtered_search_suggestion_list.vue +5 -0
  53. package/src/components/base/filtered_search/filtered_search_term.documentation.js +0 -41
  54. package/src/components/base/filtered_search/filtered_search_term.md +0 -2
  55. package/src/components/base/filtered_search/filtered_search_term.stories.js +33 -26
  56. package/src/components/base/filtered_search/filtered_search_term.vue +54 -0
  57. package/src/components/base/filtered_search/filtered_search_token.documentation.js +0 -26
  58. package/src/components/base/filtered_search/filtered_search_token.md +1 -3
  59. package/src/components/base/filtered_search/filtered_search_token.spec.js +31 -1
  60. package/src/components/base/filtered_search/filtered_search_token.stories.js +137 -132
  61. package/src/components/base/filtered_search/filtered_search_token.vue +93 -21
  62. package/src/components/base/filtered_search/filtered_search_token_segment.documentation.js +0 -43
  63. package/src/components/base/filtered_search/filtered_search_token_segment.md +0 -2
  64. package/src/components/base/filtered_search/filtered_search_token_segment.stories.js +86 -79
  65. package/src/components/base/filtered_search/filtered_search_token_segment.vue +42 -0
  66. package/src/components/base/filtered_search/filtered_search_utils.js +38 -5
  67. package/src/components/base/form/form.stories.js +2 -0
  68. package/src/components/base/form/form_checkbox_tree/form_checkbox_tree.documentation.js +0 -26
  69. package/src/components/base/form/form_checkbox_tree/form_checkbox_tree.md +0 -4
  70. package/src/components/base/form/form_checkbox_tree/form_checkbox_tree.stories.js +123 -92
  71. package/src/components/base/form/form_checkbox_tree/form_checkbox_tree.vue +13 -1
  72. package/src/components/base/form/form_radio/form_radio.spec.js +21 -8
  73. package/src/components/base/form/form_radio_group/form_radio_group.stories.js +2 -1
  74. package/src/components/base/markdown/markdown.scss +21 -0
  75. package/src/components/base/markdown/markdown_typescale_demo.html +17 -6
  76. package/src/components/base/navbar/navbar.stories.js +2 -1
  77. package/src/components/base/skeleton_loader/skeleton_loader.stories.js +67 -21
  78. package/src/components/base/tabs/tabs/tabs.stories.js +2 -2
  79. package/src/components/charts/series_label/series_label.stories.js +6 -3
  80. package/src/components/charts/series_label/series_label.vue +3 -0
  81. package/src/scss/typescale/typescale.md +0 -2
  82. package/src/scss/typescale/typescale.stories.js +17 -4
  83. package/src/utils/use_mock_intersection_observer.js +3 -3
  84. package/dist/components/base/dropdown/dropdown_divider.documentation.js +0 -8
  85. package/dist/components/base/dropdown/dropdown_form.documentation.js +0 -17
  86. package/dist/components/base/dropdown/dropdown_section_header.documentation.js +0 -8
  87. package/dist/components/base/dropdown/dropdown_text.documentation.js +0 -8
  88. package/dist/components/base/dropdown/examples/dropdown.default.example.js +0 -38
  89. package/dist/components/base/dropdown/examples/dropdown.links.example.js +0 -38
  90. package/dist/components/base/dropdown/examples/dropdown.with_avatar_and_secondary_text.example.js +0 -38
  91. package/dist/components/base/dropdown/examples/dropdown.with_checked_items.example.js +0 -38
  92. package/dist/components/base/dropdown/examples/dropdown.with_clear_all.example.js +0 -38
  93. package/dist/components/base/dropdown/examples/dropdown.with_divider.example.js +0 -38
  94. package/dist/components/base/dropdown/examples/dropdown.with_form.example.js +0 -38
  95. package/dist/components/base/dropdown/examples/dropdown.with_header.example.js +0 -38
  96. package/dist/components/base/dropdown/examples/dropdown.with_highlighted_items.example.js +0 -38
  97. package/dist/components/base/dropdown/examples/dropdown.with_icons.example.js +0 -38
  98. package/dist/components/base/dropdown/examples/dropdown.with_right_align.example.js +0 -38
  99. package/dist/components/base/dropdown/examples/dropdown.with_search.example.js +0 -67
  100. package/dist/components/base/dropdown/examples/dropdown.with_section_headers.example.js +0 -38
  101. package/dist/components/base/dropdown/examples/index.js +0 -85
  102. package/dist/components/base/filtered_search/examples/filtered_search.default.example.js +0 -422
  103. package/dist/components/base/filtered_search/examples/filtered_search.friendly.example.js +0 -423
  104. package/dist/components/base/filtered_search/examples/filtered_search.history.example.js +0 -91
  105. package/dist/components/base/filtered_search/examples/filtered_search.multi_select.example.js +0 -196
  106. package/dist/components/base/filtered_search/examples/index.js +0 -32
  107. package/dist/components/base/form/form_checkbox_tree/examples/form_checkbox_tree.basic.example.js +0 -103
  108. package/dist/components/base/form/form_checkbox_tree/examples/index.js +0 -13
  109. package/src/components/base/dropdown/dropdown_divider.documentation.js +0 -6
  110. package/src/components/base/dropdown/dropdown_divider.md +0 -7
  111. package/src/components/base/dropdown/dropdown_divider.stories.js +0 -16
  112. package/src/components/base/dropdown/dropdown_form.documentation.js +0 -9
  113. package/src/components/base/dropdown/dropdown_form.md +0 -4
  114. package/src/components/base/dropdown/dropdown_form.stories.js +0 -17
  115. package/src/components/base/dropdown/dropdown_section_header.documentation.js +0 -6
  116. package/src/components/base/dropdown/dropdown_section_header.stories.js +0 -17
  117. package/src/components/base/dropdown/dropdown_text.documentation.js +0 -6
  118. package/src/components/base/dropdown/dropdown_text.stories.js +0 -16
  119. package/src/components/base/dropdown/examples/dropdown.default.example.vue +0 -7
  120. package/src/components/base/dropdown/examples/dropdown.links.example.vue +0 -7
  121. package/src/components/base/dropdown/examples/dropdown.with_avatar_and_secondary_text.example.vue +0 -7
  122. package/src/components/base/dropdown/examples/dropdown.with_checked_items.example.vue +0 -6
  123. package/src/components/base/dropdown/examples/dropdown.with_clear_all.example.vue +0 -7
  124. package/src/components/base/dropdown/examples/dropdown.with_divider.example.vue +0 -9
  125. package/src/components/base/dropdown/examples/dropdown.with_form.example.vue +0 -10
  126. package/src/components/base/dropdown/examples/dropdown.with_header.example.vue +0 -7
  127. package/src/components/base/dropdown/examples/dropdown.with_highlighted_items.example.vue +0 -9
  128. package/src/components/base/dropdown/examples/dropdown.with_icons.example.vue +0 -43
  129. package/src/components/base/dropdown/examples/dropdown.with_right_align.example.vue +0 -7
  130. package/src/components/base/dropdown/examples/dropdown.with_search.example.vue +0 -38
  131. package/src/components/base/dropdown/examples/dropdown.with_section_headers.example.vue +0 -10
  132. package/src/components/base/dropdown/examples/index.js +0 -99
  133. package/src/components/base/filtered_search/examples/filtered_search.default.example.vue +0 -298
  134. package/src/components/base/filtered_search/examples/filtered_search.friendly.example.vue +0 -300
  135. package/src/components/base/filtered_search/examples/filtered_search.history.example.vue +0 -50
  136. package/src/components/base/filtered_search/examples/filtered_search.multi_select.example.vue +0 -132
  137. package/src/components/base/filtered_search/examples/filtered_search.single_unique.example.vue +0 -31
  138. package/src/components/base/filtered_search/examples/index.js +0 -38
  139. package/src/components/base/form/form_checkbox_tree/examples/form_checkbox_tree.basic.example.vue +0 -77
  140. package/src/components/base/form/form_checkbox_tree/examples/index.js +0 -15
@@ -25,7 +25,7 @@ class MockObserver {
25
25
  this.$_observers = [];
26
26
  }
27
27
 
28
- takeRecords() {} // eslint-disable-next-line babel/camelcase
28
+ takeRecords() {} // eslint-disable-next-line camelcase
29
29
 
30
30
 
31
31
  $_triggerObserve(nodeParam) {
@@ -42,7 +42,7 @@ class MockObserver {
42
42
  }]);
43
43
  }
44
44
  });
45
- } // eslint-disable-next-line babel/camelcase
45
+ } // eslint-disable-next-line camelcase
46
46
 
47
47
 
48
48
  $_hasObserver(node) {
@@ -2,7 +2,6 @@
2
2
  // ADD EXPORTS - needed for yarn generate:component. Do not remove
3
3
  export { default as GlTableLiteDocumentation } from '../src/components/base/table_lite/table_lite.documentation';
4
4
  export { default as GlRichTextEditorDocumentation } from '../src/components/editors/rich_text_editor/rich_text_editor.documentation';
5
- export { default as GlDropdownFormDocumentation } from '../src/components/base/dropdown/dropdown_form.documentation';
6
5
  export { default as GlKeysetPaginationDocumentation } from '../src/components/base/keyset_pagination/keyset_pagination.documentation';
7
6
  export { default as GlInputGroupTextDocumentation } from '../src/components/base/form/input_group_text/input_group_text.documentation';
8
7
  export { default as GlFormTextDocumentation } from '../src/components/base/form/form_text/form_text.documentation';
@@ -56,9 +55,6 @@ export { default as GlSearchBoxByTypeDocumentation } from '../src/components/bas
56
55
  export { default as GlSearchBoxByClickDocumentation } from '../src/components/base/search_box_by_click/search_box_by_click.documentation';
57
56
  export { default as GlDropdownDocumentation } from '../src/components/base/dropdown/dropdown.documentation';
58
57
  export { default as GlDropdownItemDocumentation } from '../src/components/base/dropdown/dropdown_item.documentation';
59
- export { default as GlDropdownDividerDocumentation } from '../src/components/base/dropdown/dropdown_divider.documentation';
60
- export { default as GlDropdownSectionHeaderDocumentation } from '../src/components/base/dropdown/dropdown_section_header.documentation';
61
- export { default as GlDropdownTextDocumentation } from '../src/components/base/dropdown/dropdown_text.documentation';
62
58
  export { default as GlTableDocumentation } from '../src/components/base/table/table.documentation';
63
59
  export { default as GlBreadcrumbDocumentation } from '../src/components/base/breadcrumb/breadcrumb.documentation';
64
60
  export { default as GlHeatmapDocumentation } from '../src/components/charts/heatmap/heatmap.documentation';
@@ -64,6 +64,8 @@ export const setupStorybookReadme = () =>
64
64
  'GlSprintf',
65
65
  'GlLink',
66
66
  'GlChart',
67
+ 'GlDropdown',
68
+ 'GlDropdownItem',
67
69
  'GlBadge',
68
70
  'GlButtonGroup',
69
71
  'GlOutsideDirective',
@@ -82,6 +84,7 @@ export const setupStorybookReadme = () =>
82
84
  'GlDashboardSkeleton',
83
85
  'GlToggle',
84
86
  'GlNavbar',
87
+ 'GlFormCheckboxTree',
85
88
  'GlProgressBar',
86
89
  'GlPath',
87
90
  'GlFriendlyWrap',
@@ -91,6 +94,12 @@ export const setupStorybookReadme = () =>
91
94
  'GlFormCheckbox',
92
95
  'GlAccordion',
93
96
  'GlAccordionItem',
97
+ 'GlFilteredSearch',
98
+ 'GlFilteredSearchSuggestion',
99
+ 'GlFilteredSearchSuggestionList',
100
+ 'GlFilteredSearchTerm',
101
+ 'GlFilteredSearchToken',
102
+ 'GlFilteredSearchTokenSegment',
94
103
  'GlIntersperse',
95
104
  'GlFormSelect',
96
105
  'GlDaterangePicker',
@@ -178,7 +187,7 @@ export const setupStorybookReadme = () =>
178
187
  },
179
188
  template: `
180
189
  <div>
181
- <div class="story-container" v-if="$options.disableForComponents.includes(componentName)">
190
+ <div class="story-container" v-if="!componentName || $options.disableForComponents.includes(componentName)">
182
191
  <slot></slot>
183
192
  </div>
184
193
  <template v-else>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gitlab/ui",
3
- "version": "38.0.1",
3
+ "version": "38.2.1",
4
4
  "description": "GitLab UI Components",
5
5
  "license": "MIT",
6
6
  "main": "dist/index.js",
@@ -37,9 +37,10 @@
37
37
  "test:unit": "NODE_ENV=test jest --testPathIgnorePatterns storyshots.spec.js",
38
38
  "test:unit:watch": "yarn test:unit --watch --notify",
39
39
  "test:unit:debug": "NODE_ENV=test node --inspect node_modules/.bin/jest --testPathIgnorePatterns storyshot.spec.js --watch --runInBand",
40
- "test:visual": "NODE_ENV=test IS_VISUAL_TEST=true start-test http-get://localhost:9001 'jest ./tests/storyshots.spec.js'",
40
+ "test:visual": "./bin/run-visual-tests.sh 'jest ./tests/storyshots.spec.js'",
41
41
  "test:visual:minimal": "node ./bin/run_minimal_visual_tests.js",
42
- "test:visual:update": "NODE_ENV=test IS_VISUAL_TEST=true JEST_IMAGE_SNAPSHOT_TRACK_OBSOLETE=1 start-test http-get://localhost:9001 'jest ./tests/storyshots.spec.js --updateSnapshot'",
42
+ "test:visual:update": "./bin/run-visual-tests.sh 'JEST_IMAGE_SNAPSHOT_TRACK_OBSOLETE=1 jest ./tests/storyshots.spec.js --updateSnapshot'",
43
+ "test:visual:internal": "NODE_ENV=test IS_VISUAL_TEST=true start-test http-get://localhost:9001",
43
44
  "prettier": "prettier --check '**/*.{js,vue}'",
44
45
  "prettier:fix": "prettier --write '**/*.{js,vue}'",
45
46
  "eslint": "eslint --max-warnings 0 --ext .js,.vue .",
@@ -77,13 +78,15 @@
77
78
  },
78
79
  "resolutions": {
79
80
  "chokidar": "^3.5.2",
81
+ "node-gyp": "^9.0.0",
82
+ "node-sass": "^6.0.0",
80
83
  "sane": "^5.0.1"
81
84
  },
82
85
  "devDependencies": {
83
- "@arkweid/lefthook": "^0.7.6",
86
+ "@arkweid/lefthook": "0.7.7",
84
87
  "@babel/core": "^7.10.2",
85
88
  "@babel/preset-env": "^7.10.2",
86
- "@gitlab/eslint-plugin": "11.0.0",
89
+ "@gitlab/eslint-plugin": "12.0.1",
87
90
  "@gitlab/stylelint-config": "4.0.0",
88
91
  "@gitlab/svgs": "2.6.0",
89
92
  "@rollup/plugin-commonjs": "^11.1.0",
@@ -118,11 +121,9 @@
118
121
  "jest": "^26.6.3",
119
122
  "jest-raw-loader": "^1.0.1",
120
123
  "jest-serializer-vue": "^2.0.2",
121
- "markdown-loader-jest": "^0.1.1",
122
124
  "markdownlint-cli": "^0.29.0",
123
125
  "mockdate": "^2.0.5",
124
- "node-sass": "^4.14.1",
125
- "node-sass-magic-importer": "^5.3.2",
126
+ "node-sass": "^6.0.0",
126
127
  "npm-run-all": "^4.1.5",
127
128
  "pikaday": "^1.8.0",
128
129
  "plop": "^2.5.4",
@@ -139,8 +140,9 @@
139
140
  "rollup-plugin-string": "^3.0.0",
140
141
  "rollup-plugin-svg": "^2.0.0",
141
142
  "rollup-plugin-vue": "^5.1.6",
143
+ "sass": "^1.49.9",
142
144
  "sass-export": "^1.0.3",
143
- "sass-loader": "^7.1.0",
145
+ "sass-loader": "^10.2.0",
144
146
  "sass-true": "^5.0.0",
145
147
  "start-server-and-test": "^1.10.6",
146
148
  "storybook-readme": "5.0.9",
@@ -2,7 +2,7 @@ import { GlAvatarLink, GlAvatar, GlAvatarLabeled } from '../../../index';
2
2
  import { avatarSizeOptions, avatarShapeOptions } from '../../../utils/constants';
3
3
  import readme from './avatar_link.md';
4
4
 
5
- const components = { GlAvatarLink, GlAvatar };
5
+ const components = { GlAvatarLink, GlAvatar, GlAvatarLabeled };
6
6
 
7
7
  const generateDefaultProps = ({
8
8
  href = 'https://gitlab.com/gitlab-org/gitlab',
@@ -37,7 +37,7 @@ export const Default = (args, { argTypes }) => ({
37
37
  Default.args = { ...generateDefaultProps(), ...generateImageProps() };
38
38
 
39
39
  export const WithLabeledAvatar = (args, { argTypes }) => ({
40
- components: { GlAvatarLink, GlAvatarLabeled },
40
+ components,
41
41
  props: Object.keys(argTypes),
42
42
  template: `
43
43
  <gl-avatar-link target="blank" :href="href">
@@ -1,9 +1,10 @@
1
1
  import { shallowMount } from '@vue/test-utils';
2
- import { BBreadcrumbItem } from 'bootstrap-vue';
2
+ import { nextTick } from 'vue';
3
3
  import Breadcrumb, { COLLAPSE_AT_SIZE } from './breadcrumb.vue';
4
+ import GlBreadcrumbItem from './breadcrumb_item.vue';
4
5
  import { createMockDirective } from '~helpers/vue_mock_directive';
5
6
 
6
- describe('Broadcast message component', () => {
7
+ describe('Breadcrumb component', () => {
7
8
  let wrapper;
8
9
 
9
10
  const items = [
@@ -25,7 +26,7 @@ describe('Broadcast message component', () => {
25
26
 
26
27
  const findAvatarSlot = () => wrapper.find('[data-testid="avatar-slot"]');
27
28
  const findSeparatorSlot = () => wrapper.find('[data-testid="separator-slot"]');
28
- const findBreadcrumbItems = () => wrapper.findAllComponents(BBreadcrumbItem);
29
+ const findBreadcrumbItems = () => wrapper.findAllComponents(GlBreadcrumbItem);
29
30
  const findAllSeparators = () => wrapper.findAll('[data-testid="separator"]');
30
31
  const findCollapsedListExpander = () => wrapper.find('[data-testid="collapsed-expander"]');
31
32
  const findExpanderSeparator = () => wrapper.find('[data-testid="expander-separator"]');
@@ -42,6 +43,9 @@ describe('Broadcast message component', () => {
42
43
  separator: '<div data-testid="separator-slot"></div>',
43
44
  },
44
45
  directives: { GlTooltip: createMockDirective('gl-tooltip') },
46
+ stubs: {
47
+ GlBreadcrumbItem,
48
+ },
45
49
  });
46
50
 
47
51
  wrapper.vm.$refs.firstItem = [
@@ -86,21 +90,31 @@ describe('Broadcast message component', () => {
86
90
  });
87
91
 
88
92
  describe('bindings', () => {
89
- it('first breadcrumb has text and href bound', () => {
93
+ beforeEach(() => {
90
94
  createComponent();
95
+ });
91
96
 
92
- expect(findBreadcrumbItems().at(0).attributes()).toMatchObject({
97
+ it('first breadcrumb has text, href && ariaCurrent=`false` bound', () => {
98
+ expect(findBreadcrumbItems().at(0).props()).toMatchObject({
93
99
  text: items[0].text,
94
100
  href: items[0].href,
101
+ ariaCurrent: false,
95
102
  });
96
103
  });
97
104
 
98
- it('second breadcrumb has text and to bound', () => {
99
- createComponent();
100
-
101
- expect(findBreadcrumbItems().at(1).attributes()).toMatchObject({
105
+ it('second breadcrumb has text, to && ariaCurrent=`false` bound', () => {
106
+ expect(findBreadcrumbItems().at(1).props()).toMatchObject({
102
107
  text: items[1].text,
103
108
  to: items[1].to,
109
+ ariaCurrent: false,
110
+ });
111
+ });
112
+
113
+ it('last breadcrumb has text, to && ariaCurrent=`page` bound', () => {
114
+ expect(findBreadcrumbItems().at(2).props()).toMatchObject({
115
+ text: items[2].text,
116
+ href: items[2].href,
117
+ ariaCurrent: 'page',
104
118
  });
105
119
  });
106
120
  });
@@ -139,7 +153,7 @@ describe('Broadcast message component', () => {
139
153
 
140
154
  it('should expand the list on expander click', async () => {
141
155
  findCollapsedListExpander().vm.$emit('click');
142
- await wrapper.vm.$nextTick();
156
+ await nextTick();
143
157
  expect(findHiddenBreadcrumbItems()).toHaveLength(0);
144
158
  expect(findVisibleBreadcrumbItems()).toHaveLength(items.length + extraItems.length);
145
159
  });
@@ -1,17 +1,18 @@
1
1
  <script>
2
- import { BBreadcrumb, BBreadcrumbItem } from 'bootstrap-vue';
2
+ import { BBreadcrumb } from 'bootstrap-vue';
3
3
  import GlIcon from '../icon/icon.vue';
4
4
  import GlButton from '../button/button.vue';
5
5
  import { GlTooltipDirective } from '../../../directives/tooltip';
6
+ import GlBreadcrumbItem from './breadcrumb_item.vue';
6
7
 
7
8
  export const COLLAPSE_AT_SIZE = 4;
8
9
 
9
10
  export default {
10
11
  components: {
11
12
  BBreadcrumb,
12
- BBreadcrumbItem,
13
13
  GlIcon,
14
14
  GlButton,
15
+ GlBreadcrumbItem,
15
16
  },
16
17
  directives: {
17
18
  GlTooltip: GlTooltipDirective,
@@ -58,11 +59,12 @@ export default {
58
59
  },
59
60
  expandBreadcrumbs() {
60
61
  this.isListCollapsed = false;
62
+
61
63
  try {
62
64
  this.$refs.firstItem[0].querySelector('a').focus();
63
65
  } catch (e) {
64
66
  /* eslint-disable-next-line no-console */
65
- console.error(`Failed to set focus on the last breadcrumb item.`);
67
+ console.error(`Failed to set focus on the first breadcrumb item.`);
66
68
  }
67
69
  },
68
70
  showCollapsedBreadcrumbsExpander(index) {
@@ -73,6 +75,9 @@ export default {
73
75
  this.hasCollapsible && this.isListCollapsed && !this.nonCollapsibleIndices.includes(index)
74
76
  );
75
77
  },
78
+ getAriaCurrentAttr(index) {
79
+ return this.isLastItem(index) ? 'page' : false;
80
+ },
76
81
  },
77
82
  };
78
83
  </script>
@@ -82,14 +87,14 @@ export default {
82
87
  <slot name="avatar"></slot>
83
88
  <b-breadcrumb class="gl-breadcrumb-list" v-bind="$attrs" v-on="$listeners">
84
89
  <template v-for="(item, index) in items">
85
- <b-breadcrumb-item
90
+ <gl-breadcrumb-item
86
91
  :key="index"
87
92
  :ref="isFirstItem(index) ? 'firstItem' : null"
88
- class="gl-breadcrumb-item"
89
93
  :text="item.text"
90
94
  :href="item.href"
91
95
  :to="item.to"
92
96
  :class="{ 'gl-display-none': isItemCollapsed(index) }"
97
+ :aria-current="getAriaCurrentAttr(index)"
93
98
  >
94
99
  <span>{{ item.text }}</span>
95
100
  <span
@@ -103,7 +108,7 @@ export default {
103
108
  <gl-icon name="chevron-right" />
104
109
  </slot>
105
110
  </span>
106
- </b-breadcrumb-item>
111
+ </gl-breadcrumb-item>
107
112
 
108
113
  <template v-if="showCollapsedBreadcrumbsExpander(index)">
109
114
  <!-- eslint-disable-next-line vue/valid-v-for -->
@@ -0,0 +1,45 @@
1
+ import { shallowMount } from '@vue/test-utils';
2
+ import { BLink } from 'bootstrap-vue';
3
+ import BreadcrumbItem from './breadcrumb_item.vue';
4
+
5
+ describe('Breadcrumb Item Component', () => {
6
+ let wrapper;
7
+
8
+ const item = { href: 'http://about.gitlab.com', to: { name: 'about' }, ariaCurrent: 'page' };
9
+
10
+ const findBLink = () => wrapper.findComponent(BLink);
11
+ const findDefaultSlot = () => wrapper.find('[data-testid="default-slot"]');
12
+
13
+ const createComponent = () => {
14
+ wrapper = shallowMount(BreadcrumbItem, {
15
+ propsData: {
16
+ href: item.href,
17
+ to: item.to,
18
+ ariaCurrent: item.ariaCurrent,
19
+ },
20
+ slots: {
21
+ default: '<div data-testid="default-slot"></div>',
22
+ },
23
+ });
24
+ };
25
+
26
+ describe('slots', () => {
27
+ it('renders provided content to default slot', () => {
28
+ createComponent();
29
+
30
+ expect(findDefaultSlot().exists()).toBe(true);
31
+ });
32
+ });
33
+
34
+ describe('bindings', () => {
35
+ it('passes provided props down to BLink', () => {
36
+ createComponent();
37
+
38
+ const bLink = findBLink();
39
+
40
+ expect(bLink.props('to')).toMatchObject(item.to);
41
+ expect(bLink.props('href')).toBe(item.href);
42
+ expect(bLink.attributes('aria-current')).toBe(item.ariaCurrent);
43
+ });
44
+ });
45
+ });
@@ -0,0 +1,43 @@
1
+ <script>
2
+ import { BLink } from 'bootstrap-vue';
3
+
4
+ export default {
5
+ components: {
6
+ BLink,
7
+ },
8
+ inheritAttrs: false,
9
+ props: {
10
+ text: {
11
+ type: String,
12
+ required: false,
13
+ default: null,
14
+ },
15
+ to: {
16
+ type: [String, Object],
17
+ required: false,
18
+ default: null,
19
+ },
20
+ href: {
21
+ type: String,
22
+ required: false,
23
+ default: null,
24
+ },
25
+ ariaCurrent: {
26
+ type: [String, Boolean],
27
+ required: false,
28
+ default: false,
29
+ validator(value) {
30
+ return [false, 'page'].indexOf(value) !== -1;
31
+ },
32
+ },
33
+ },
34
+ };
35
+ </script>
36
+
37
+ <template>
38
+ <li class="gl-breadcrumb-item">
39
+ <b-link :href="href" :to="to" :aria-current="ariaCurrent">
40
+ <slot>{{ text }}</slot>
41
+ </b-link>
42
+ </li>
43
+ </template>
@@ -1,9 +1,6 @@
1
1
  import description from './dropdown.md';
2
- import examples from './examples';
3
2
 
4
3
  export default {
5
4
  description,
6
- bootstrapComponent: 'b-dropdown',
7
- examples,
8
5
  followsDesignSystem: false,
9
6
  };
@@ -1,5 +1,3 @@
1
- ## Usage
2
-
3
1
  The dropdown component offers a user multiple items or actions to choose from which are initially
4
2
  collapsed behind a button.
5
3
 
@@ -55,3 +53,10 @@ loading spinner, icon, and dropdown caret:
55
53
  </template>
56
54
  </gl-dropdown>
57
55
  ```
56
+
57
+ ### GlDropdownForm
58
+
59
+ Unlike `b-dropdown-form`, we do _not_ add any additional padding with the `gl-dropdown-form` component.
60
+ This is to prevent double padding with `gl-dropdown-item` and similar components, so in most cases
61
+ shouldn't be needed. To add padding, either add a padding utility class to your form, or an inner
62
+ element with some padding.