@atlaskit/link-datasource 1.15.4 → 1.16.0

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 (28) hide show
  1. package/CHANGELOG.md +6 -0
  2. package/dist/cjs/analytics/constants.js +1 -1
  3. package/dist/cjs/ui/jira-issues-modal/basic-filters/hooks/useFilterOptions.js +14 -14
  4. package/dist/cjs/ui/jira-issues-modal/basic-filters/ui/async-popup-select/index.js +18 -3
  5. package/dist/cjs/ui/jira-issues-modal/basic-filters/ui/async-popup-select/messages.js +5 -0
  6. package/dist/cjs/ui/jira-issues-modal/basic-filters/ui/async-popup-select/showMoreButton.js +22 -0
  7. package/dist/cjs/ui/jira-issues-modal/basic-filters/ui/menu-list/index.js +21 -4
  8. package/dist/es2019/analytics/constants.js +1 -1
  9. package/dist/es2019/ui/jira-issues-modal/basic-filters/hooks/useFilterOptions.js +2 -2
  10. package/dist/es2019/ui/jira-issues-modal/basic-filters/ui/async-popup-select/index.js +18 -3
  11. package/dist/es2019/ui/jira-issues-modal/basic-filters/ui/async-popup-select/messages.js +5 -0
  12. package/dist/es2019/ui/jira-issues-modal/basic-filters/ui/async-popup-select/showMoreButton.js +17 -0
  13. package/dist/es2019/ui/jira-issues-modal/basic-filters/ui/menu-list/index.js +18 -3
  14. package/dist/esm/analytics/constants.js +1 -1
  15. package/dist/esm/ui/jira-issues-modal/basic-filters/hooks/useFilterOptions.js +14 -14
  16. package/dist/esm/ui/jira-issues-modal/basic-filters/ui/async-popup-select/index.js +18 -3
  17. package/dist/esm/ui/jira-issues-modal/basic-filters/ui/async-popup-select/messages.js +5 -0
  18. package/dist/esm/ui/jira-issues-modal/basic-filters/ui/async-popup-select/showMoreButton.js +15 -0
  19. package/dist/esm/ui/jira-issues-modal/basic-filters/ui/menu-list/index.js +21 -4
  20. package/dist/types/ui/jira-issues-modal/basic-filters/hooks/useFilterOptions.d.ts +1 -1
  21. package/dist/types/ui/jira-issues-modal/basic-filters/ui/async-popup-select/messages.d.ts +5 -0
  22. package/dist/types/ui/jira-issues-modal/basic-filters/ui/async-popup-select/showMoreButton.d.ts +6 -0
  23. package/dist/types/ui/jira-issues-modal/basic-filters/ui/menu-list/index.d.ts +4 -1
  24. package/dist/types-ts4.5/ui/jira-issues-modal/basic-filters/hooks/useFilterOptions.d.ts +1 -1
  25. package/dist/types-ts4.5/ui/jira-issues-modal/basic-filters/ui/async-popup-select/messages.d.ts +5 -0
  26. package/dist/types-ts4.5/ui/jira-issues-modal/basic-filters/ui/async-popup-select/showMoreButton.d.ts +6 -0
  27. package/dist/types-ts4.5/ui/jira-issues-modal/basic-filters/ui/menu-list/index.d.ts +4 -1
  28. package/package.json +1 -1
package/CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # @atlaskit/link-datasource
2
2
 
