@collectionspace/cspace-public-browser 3.3.0 → 3.4.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.
@@ -16,7 +16,7 @@ var _DetailNavBar = _interopRequireDefault(require("../../../styles/cspace/Detai
16
16
  var _Link = _interopRequireDefault(require("../../../styles/cspace/Link.css"));
17
17
  function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
18
18
  const propTypes = {
19
- params: _propTypes.default.instanceOf(_immutable.default.Map).isRequired,
19
+ params: _propTypes.default.instanceOf(_immutable.default.Map),
20
20
  prev: _propTypes.default.shape({
21
21
  'ecm:name': _propTypes.default.string
22
22
  }),
@@ -25,6 +25,7 @@ const propTypes = {
25
25
  })
26
26
  };
27
27
  const defaultProps = {
28
+ params: _immutable.default.Map(),
28
29
  prev: undefined,
29
30
  next: undefined
30
31
  };
@@ -42,48 +43,36 @@ const messages = (0, _reactIntl.defineMessages)({
42
43
  "defaultMessage": "Next"
43
44
  }
44
45
  });
45
- function DetailNavBar(props) {
46
- const {
47
- params,
48
- prev,
49
- next
50
- } = props;
51
- const index = params.get('index');
52
- const searchParams = params.get('searchParams');
53
- if (!searchParams || typeof index === 'undefined') {
54
- return null;
55
- }
56
- const searchParamsObj = searchParams.toJS();
57
- const detailPath = _config.default.get('detailPath');
58
- let prevLink;
59
- let nextLink;
60
- if (prev) {
61
- const csid = (0, _get.default)(prev, 'ecm:name');
62
- prevLink = /*#__PURE__*/_react.default.createElement("span", null, /*#__PURE__*/_react.default.createElement(_reactRouterDom.Link, {
63
- className: _Link.default.prev,
46
+ function DetailNavBar({
47
+ params,
48
+ prev,
49
+ next
50
+ }) {
51
+ function renderLink(searchParams, index, adjacent, className, message) {
52
+ const detailPath = _config.default.get('detailPath');
53
+ const csid = (0, _get.default)(adjacent, 'ecm:name');
54
+ return /*#__PURE__*/_react.default.createElement("span", null, /*#__PURE__*/_react.default.createElement(_reactRouterDom.Link, {
55
+ className: className,
64
56
  to: {
65
57
  pathname: `/${detailPath}/${csid}`,
66
58
  state: {
67
- index: index - 1,
68
- searchParams: searchParamsObj
59
+ index,
60
+ searchParams
69
61
  }
70
62
  }
71
- }, /*#__PURE__*/_react.default.createElement(_reactIntl.FormattedMessage, messages.prev)));
63
+ }, /*#__PURE__*/_react.default.createElement(_reactIntl.FormattedMessage, message)));
72
64
  }
73
- if (next) {
74
- const csid = (0, _get.default)(next, 'ecm:name');
75
- nextLink = /*#__PURE__*/_react.default.createElement("span", null, /*#__PURE__*/_react.default.createElement(_reactRouterDom.Link, {
76
- className: _Link.default.next,
77
- to: {
78
- pathname: `/${detailPath}/${csid}`,
79
- state: {
80
- index: index + 1,
81
- searchParams: searchParamsObj
82
- }
83
- }
84
- }, /*#__PURE__*/_react.default.createElement(_reactIntl.FormattedMessage, messages.next)));
65
+ let prevLink;
66
+ let nextLink;
67
+ let queryString = '';
68
+ const index = params.get('index');
69
+ const searchParams = params.get('searchParams');
70
+ if (searchParams && index !== undefined) {
71
+ const searchParamsObj = searchParams.toJS();
72
+ prevLink = prev && renderLink(searchParamsObj, index - 1, prev, _Link.default.prev, messages.prev);
73
+ nextLink = next && renderLink(searchParamsObj, index + 1, next, _Link.default.next, messages.next);
74
+ queryString = (0, _urlHelpers.searchParamsToQueryString)(searchParams);
85
75
  }
86
- const queryString = (0, _urlHelpers.searchParamsToQueryString)(searchParams);
87
76
  return /*#__PURE__*/_react.default.createElement("nav", {
88
77
  className: _DetailNavBar.default.common
89
78
  }, /*#__PURE__*/_react.default.createElement("div", null, /*#__PURE__*/_react.default.createElement(_reactRouterDom.Link, {
@@ -115,11 +115,11 @@ var _default = exports.default = {
115
115
  fields: ['fieldCollectionDate', 'fieldCollector']
116
116
  },
117
117
  group_description: {
118
- fields: ['material', 'technique', 'subject', 'contentDescription', 'measuredPart', 'creditLine', 'taxon']
118
+ fields: ['material', 'technique', 'subject', 'color', 'contentDescription', 'measuredPart', 'creditLine', 'taxon']
119
119
  }
120
120
  },
121
121
  layout: {
122
- fields1: ['group_id', 'group_collection', 'group_description', 'group_production']
122
+ fields1: ['group_id', 'group_collection', 'group_description', 'group_production', 'group_reference']
123
123
  }
124
124
  }
125
125
  };
@@ -343,7 +343,7 @@ var _default = exports.default = {
343
343
  'collectionobjects_common:briefDescriptions': briefDescriptions
344
344
  } = data;
345
345
  if (briefDescriptions && briefDescriptions.length > 0) {
346
- return briefDescriptions;
346
+ return briefDescriptions.flatMap(desc => desc.split('\n'));
347
347
  }
348
348
  return [];
349
349
  },
@@ -460,6 +460,16 @@ var _default = exports.default = {
460
460
  format: (0, _formatHelpers.filterLink)({})
461
461
  }))
462
462
  },
463
+ color: {
464
+ messages: (0, _reactIntl.defineMessages)({
465
+ label: {
466
+ "id": "filter.color.label",
467
+ "defaultMessage": "Color"
468
+ }
469
+ }),
470
+ field: 'collectionobjects_common:colors',
471
+ format: _formatHelpers.inlineList
472
+ },
463
473
  technique: {
464
474
  messages: (0, _reactIntl.defineMessages)({
465
475
  label: {
@@ -493,7 +503,10 @@ var _default = exports.default = {
493
503
  "defaultMessage": "Content Description"
494
504
  }
495
505
  }),
496
- field: 'collectionobjects_common:contentDescription'
506
+ field: 'collectionobjects_common:contentDescription',
507
+ format: (0, _formatHelpers.split)({
508
+ format: _formatHelpers.paragraphs
509
+ })
497
510
  },
498
511
  measuredPart: {
499
512
  messages: (0, _reactIntl.defineMessages)({
@@ -32,7 +32,7 @@ var _default = exports.default = {
32
32
  }
33
33
  },
34
34
  layout: {
35
- fields1: ['group_production', 'group_id', 'group_description', 'group_rights']
35
+ fields1: ['group_production', 'group_id', 'group_description', 'group_rights', 'group_reference']
36
36
  }
37
37
  }
38
38
  };
@@ -5,7 +5,7 @@ Object.defineProperty(exports, "__esModule", {
5
5
  });
6
6
  exports.default = void 0;
7
7
  var _get = _interopRequireDefault(require("lodash/get"));
8
- var _merge = _interopRequireDefault(require("lodash/merge"));
8
+ var _mergeWith = _interopRequireDefault(require("lodash/mergeWith"));
9
9
  var _default2 = _interopRequireDefault(require("./default"));
10
10
  var _anthro = _interopRequireDefault(require("./anthro"));
11
11
  var _bonsai = _interopRequireDefault(require("./bonsai"));
@@ -26,7 +26,14 @@ const namedConfig = {
26
26
  materials: _materials.default,
27
27
  publicart: _publicart.default
28
28
  };
29
- const config = (0, _merge.default)({}, _default2.default);
29
+ const config = (0, _mergeWith.default)({}, _default2.default);
30
+ const configMerge = (objValue, srcValue) => {
31
+ // overwrite arrays instead of merging them
32
+ if (Array.isArray(objValue)) {
33
+ return srcValue;
34
+ }
35
+ return undefined;
36
+ };
30
37
  var _default = exports.default = {
31
38
  get: (path, defaultValue) => (0, _get.default)(config, path, defaultValue),
32
39
  // eslint-disable-next-line no-console
@@ -39,10 +46,10 @@ var _default = exports.default = {
39
46
  if (baseConfigName) {
40
47
  const baseConfig = namedConfig[baseConfigName];
41
48
  if (baseConfig) {
42
- (0, _merge.default)(config, baseConfig);
49
+ (0, _mergeWith.default)(config, baseConfig, configMerge);
43
50
  }
44
51
  }
45
- (0, _merge.default)(config, source);
52
+ (0, _mergeWith.default)(config, source, configMerge);
46
53
  });
47
54
  },
48
55
  getFilterFieldConfig: id => (0, _get.default)(config, ['filters', 'fields', id])
@@ -15,7 +15,7 @@ var _default = exports.default = {
15
15
  },
16
16
  detailFields: {
17
17
  layout: {
18
- fields1: ['group_production', 'group_id', 'group_description', 'group_rights']
18
+ fields1: ['group_production', 'group_id', 'group_description', 'group_rights', 'group_reference']
19
19
  }
20
20
  }
21
21
  };