3
+ ## 1.16.0
4
+
5
+ ### Minor Changes
6
+
7
+ - [#42962](https://bitbucket.org/atlassian/atlassian-frontend/pull-requests/42962) [`00b9a417c51`](https://bitbucket.org/atlassian/atlassian-frontend/commits/00b9a417c51) - Adds show more button to UI and functionality to fetch more data for datasource basic filters
8
+
3
9
  ## 1.15.4
4
10
 
5
11
  ### Patch Changes
@@ -7,5 +7,5 @@ exports.packageMetaData = exports.EVENT_CHANNEL = void 0;
7
7
  var EVENT_CHANNEL = exports.EVENT_CHANNEL = 'media';
8
8
  var packageMetaData = exports.packageMetaData = {
9
9
  packageName: "@atlaskit/link-datasource",
10
- packageVersion: "1.15.4"
10
+ packageVersion: "1.16.0"
11
11
  };
@@ -38,28 +38,29 @@ var useFilterOptions = exports.useFilterOptions = function useFilterOptions(_ref
38
38
  var _ref3,
39
39
  pageCursor,
40
40
  searchString,
41
+ isNewSearch,
41
42
  isRequestLikeInitialSearch,
42
43
  initialResponseData,
43
44
  response,
44
- isNewSearch,
45
45
  _args = arguments;
46
46
  return _regenerator.default.wrap(function _callee$(_context) {
47
47
  while (1) switch (_context.prev = _context.next) {
48
48
  case 0:
49
49
  _ref3 = _args.length > 0 && _args[0] !== undefined ? _args[0] : {}, pageCursor = _ref3.pageCursor, searchString = _ref3.searchString;
50
- setStatus('loading');
50
+ isNewSearch = !pageCursor;
51
+ isNewSearch ? setStatus('loading') : setStatus('loadingMore');
51
52
  isRequestLikeInitialSearch = !pageCursor && !searchString;
52
53
  initialResponseData = initialData.current;
53
- _context.prev = 4;
54
+ _context.prev = 5;
54
55
  if (!(isRequestLikeInitialSearch && initialResponseData)) {
55
- _context.next = 9;
56
+ _context.next = 10;
56
57
  break;
57
58
  }
58
59
  _context.t0 = initialResponseData;
59
- _context.next = 12;
60
+ _context.next = 13;
60
61
  break;
61
- case 9:
62
- _context.next = 11;
62
+ case 10:
63
+ _context.next = 12;
63
64
  return getFieldValues({
64
65
  cloudId: cloudId,
65
66
  jql: '',
@@ -67,18 +68,17 @@ var useFilterOptions = exports.useFilterOptions = function useFilterOptions(_ref
67
68
  searchString: searchString,
68
69
  pageCursor: pageCursor
69
70
  });
70
- case 11:
71
- _context.t0 = _context.sent;
72
71
  case 12:
72
+ _context.t0 = _context.sent;
73
+ case 13:
73
74
  response = _context.t0;
74
75
  if (!(response.errors && response.errors.length > 0)) {
75
- _context.next = 16;
76
+ _context.next = 17;
76
77
  break;
77
78
  }
78
79
  setStatus('rejected');
79
80
  return _context.abrupt("return");
80
- case 16:
81
- isNewSearch = !pageCursor;
81
+ case 17:
82
82
  if (isNewSearch) {
83
83
  setFilterOptions((0, _transformers.mapFieldValuesToFilterOptions)(response));
84
84
  if (isRequestLikeInitialSearch) {
@@ -98,13 +98,13 @@ var useFilterOptions = exports.useFilterOptions = function useFilterOptions(_ref
98
98
  break;
99
99
  case 23:
100
100
  _context.prev = 23;
101
- _context.t1 = _context["catch"](4);
101
+ _context.t1 = _context["catch"](5);
102
102
  setStatus('rejected');
103
103
  case 26:
104
104
  case "end":
105
105
  return _context.stop();
106
106
  }
107
- }, _callee, null, [[4, 23]]);
107
+ }, _callee, null, [[5, 23]]);
108
108
  })), [cloudId, filterOptions, filterType, getFieldValues]);
109
109
  return {
110
110
  filterOptions: filterOptions,
@@ -57,7 +57,8 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
57
57
  filterOptions = _useFilterOptions.filterOptions,
58
58
  fetchFilterOptions = _useFilterOptions.fetchFilterOptions,
59
59
  totalCount = _useFilterOptions.totalCount,
60
- status = _useFilterOptions.status;
60
+ status = _useFilterOptions.status,
61
+ pageCursor = _useFilterOptions.pageCursor;
61
62
  var _useDebouncedCallback = (0, _useDebounce.useDebouncedCallback)(function (searchString) {
62
63
  fetchFilterOptions({
63
64
  searchString: searchString
@@ -96,6 +97,14 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
96
97
  });
97
98
  }
98
99
  }, [fetchFilterOptions, searchTerm, status]);