@@ -68,7 +68,7 @@ var _default = exports.default = {
68
68
  const {
69
69
  'materials_common:description': description
70
70
  } = data;
71
- return description;
71
+ return description && description.split('\n');
72
72
  },
73
73
  filters: {
74
74
  fields: {
@@ -1003,7 +1003,7 @@ var _default = exports.default = {
1003
1003
  }
1004
1004
  },
1005
1005
  layout: {
1006
- fields1: ['group_sample_otherNumberList', 'group_sample_collection', 'group_sample_namedCollection', 'group_sample_computedCurrentLocation', 'group_sample_materialPhysicalDescriptions', 'group_sample_condition', 'group_sample_description', 'group_sample_holdings', 'group_sample_briefDescriptions', 'group_sample_measuredPartGroupList', 'group_sample_system']
1006
+ fields1: ['group_sample_otherNumberList', 'group_sample_collection', 'group_sample_namedCollection', 'group_sample_computedCurrentLocation', 'group_sample_materialPhysicalDescriptions', 'group_sample_condition', 'group_sample_description', 'group_sample_holdings', 'group_sample_briefDescriptions', 'group_sample_measuredPartGroupList', 'group_sample_system', 'group_reference']
1007
1007
  }
1008
1008
  }
1009
1009
  }
@@ -3,7 +3,7 @@
3
3
  Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
- exports.valueWithNote = exports.valueAt = exports.unqualifiedFieldName = exports.unformatted = exports.renderLink = exports.renderJoined = exports.renderFilterLink = exports.property = exports.pickFromList = exports.pickAllFromList = exports.paragraphs = exports.objectTypeValue = exports.numericRange = exports.nameValue = exports.nameRole = exports.literal = exports.listOf = exports.list = exports.linkedDisplayName = exports.linkText = exports.linkNote = exports.lines = exports.inlineListOf = exports.inlineList = exports.html = exports.head = exports.filterLink = exports.displayNameFrom = exports.displayName = exports.decade = exports.collectionValue = exports.boolean = void 0;
6
+ exports.valueWithNote = exports.valueAt = exports.unqualifiedFieldName = exports.unformatted = exports.split = exports.renderLink = exports.renderJoined = exports.renderFilterLink = exports.property = exports.pickFromList = exports.pickAllFromList = exports.paragraphs = exports.objectTypeValue = exports.numericRange = exports.nameValue = exports.nameRole = exports.literal = exports.listOf = exports.list = exports.linkedDisplayName = exports.linkText = exports.linkNote = exports.lines = exports.inlineListOf = exports.inlineList = exports.html = exports.head = exports.filterLink = exports.displayNameFrom = exports.displayName = exports.decade = exports.collectionValue = exports.boolean = void 0;
7
7
  var _react = _interopRequireDefault(require("react"));
8
8
  var _get = _interopRequireDefault(require("lodash/get"));
9
9
  var _qs = _interopRequireDefault(require("qs"));