100
+ var handleShowMore = (0, _react.useCallback)(function () {
101
+ if (pageCursor) {
102
+ fetchFilterOptions({
103
+ pageCursor: pageCursor,
104
+ searchString: searchTerm
105
+ });
106
+ }
107
+ }, [fetchFilterOptions, pageCursor, searchTerm]);
99
108
  (0, _react.useEffect)(function () {
100
109
  if (status === 'resolved') {
101
110
  var _pickerRef$current;
@@ -106,8 +115,11 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
106
115
  var filterOptionsLength = filterOptions.length;
107
116
  var isError = status === 'rejected';
108
117
  var isLoading = status === 'loading' || status === 'empty';
118
+ var isLoadingMore = status === 'loadingMore';
109
119
  var isEmpty = status === 'resolved' && filterOptionsLength === 0;
110
- var shouldShowFooter = status === 'resolved' && filterOptionsLength > 0;
120
+ var areAllResultsLoaded = filterOptions.length === totalCount;
121
+ var shouldShowFooter = (status === 'resolved' || isLoadingMore) && filterOptions.length > 0; // footer should not disappear when there is an inline spinner for loading more data
122
+ var shouldDisplayShowMoreButton = status === 'resolved' && !!pageCursor && !areAllResultsLoaded;
111
123
  var options = isLoading || isError ? [] : filterOptions; // if not set to [], for eg: on loading, no loading UI will be shown
112
124
 
113
125
  return /*#__PURE__*/_react.default.createElement(_select.PopupSelect, {
@@ -136,7 +148,10 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
136
148
  return /*#__PURE__*/_react.default.createElement(_menuList.default, (0, _extends2.default)({}, props, {
137
149
  isError: isError,
138
150
  isEmpty: isEmpty,
139
- isLoading: isLoading
151
+ isLoading: isLoading,
152
+ isLoadingMore: isLoadingMore,
153
+ showMore: shouldDisplayShowMoreButton,
154
+ handleShowMore: handleShowMore
140
155
  }));
141
156
  },
142
157
  DropdownIndicator: _dropdownIndicator.default,
@@ -34,5 +34,10 @@ var asyncPopupSelectMessages = exports.asyncPopupSelectMessages = {
34
34
  id: 'linkDataSource.basic-filter.assignee.label',
35
35
  description: 'Label to be displayed for assignee filter dropdown button.',
36
36
  defaultMessage: 'Assignee'
37
+ },
38
+ showMoreMessage: {
39
+ id: 'linkDataSource.basic-filter.showMoreButton',
40
+ defaultMessage: 'Show more',
41
+ description: 'The text to show more options in dropdown'
37
42
  }
38
43
  };
@@ -0,0 +1,22 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
4
+ Object.defineProperty(exports, "__esModule", {
5
+ value: true
6
+ });
7
+ exports.default = void 0;
8
+ var _react = _interopRequireDefault(require("react"));
9
+ var _reactIntlNext = require("react-intl-next");
10
+ var _button = _interopRequireDefault(require("@atlaskit/button"));
11
+ var _messages = require("./messages");
12
+ var ShowMoreButton = function ShowMoreButton(_ref) {
13
+ var onShowMore = _ref.onShowMore;
14
+ var _useIntl = (0, _reactIntlNext.useIntl)(),
15
+ formatMessage = _useIntl.formatMessage;
16
+ return /*#__PURE__*/_react.default.createElement(_button.default, {
17
+ onClick: onShowMore,
18
+ appearance: "link",
19
+ testId: "jlol-basic-filter-popup-select--show-more-button"
20
+ }, formatMessage(_messages.asyncPopupSelectMessages.showMoreMessage));
21
+ };
22
+ var _default = exports.default = ShowMoreButton;
@@ -7,18 +7,33 @@ Object.defineProperty(exports, "__esModule", {
7
7
  exports.default = void 0;
8
8
  var _objectWithoutProperties2 = _interopRequireDefault(require("@babel/runtime/helpers/objectWithoutProperties"));
9
9
  var _react = _interopRequireDefault(require("react"));
10
+ var _primitives = require("@atlaskit/primitives");
10
11
  var _select = require("@atlaskit/select");
12
+ var _spinner = _interopRequireDefault(require("@atlaskit/spinner"));
13
+ var _showMoreButton = _interopRequireDefault(require("../async-popup-select/showMoreButton"));
11
14
  var _errorMessage = _interopRequireDefault(require("./errorMessage"));
12
15
  var _loadingMessage = _interopRequireDefault(require("./loadingMessage"));
13
16
  var _noOptionsMessage = _interopRequireDefault(require("./noOptionsMessage"));
14
- var _excluded = ["isLoading", "isError", "isEmpty", "children"];
17
+ var _excluded = ["isLoading", "isLoadingMore", "isError", "isEmpty", "showMore", "handleShowMore", "children"];
15
18
  var CustomMenuList = function CustomMenuList(_ref) {
16
19
  var isLoading = _ref.isLoading,
20
+ isLoadingMore = _ref.isLoadingMore,
17
21
  isError = _ref.isError,
18
22
  isEmpty = _ref.isEmpty,
23
+ showMore = _ref.showMore,
24
+ handleShowMore = _ref.handleShowMore,
19
25
  children = _ref.children,
20
26
  props = (0, _objectWithoutProperties2.default)(_ref, _excluded);
21
- var getChildComponent = function getChildComponent() {
27
+ var shouldDisplayShowMore = showMore && !isLoadingMore;
28
+ var isLoadingMoreData = !shouldDisplayShowMore && isLoadingMore;
29
+ var InlineSpinner = function InlineSpinner() {
30
+ return /*#__PURE__*/_react.default.createElement(_primitives.Flex, {
31
+ justifyContent: "center"
32
+ }, /*#__PURE__*/_react.default.createElement(_spinner.default, {
33
+ size: "medium"
34
+ }));
35
+ };
36
+ var renderChildren = function renderChildren() {
22
37
  if (isLoading) {
23
38
  return /*#__PURE__*/_react.default.createElement(_loadingMessage.default, null);
24
39
  }
@@ -28,8 +43,10 @@ var CustomMenuList = function CustomMenuList(_ref) {
28
43
  if (isEmpty) {
29
44
  return /*#__PURE__*/_react.default.createElement(_noOptionsMessage.default, null);
30
45
  }
31
- return children;
46
+ return /*#__PURE__*/_react.default.createElement(_react.default.Fragment, null, children, shouldDisplayShowMore && /*#__PURE__*/_react.default.createElement(_showMoreButton.default, {
47
+ onShowMore: handleShowMore
48
+ }), isLoadingMoreData && /*#__PURE__*/_react.default.createElement(InlineSpinner, null));
32
49
  };
33
- return /*#__PURE__*/_react.default.createElement(_select.components.MenuList, props, getChildComponent());
50
+ return /*#__PURE__*/_react.default.createElement(_select.components.MenuList, props, renderChildren());
34
51
  };
35
52
  var _default = exports.default = CustomMenuList;
@@ -1,5 +1,5 @@
1
1
  export const EVENT_CHANNEL = 'media';
2
2
  export const packageMetaData = {
3
3
  packageName: "@atlaskit/link-datasource",
4
- packageVersion: "1.15.4"
4
+ packageVersion: "1.16.0"
5
5
  };
@@ -17,7 +17,8 @@ export const useFilterOptions = ({
17
17
  pageCursor,
18
18
  searchString
19
19
  } = {}) => {
20
- setStatus('loading');
20
+ const isNewSearch = !pageCursor;
21
+ isNewSearch ? setStatus('loading') : setStatus('loadingMore');
21
22
  const isRequestLikeInitialSearch = !pageCursor && !searchString;
22
23
  const {
23
24
  current: initialResponseData
@@ -34,7 +35,6 @@ export const useFilterOptions = ({
34
35
  setStatus('rejected');
35
36
  return;
36
37
  }
37
- const isNewSearch = !pageCursor;
38
38
  if (isNewSearch) {
39
39
  setFilterOptions(mapFieldValuesToFilterOptions(response));
40
40
  if (isRequestLikeInitialSearch) {
@@ -31,7 +31,8 @@ const AsyncPopupSelect = ({
31
31
  filterOptions,
32
32
  fetchFilterOptions,
33
33
  totalCount,
34
- status
34
+ status,
35
+ pageCursor
35
36
  } = useFilterOptions({
36
37
  filterType,
37
38
  cloudId
@@ -59,6 +60,14 @@ const AsyncPopupSelect = ({
59
60
  });
60
61
  }
61
62
  }, [fetchFilterOptions, searchTerm, status]);
63
+ const handleShowMore = useCallback(() => {
64
+ if (pageCursor) {
65
+ fetchFilterOptions({
66
+ pageCursor,
67
+ searchString: searchTerm
68
+ });
69
+ }
70
+ }, [fetchFilterOptions, pageCursor, searchTerm]);
62
71
  useEffect(() => {
63
72
  if (status === 'resolved') {
64
73
  var _pickerRef$current, _pickerRef$current$se, _pickerRef$current$se2;
@@ -69,8 +78,11 @@ const AsyncPopupSelect = ({
69
78
  const filterOptionsLength = filterOptions.length;
70
79
  const isError = status === 'rejected';
71
80
  const isLoading = status === 'loading' || status === 'empty';
81
+ const isLoadingMore = status === 'loadingMore';
72
82
  const isEmpty = status === 'resolved' && filterOptionsLength === 0;
73
- const shouldShowFooter = status === 'resolved' && filterOptionsLength > 0;
83
+ const areAllResultsLoaded = filterOptions.length === totalCount;
84
+ const shouldShowFooter = (status === 'resolved' || isLoadingMore) && filterOptions.length > 0; // footer should not disappear when there is an inline spinner for loading more data
85
+ const shouldDisplayShowMoreButton = status === 'resolved' && !!pageCursor && !areAllResultsLoaded;
74
86
  const options = isLoading || isError ? [] : filterOptions; // if not set to [], for eg: on loading, no loading UI will be shown
75
87
 
76
88
  return /*#__PURE__*/React.createElement(PopupSelect, {
@@ -98,7 +110,10 @@ const AsyncPopupSelect = ({
98
110
  MenuList: props => /*#__PURE__*/React.createElement(CustomMenuList, _extends({}, props, {
99
111
  isError: isError,
100
112
  isEmpty: isEmpty,
101
- isLoading: isLoading
113
+ isLoading: isLoading,
114
+ isLoadingMore: isLoadingMore,
115
+ showMore: shouldDisplayShowMoreButton,
116
+ handleShowMore: handleShowMore
102
117
  })),
103
118
  DropdownIndicator: CustomDropdownIndicator,
104
119
  LoadingIndicator: undefined,
@@ -28,5 +28,10 @@ export const asyncPopupSelectMessages = {
28
28
  id: 'linkDataSource.basic-filter.assignee.label',
29
29
  description: 'Label to be displayed for assignee filter dropdown button.',
30
30
  defaultMessage: 'Assignee'
31
+ },
32
+ showMoreMessage: {
33
+ id: 'linkDataSource.basic-filter.showMoreButton',
34
+ defaultMessage: 'Show more',
35
+ description: 'The text to show more options in dropdown'
31
36
  }
32
37
  };
@@ -0,0 +1,17 @@
1
+ import React from 'react';
2
+ import { useIntl } from 'react-intl-next';
3
+ import Button from '@atlaskit/button';
4
+ import { asyncPopupSelectMessages } from './messages';
5
+ const ShowMoreButton = ({
6
+ onShowMore
7
+ }) => {
8
+ const {
9
+ formatMessage
10
+ } = useIntl();
11
+ return /*#__PURE__*/React.createElement(Button, {
12
+ onClick: onShowMore,
13
+ appearance: "link",
14
+ testId: "jlol-basic-filter-popup-select--show-more-button"
15
+ }, formatMessage(asyncPopupSelectMessages.showMoreMessage));
16
+ };
17
+ export default ShowMoreButton;
@@ -1,16 +1,29 @@
1
1
  import React from 'react';
2
+ import { Flex } from '@atlaskit/primitives';
2
3
  import { components } from '@atlaskit/select';
4
+ import Spinner from '@atlaskit/spinner';
5
+ import ShowMoreButton from '../async-popup-select/showMoreButton';
3
6
  import CustomErrorMessage from './errorMessage';
4
7
  import CustomDropdownLoadingMessage from './loadingMessage';
5
8
  import CustomNoOptionsMessage from './noOptionsMessage';
6
9
  const CustomMenuList = ({
7
10
  isLoading,
11
+ isLoadingMore,
8
12
  isError,
9
13
  isEmpty,
14
+ showMore,
15
+ handleShowMore,
10
16
  children,
11
17
  ...props
12
18
  }) => {
13
- const getChildComponent = () => {
19
+ const shouldDisplayShowMore = showMore && !isLoadingMore;
20
+ const isLoadingMoreData = !shouldDisplayShowMore && isLoadingMore;
21
+ const InlineSpinner = () => /*#__PURE__*/React.createElement(Flex, {
22
+ justifyContent: "center"
23
+ }, /*#__PURE__*/React.createElement(Spinner, {
24
+ size: "medium"
25
+ }));
26
+ const renderChildren = () => {
14
27
  if (isLoading) {
15
28
  return /*#__PURE__*/React.createElement(CustomDropdownLoadingMessage, null);
16
29
  }
@@ -20,8 +33,10 @@ const CustomMenuList = ({
20
33
  if (isEmpty) {
21
34
  return /*#__PURE__*/React.createElement(CustomNoOptionsMessage, null);
22
35
  }
23
- return children;
36
+ return /*#__PURE__*/React.createElement(React.Fragment, null, children, shouldDisplayShowMore && /*#__PURE__*/React.createElement(ShowMoreButton, {
37
+ onShowMore: handleShowMore
38
+ }), isLoadingMoreData && /*#__PURE__*/React.createElement(InlineSpinner, null));
24
39
  };
25
- return /*#__PURE__*/React.createElement(components.MenuList, props, getChildComponent());
40
+ return /*#__PURE__*/React.createElement(components.MenuList, props, renderChildren());
26
41
  };
27
42
  export default CustomMenuList;
@@ -1,5 +1,5 @@
1
1
  export var EVENT_CHANNEL = 'media';
2
2
  export var packageMetaData = {
3
3
  packageName: "@atlaskit/link-datasource",
4
- packageVersion: "1.15.4"
4
+ packageVersion: "1.16.0"
5
5
  };
@@ -31,28 +31,29 @@ export var useFilterOptions = function useFilterOptions(_ref) {
31
31
  var _ref3,
32
32
  pageCursor,
33
33
  searchString,
34
+ isNewSearch,
34
35
  isRequestLikeInitialSearch,
35
36
  initialResponseData,
36
37
  response,
37
- isNewSearch,
38
38
  _args = arguments;
39
39
  return _regeneratorRuntime.wrap(function _callee$(_context) {
40
40
  while (1) switch (_context.prev = _context.next) {
41
41
  case 0:
42
42
  _ref3 = _args.length > 0 && _args[0] !== undefined ? _args[0] : {}, pageCursor = _ref3.pageCursor, searchString = _ref3.searchString;
43
- setStatus('loading');
43
+ isNewSearch = !pageCursor;
44
+ isNewSearch ? setStatus('loading') : setStatus('loadingMore');
44
45
  isRequestLikeInitialSearch = !pageCursor && !searchString;
45
46
  initialResponseData = initialData.current;
46
- _context.prev = 4;
47
+ _context.prev = 5;
47
48
  if (!(isRequestLikeInitialSearch && initialResponseData)) {
48
- _context.next = 9;
49
+ _context.next = 10;
49
50
  break;
50
51
  }
51
52
  _context.t0 = initialResponseData;
52
- _context.next = 12;
53
+ _context.next = 13;
53
54
  break;
54
- case 9:
55
- _context.next = 11;
55
+ case 10:
56
+ _context.next = 12;
56
57
  return getFieldValues({
57
58
  cloudId: cloudId,
58
59
  jql: '',
@@ -60,18 +61,17 @@ export var useFilterOptions = function useFilterOptions(_ref) {
60
61
  searchString: searchString,
61
62
  pageCursor: pageCursor
62
63
  });
63
- case 11:
64
- _context.t0 = _context.sent;
65
64
  case 12:
65
+ _context.t0 = _context.sent;
66
+ case 13:
66
67
  response = _context.t0;
67
68
  if (!(response.errors && response.errors.length > 0)) {
68
- _context.next = 16;
69
+ _context.next = 17;
69
70
  break;
70
71
  }
71
72
  setStatus('rejected');
72
73
  return _context.abrupt("return");
73
- case 16:
74
- isNewSearch = !pageCursor;
74
+ case 17:
75
75
  if (isNewSearch) {
76
76
  setFilterOptions(mapFieldValuesToFilterOptions(response));
77
77
  if (isRequestLikeInitialSearch) {
@@ -91,13 +91,13 @@ export var useFilterOptions = function useFilterOptions(_ref) {
91
91
  break;
92
92
  case 23:
93
93
  _context.prev = 23;
94
- _context.t1 = _context["catch"](4);
94
+ _context.t1 = _context["catch"](5);
95
95
  setStatus('rejected');
96
96
  case 26:
97
97
  case "end":
98
98
  return _context.stop();
99
99
  }
100
- }, _callee, null, [[4, 23]]);
100
+ }, _callee, null, [[5, 23]]);
101
101
  })), [cloudId, filterOptions, filterType, getFieldValues]);
102
102
  return {
103
103
  filterOptions: filterOptions,
@@ -47,7 +47,8 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
47
47
  filterOptions = _useFilterOptions.filterOptions,
48
48
  fetchFilterOptions = _useFilterOptions.fetchFilterOptions,
49
49
  totalCount = _useFilterOptions.totalCount,
50
- status = _useFilterOptions.status;
50
+ status = _useFilterOptions.status,
51
+ pageCursor = _useFilterOptions.pageCursor;
51
52
  var _useDebouncedCallback = useDebouncedCallback(function (searchString) {
52
53
  fetchFilterOptions({
53
54
  searchString: searchString
@@ -86,6 +87,14 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
86
87
  });
87
88
  }
88
89
  }, [fetchFilterOptions, searchTerm, status]);
90
+ var handleShowMore = useCallback(function () {
91
+ if (pageCursor) {
92
+ fetchFilterOptions({
93
+ pageCursor: pageCursor,
94
+ searchString: searchTerm
95
+ });
96
+ }
97
+ }, [fetchFilterOptions, pageCursor, searchTerm]);
89
98
  useEffect(function () {
90
99
  if (status === 'resolved') {
91
100
  var _pickerRef$current;
@@ -96,8 +105,11 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
96
105
  var filterOptionsLength = filterOptions.length;
97
106
  var isError = status === 'rejected';
98
107
  var isLoading = status === 'loading' || status === 'empty';
108
+ var isLoadingMore = status === 'loadingMore';
99
109
  var isEmpty = status === 'resolved' && filterOptionsLength === 0;
100
- var shouldShowFooter = status === 'resolved' && filterOptionsLength > 0;
110
+ var areAllResultsLoaded = filterOptions.length === totalCount;
111
+ var shouldShowFooter = (status === 'resolved' || isLoadingMore) && filterOptions.length > 0; // footer should not disappear when there is an inline spinner for loading more data
112
+ var shouldDisplayShowMoreButton = status === 'resolved' && !!pageCursor && !areAllResultsLoaded;
101
113
  var options = isLoading || isError ? [] : filterOptions; // if not set to [], for eg: on loading, no loading UI will be shown
102
114
 
103
115
  return /*#__PURE__*/React.createElement(PopupSelect, {
@@ -126,7 +138,10 @@ var AsyncPopupSelect = function AsyncPopupSelect(_ref) {
126
138
  return /*#__PURE__*/React.createElement(CustomMenuList, _extends({}, props, {
127
139
  isError: isError,
128
140
  isEmpty: isEmpty,
129
- isLoading: isLoading
141
+ isLoading: isLoading,
142
+ isLoadingMore: isLoadingMore,
143
+ showMore: shouldDisplayShowMoreButton,
144
+ handleShowMore: handleShowMore
130
145
  }));
131
146
  },
132
147
  DropdownIndicator: CustomDropdownIndicator,
@@ -28,5 +28,10 @@ export var asyncPopupSelectMessages = {
28
28
  id: 'linkDataSource.basic-filter.assignee.label',
29
29
  description: 'Label to be displayed for assignee filter dropdown button.',
30
30
  defaultMessage: 'Assignee'
31
+ },
32
+ showMoreMessage: {
33
+ id: 'linkDataSource.basic-filter.showMoreButton',
34
+ defaultMessage: 'Show more',
35
+ description: 'The text to show more options in dropdown'
31
36
  }
32
37
  };
@@ -0,0 +1,15 @@
1
+ import React from 'react';
2
+ import { useIntl } from 'react-intl-next';
3
+ import Button from '@atlaskit/button';
4
+ import { asyncPopupSelectMessages } from './messages';
5
+ var ShowMoreButton = function ShowMoreButton(_ref) {
6
+ var onShowMore = _ref.onShowMore;
7
+ var _useIntl = useIntl(),
8
+ formatMessage = _useIntl.formatMessage;
9
+ return /*#__PURE__*/React.createElement(Button, {
10
+ onClick: onShowMore,
11
+ appearance: "link",
12
+ testId: "jlol-basic-filter-popup-select--show-more-button"
13
+ }, formatMessage(asyncPopupSelectMessages.showMoreMessage));
14
+ };
15
+ export default ShowMoreButton;
@@ -1,17 +1,32 @@
1
1
  import _objectWithoutProperties from "@babel/runtime/helpers/objectWithoutProperties";
2
- var _excluded = ["isLoading", "isError", "isEmpty", "children"];
2
+ var _excluded = ["isLoading", "isLoadingMore", "isError", "isEmpty", "showMore", "handleShowMore", "children"];
3
3
  import React from 'react';
4
+ import { Flex } from '@atlaskit/primitives';
4
5
  import { components } from '@atlaskit/select';
6
+ import Spinner from '@atlaskit/spinner';
7
+ import ShowMoreButton from '../async-popup-select/showMoreButton';
5
8
  import CustomErrorMessage from './errorMessage';
6
9
  import CustomDropdownLoadingMessage from './loadingMessage';
7
10
  import CustomNoOptionsMessage from './noOptionsMessage';
8
11
  var CustomMenuList = function CustomMenuList(_ref) {
9
12
  var isLoading = _ref.isLoading,
13
+ isLoadingMore = _ref.isLoadingMore,
10
14
  isError = _ref.isError,
11
15
  isEmpty = _ref.isEmpty,
16
+ showMore = _ref.showMore,
17
+ handleShowMore = _ref.handleShowMore,
12
18
  children = _ref.children,
13
19
  props = _objectWithoutProperties(_ref, _excluded);
14
- var getChildComponent = function getChildComponent() {
20
+ var shouldDisplayShowMore = showMore && !isLoadingMore;
21
+ var isLoadingMoreData = !shouldDisplayShowMore && isLoadingMore;
22
+ var InlineSpinner = function InlineSpinner() {
23
+ return /*#__PURE__*/React.createElement(Flex, {
24
+ justifyContent: "center"
25
+ }, /*#__PURE__*/React.createElement(Spinner, {
26
+ size: "medium"
27
+ }));
28
+ };
29
+ var renderChildren = function renderChildren() {
15
30
  if (isLoading) {
16
31
  return /*#__PURE__*/React.createElement(CustomDropdownLoadingMessage, null);
17
32
  }
@@ -21,8 +36,10 @@ var CustomMenuList = function CustomMenuList(_ref) {
21
36
  if (isEmpty) {
22
37
  return /*#__PURE__*/React.createElement(CustomNoOptionsMessage, null);
23
38
  }
24
- return children;
39
+ return /*#__PURE__*/React.createElement(React.Fragment, null, children, shouldDisplayShowMore && /*#__PURE__*/React.createElement(ShowMoreButton, {
40
+ onShowMore: handleShowMore
41
+ }), isLoadingMoreData && /*#__PURE__*/React.createElement(InlineSpinner, null));
25
42
  };
26
- return /*#__PURE__*/React.createElement(components.MenuList, props, getChildComponent());
43
+ return /*#__PURE__*/React.createElement(components.MenuList, props, renderChildren());
27
44
  };
28
45
  export default CustomMenuList;
@@ -12,7 +12,7 @@ export interface FilterOptionsState {
12
12
  fetchFilterOptions: (prop?: FetchFilterOptionsProps) => Promise<void>;
13
13
  totalCount: number;
14
14
  pageCursor?: string;
15
- status: 'empty' | 'loading' | 'resolved' | 'rejected';
15
+ status: 'empty' | 'loading' | 'resolved' | 'rejected' | 'loadingMore';
16
16
  }
17
17
  export declare const useFilterOptions: ({ filterType, cloudId, }: FilterOptionsProps) => FilterOptionsState;
18
18
  export {};
@@ -29,4 +29,9 @@ export declare const asyncPopupSelectMessages: {
29
29
  description: string;
30
30
  defaultMessage: string;
31
31
  };
32
+ showMoreMessage: {
33
+ id: string;
34
+ defaultMessage: string;
35
+ description: string;
36
+ };
32
37
  };
@@ -0,0 +1,6 @@
1
+ /// <reference types="react" />
2
+ type ShowMoreButtonProps = {
3
+ onShowMore: () => void;
4
+ };
5
+ declare const ShowMoreButton: ({ onShowMore }: ShowMoreButtonProps) => JSX.Element;
6
+ export default ShowMoreButton;
@@ -4,7 +4,10 @@ import { SelectOption } from '../../types';
4
4
  type CustomProps = {
5
5
  isError?: boolean;
6
6
  isLoading?: boolean;
7
+ isLoadingMore?: boolean;
7
8
  isEmpty?: boolean;
9
+ showMore?: boolean;
10
+ handleShowMore: () => void;
8
11
  };
9
- declare const CustomMenuList: ({ isLoading, isError, isEmpty, children, ...props }: MenuListComponentProps<SelectOption, true> & CustomProps) => JSX.Element;
12
+ declare const CustomMenuList: ({ isLoading, isLoadingMore, isError, isEmpty, showMore, handleShowMore, children, ...props }: MenuListComponentProps<SelectOption, true> & CustomProps) => JSX.Element;
10
13
  export default CustomMenuList;
@@ -12,7 +12,7 @@ export interface FilterOptionsState {
12
12
  fetchFilterOptions: (prop?: FetchFilterOptionsProps) => Promise<void>;
13
13
  totalCount: number;
14
14
  pageCursor?: string;
15
- status: 'empty' | 'loading' | 'resolved' | 'rejected';
15
+ status: 'empty' | 'loading' | 'resolved' | 'rejected' | 'loadingMore';
16
16
  }
17
17
  export declare const useFilterOptions: ({ filterType, cloudId, }: FilterOptionsProps) => FilterOptionsState;
18
18
  export {};
@@ -29,4 +29,9 @@ export declare const asyncPopupSelectMessages: {
29
29
  description: string;
30
30
  defaultMessage: string;
31
31
  };
32
+ showMoreMessage: {
33
+ id: string;
34
+ defaultMessage: string;
35
+ description: string;
36
+ };
32
37
  };
@@ -0,0 +1,6 @@
1
+ /// <reference types="react" />
2
+ type ShowMoreButtonProps = {
3
+ onShowMore: () => void;
4
+ };
5
+ declare const ShowMoreButton: ({ onShowMore }: ShowMoreButtonProps) => JSX.Element;
6
+ export default ShowMoreButton;
@@ -4,7 +4,10 @@ import { SelectOption } from '../../types';
4
4
  type CustomProps = {
5
5
  isError?: boolean;
6
6
  isLoading?: boolean;
7
+ isLoadingMore?: boolean;
7
8
  isEmpty?: boolean;
9
+ showMore?: boolean;
10
+ handleShowMore: () => void;
8
11
  };
9
- declare const CustomMenuList: ({ isLoading, isError, isEmpty, children, ...props }: MenuListComponentProps<SelectOption, true> & CustomProps) => JSX.Element;
12
+ declare const CustomMenuList: ({ isLoading, isLoadingMore, isError, isEmpty, showMore, handleShowMore, children, ...props }: MenuListComponentProps<SelectOption, true> & CustomProps) => JSX.Element;
10
13
  export default CustomMenuList;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@atlaskit/link-datasource",
3
- "version": "1.15.4",
3
+ "version": "1.16.0",
4
4
  "description": "UI Components to support linking platform dataset feature",
5
5
  "publishConfig": {
6
6
  "registry": "https://registry.npmjs.org/"