@@ -224,13 +224,39 @@ const numericRange = config => data => {
224
224
  const rangeUnit = renderJoined([range, unit], ' ');
225
225
  return renderJoined([rangeUnit, linkQualifier ? renderFilterLink(qualifierFieldName, qualifier) : qualifier], qualifierSeparator);
226
226
  };
227
+
228
+ /**
229
+ * Create a paragraph element for each String in an array. If the String contains a newline, it will
230
+ * be split in order to retain line breaks in that display.
231
+ *
232
+ * @param {} array
233
+ * @returns
234
+ */
227
235
  exports.numericRange = numericRange;
228
236
  const paragraphs = array =>
229
237
  // eslint-disable-next-line react/no-array-index-key
230
- array && array.length > 0 && array.map((value, index) => /*#__PURE__*/_react.default.createElement("p", {
238
+ Array.isArray(array) && array.flatMap(value => value.split('\n')).map((value, index) => /*#__PURE__*/_react.default.createElement("p", {
231
239
  key: index
232
240
  }, value));
241
+
242
+ /**
243
+ * Split a string based on a given character to split with. Defaults to newline.
244
+ *
245
+ * @param {*} config
246
+ * @returns
247
+ */
233
248
  exports.paragraphs = paragraphs;
249
+ const split = config => string => {
250
+ const {
251
+ splitter = '\n',
252
+ format = unformatted
253
+ } = config;
254
+ if (!(typeof string === 'string' || string instanceof String)) {
255
+ return null;
256
+ }
257
+ return format(string.split(splitter));
258
+ };
259
+ exports.split = split;
234
260
  const head = format => (array, fieldName) => Array.isArray(array) && array.length > 0 ? format(array[0], fieldName) : null;
235
261
  exports.head = head;
236
262
  const valueAt = config => data => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@collectionspace/cspace-public-browser",
3
- "version": "3.3.0",
3
+ "version": "3.4.0",
4
4
  "description": "CollectionSpace public browser",
5
5
  "author": "Ray Lee <ray.lee@lyrasis.org>",
6
6
  "license": "ECL-2.0",
@@ -10,7 +10,7 @@ import styles from '../../../styles/cspace/DetailNavBar.css';
10
10
  import linkStyles from '../../../styles/cspace/Link.css';
11
11
 
12
12
  const propTypes = {
13
- params: PropTypes.instanceOf(Immutable.Map).isRequired,
13
+ params: PropTypes.instanceOf(Immutable.Map),
14
14
  prev: PropTypes.shape({
15
15
  'ecm:name': PropTypes.string,
16
16
  }),
@@ -20,6 +20,7 @@ const propTypes = {
20
20
  };
21
21
 
22
22
  const defaultProps = {
23
+ params: Immutable.Map(),
23
24
  prev: undefined,
24
25
  next: undefined,
25
26
  };
@@ -39,72 +40,43 @@ const messages = defineMessages({
39
40
  },
40
41
  });
41
42
 
42
- export default function DetailNavBar(props) {
43
- const {
44
- params,
45
- prev,
46
- next,
47
- } = props;
43
+ export default function DetailNavBar({ params, prev, next }) {
44
+ function renderLink(searchParams, index, adjacent, className, message) {
45
+ const detailPath = config.get('detailPath');
46
+ const csid = get(adjacent, 'ecm:name');
48
47
 
49
- const index = params.get('index');
50
- const searchParams = params.get('searchParams');
51
-
52
- if (!searchParams || typeof index === 'undefined') {
53
- return null;
54
- }
55
-
56
- const searchParamsObj = searchParams.toJS();
57
- const detailPath = config.get('detailPath');
58
-
59
- let prevLink;
60
- let nextLink;
61
-
62
- if (prev) {
63
- const csid = get(prev, 'ecm:name');
64
-
65
- prevLink = (
48
+ return (
66
49
  <span>
67
50
  <Link
68
- className={linkStyles.prev}
51
+ className={className}
69
52
  to={{
70
53
  pathname: `/${detailPath}/${csid}`,
71
54
  state: {
72
- index: index - 1,
73
- searchParams: searchParamsObj,
55
+ index,
56
+ searchParams,
74
57
  },
75
58
  }}
76
59
  >
77
60
  {/* eslint-disable-next-line react/jsx-props-no-spreading */}
78
- <FormattedMessage {...messages.prev} />
61
+ <FormattedMessage {...message} />
79
62
  </Link>
80
63
  </span>
81
64
  );
82
65
  }
83
66
 
84
- if (next) {
85
- const csid = get(next, 'ecm:name');
67
+ let prevLink;
68
+ let nextLink;
69
+ let queryString = '';
86
70
 
87
- nextLink = (
88
- <span>
89
- <Link
90
- className={linkStyles.next}
91
- to={{
92
- pathname: `/${detailPath}/${csid}`,
93
- state: {
94
- index: index + 1,
95
- searchParams: searchParamsObj,
96
- },
97
- }}
98
- >
99
- {/* eslint-disable-next-line react/jsx-props-no-spreading */}
100
- <FormattedMessage {...messages.next} />
101
- </Link>
102
- </span>
103
- );
71
+ const index = params.get('index');
72
+ const searchParams = params.get('searchParams');
73
+ if (searchParams && index !== undefined) {
74
+ const searchParamsObj = searchParams.toJS();
75
+ prevLink = prev && renderLink(searchParamsObj, index - 1, prev, linkStyles.prev, messages.prev);
76
+ nextLink = next && renderLink(searchParamsObj, index + 1, next, linkStyles.next, messages.next);
77
+ queryString = searchParamsToQueryString(searchParams);
104
78
  }
105
79
 
106
- const queryString = searchParamsToQueryString(searchParams);
107
-
108
80
  return (
109
81
  <nav className={styles.common}>
110
82
  <div>
@@ -138,6 +138,7 @@ export default {
138
138
  'material',
139
139
  'technique',
140
140
  'subject',
141
+ 'color',
141
142
  'contentDescription',
142
143
  'measuredPart',
143
144
  'creditLine',
@@ -151,6 +152,7 @@ export default {
151
152
  'group_collection',
152
153
  'group_description',
153
154
  'group_production',
155
+ 'group_reference',
154
156
  ],
155
157
  },
156
158
  },
@@ -6,10 +6,13 @@ import {
6
6
  decade,
7
7
  displayName,
8
8
  filterLink,
9
+ inlineList,
9
10
  linkText,
10
11
  list,
11
12
  listOf,
12
13
  nameRole,
14
+ paragraphs,
15
+ split,
13
16
  valueAt,
14
17
  } from '../helpers/formatHelpers';
15
18
 
@@ -401,7 +404,7 @@ export default {
401
404
  } = data;
402
405
 
403
406
  if (briefDescriptions && briefDescriptions.length > 0) {
404
- return briefDescriptions;
407
+ return briefDescriptions.flatMap((desc) => desc.split('\n'));
405
408
  }
406
409
 
407
410
  return [];
@@ -516,6 +519,16 @@ export default {
516
519
  format: filterLink({}),
517
520
  })),
518
521
  },
522
+ color: {
523
+ messages: defineMessages({
524
+ label: {
525
+ id: 'filter.color.label',
526
+ defaultMessage: 'Color',
527
+ },
528
+ }),
529
+ field: 'collectionobjects_common:colors',
530
+ format: inlineList,
531
+ },
519
532
  technique: {
520
533
  messages: defineMessages({
521
534
  label: {
@@ -550,6 +563,9 @@ export default {
550
563
  },
551
564
  }),
552
565
  field: 'collectionobjects_common:contentDescription',
566
+ format: split({
567
+ format: paragraphs,
568
+ }),
553
569
  },
554
570
  measuredPart: {
555
571
  messages: defineMessages({
@@ -41,6 +41,7 @@ export default {
41
41
  'group_id',
42
42
  'group_description',
43
43
  'group_rights',
44
+ 'group_reference',
44
45
  ],
45
46
  },
46
47
  },
@@ -1,5 +1,5 @@
1
1
  import loget from 'lodash/get';
2
- import lomerge from 'lodash/merge';
2
+ import lomerge from 'lodash/mergeWith';
3
3
  import defaultConfig from './default';
4
4
  import anthroConfig from './anthro';
5
5
  import bonsaiConfig from './bonsai';
@@ -23,6 +23,15 @@ const namedConfig = {
23
23
 
24
24
  const config = lomerge({}, defaultConfig);
25
25
 
26
+ const configMerge = (objValue, srcValue) => {
27
+ // overwrite arrays instead of merging them
28
+ if (Array.isArray(objValue)) {
29
+ return srcValue;
30
+ }
31
+
32
+ return undefined;
33
+ };
34
+
26
35
  export default {
27
36
  get: (path, defaultValue) => loget(config, path, defaultValue),
28
37
 
@@ -39,11 +48,11 @@ export default {
39
48
  const baseConfig = namedConfig[baseConfigName];
40
49
 
41
50
  if (baseConfig) {
42
- lomerge(config, baseConfig);
51
+ lomerge(config, baseConfig, configMerge);
43
52
  }
44
53
  }
45
54
 
46
- lomerge(config, source);
55
+ lomerge(config, source, configMerge);
47
56
  });
48
57
  },
49
58
 
@@ -15,6 +15,7 @@ export default {
15
15
  'group_id',
16
16
  'group_description',
17
17
  'group_rights',
18
+ 'group_reference',
18
19
  ],
19
20
  },
20
21
  },
@@ -119,7 +119,7 @@ export default {
119
119
  'materials_common:description': description,
120
120
  } = data;
121
121
 
122
- return description;
122
+ return description && description.split('\n');
123
123
  },
124
124
 
125
125
  filters: {
@@ -1194,6 +1194,7 @@ export default {
1194
1194
  'group_sample_briefDescriptions',
1195
1195
  'group_sample_measuredPartGroupList',
1196
1196
  'group_sample_system',
1197
+ 'group_reference',
1197
1198
  ],
1198
1199
  },
1199
1200
  },
@@ -294,11 +294,37 @@ export const numericRange = (config) => (data) => {
294
294
  ], qualifierSeparator);
295
295
  };
296
296
 
297
+ /**
298
+ * Create a paragraph element for each String in an array. If the String contains a newline, it will
299
+ * be split in order to retain line breaks in that display.
300
+ *
301
+ * @param {} array
302
+ * @returns
303
+ */
297
304
  export const paragraphs = (array) => (
298
305
  // eslint-disable-next-line react/no-array-index-key
299
- array && array.length > 0 && array.map((value, index) => <p key={index}>{value}</p>)
306
+ Array.isArray(array) && array.flatMap((value) => value.split('\n')).map((value, index) => <p key={index}>{value}</p>)
300
307
  );
301
308
 
309
+ /**
310
+ * Split a string based on a given character to split with. Defaults to newline.
311
+ *
312
+ * @param {*} config
313
+ * @returns
314
+ */
315
+ export const split = (config) => (string) => {
316
+ const {
317
+ splitter = '\n',
318
+ format = unformatted,
319
+ } = config;
320
+
321
+ if (!(typeof string === 'string' || string instanceof String)) {
322
+ return null;
323
+ }
324
+
325
+ return format(string.split(splitter));
326
+ };
327
+
302
328
  export const head = (format) => (array, fieldName) => (
303
329
  Array.isArray(array) && array.length > 0 ? format(array[0], fieldName) : null
304
330
  );
@@ -67,16 +67,3 @@ and (max-width: 839px) {
67
67
  grid-template-columns: auto 360px;
68
68
  }
69
69
  }
70
-
71
- .description > p {
72
- margin-top: 0;
73
- margin-bottom: 0;
74
- }
75
-
76
- .description > p:first-child {
77
- margin-top: 16px;
78
- }
79
-
80
- .description > p:last-child {
81
- margin-bottom: 16px;
82
- }
@@ -25,11 +25,15 @@ a:focus {
25
25
  }
26
26
 
27
27
  p {
28
- margin: 16px 0;
28
+ margin: 0;
29
29
  }
30
30
 
31
31
  p:first-child {
32
- margin-top: 0;
32
+ margin-top: 16px;
33
+ }
34
+
35
+ p:last-child {
36
+ margin-bottom: 16px;
33
37
  }
34
38
 
35
39
  input {