@truedat/audit 4.47.9 → 4.48.3

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.
package/CHANGELOG.md CHANGED
@@ -1,7 +1,15 @@
1
1
  # Changelog
2
2
 
3
+ ## [4.48.2] 2022-07-08
4
+
5
+ ### Changed
6
+
7
+ - [TD-4995] Support localization of template fields and fixed values
8
+
3
9
  ## [4.47.4] 2022-06-29
4
10
 
11
+ ### Added
12
+
5
13
  - [TD-4921] Add implementation workflow events
6
14
 
7
15
  ## [4.45.6] 2022-06-06
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@truedat/audit",
3
- "version": "4.47.9",
3
+ "version": "4.48.3",
4
4
  "description": "Truedat Web Audit Module",
5
5
  "sideEffects": false,
6
6
  "jsnext:main": "src/index.js",
@@ -85,8 +85,8 @@
85
85
  ]
86
86
  },
87
87
  "dependencies": {
88
- "@truedat/auth": "4.47.9",
89
- "@truedat/core": "4.47.9",
88
+ "@truedat/auth": "4.48.3",
89
+ "@truedat/core": "4.48.3",
90
90
  "axios": "^0.19.2",
91
91
  "path-to-regexp": "^1.7.0",
92
92
  "prop-types": "^15.8.1",
@@ -107,5 +107,5 @@
107
107
  "react-dom": ">= 16.8.6 < 17",
108
108
  "semantic-ui-react": ">= 0.88.2 < 2.1"
109
109
  },
110
- "gitHead": "21954b7a0ea8240d2a9e8dc5014372eceed3b047"
110
+ "gitHead": "5b30312f30c532988985ab9271d1e39ad0ad5c43"
111
111
  }
@@ -7,44 +7,66 @@ import { useIntl } from "react-intl";
7
7
  import { connect } from "react-redux";
8
8
  import { CONCEPT_EVENTS, isSubset } from "../subscriptionConstants";
9
9
 
10
- const toTemplateOptions = (templates) =>
10
+ const toTemplateOptions = (formatMessage) =>
11
11
  _.flow(
12
- _.map(({ id: value, label: text }) => ({ value, text })),
12
+ _.map(({ id: value, label }) => ({
13
+ value,
14
+ text: formatMessage({ id: `templates.${label}`, defaultMessage: label }),
15
+ })),
13
16
  _.sortBy("text")
14
- )(templates);
17
+ );
15
18
 
16
- const isFixed = (values) =>
17
- _.conformsTo({ fixed: _.negate(_.isEmpty) })(values);
18
- const isFixedTuple = (values) =>
19
- _.conformsTo({ fixed_tuple: _.negate(_.isEmpty) })(values);
19
+ const isFixed = _.conformsTo({ fixed: _.negate(_.isEmpty) });
20
+ const isFixedTuple = _.conformsTo({ fixed_tuple: _.negate(_.isEmpty) });
20
21
 
21
- const toFieldOptions = (fields) =>
22
- _.map(({ label: text, name: value }) => ({
23
- text,
22
+ const toFieldOptions = (formatMessage) =>
23
+ _.map(({ label, name: value }) => ({
24
+ text: label
25
+ ? formatMessage({ id: `fields.${label}`, defaultMessage: label })
26
+ : label,
24
27
  value,
25
- }))(fields);
26
-
27
- const fieldsFromTemplate = (template) =>
28
- template
29
- ? _.flow(
30
- _.prop("content"),
31
- _.map("fields"),
32
- _.flatten,
33
- _.filter(_.propOr(false, "subscribable"))
34
- )(template)
35
- : [];
28
+ }));
36
29
 
37
- const renderFixed = _.flow(
38
- _.propOr([], "fixed"),
39
- _.map((opt) => ({ text: opt, value: opt }))
30
+ const fieldsFromTemplate = _.flow(
31
+ _.prop("content"),
32
+ _.flatMap("fields"),
33
+ _.filter("subscribable"),
34
+ _.defaultTo([])
40
35
  );
41
- const renderFixedTuple = _.propOr([], "fixed_tuple");
42
- const toValueOptions = (field) => {
43
- const values = _.prop("values")(field);
44
- if (isFixed(values)) return renderFixed(values);
45
- if (isFixedTuple(values)) return renderFixedTuple(values);
46
- return [];
47
- };
36
+
37
+ const renderFixed = (formatMessage, fieldName) =>
38
+ _.flow(
39
+ _.propOr([], "fixed"),
40
+ _.map((value) => ({
41
+ text: value
42
+ ? formatMessage({
43
+ id: `fields.${fieldName}.${value}`,
44
+ defaultMessage: value,
45
+ })
46
+ : value,
47
+ value,
48
+ }))
49
+ );
50
+ const renderFixedTuple = (formatMessage, fieldName) =>
51
+ _.flow(
52
+ _.propOr([], "fixed_tuple"),
53
+ _.map(({ text, value }) => ({
54
+ text: text
55
+ ? formatMessage({
56
+ id: `fields.${fieldName}.${text}`,
57
+ defaultMessage: text,
58
+ })
59
+ : text,
60
+ value,
61
+ }))
62
+ );
63
+
64
+ const toValueOptions = (formatMessage, fieldName) =>
65
+ _.cond([
66
+ [isFixed, renderFixed(formatMessage, fieldName)],
67
+ [isFixedTuple, renderFixedTuple(formatMessage, fieldName)],
68
+ [_.stubTrue, _.constant([])],
69
+ ]);
48
70
 
49
71
  export const ContentFilters = ({
50
72
  conceptType,
@@ -83,14 +105,14 @@ export const ContentFilters = ({
83
105
  });
84
106
  };
85
107
  const fields = _.flow(
86
- _.find(({ id }) => id === templateId),
108
+ _.find({ id: templateId }),
87
109
  fieldsFromTemplate
88
110
  )(templates);
89
- const field = _.find(({ name }) => name === filterName)(fields);
111
+ const field = _.find({ name: filterName })(fields);
90
112
 
91
- const templateOptions = toTemplateOptions(templates);
92
- const fieldOptions = toFieldOptions(fields);
93
- const valueOptions = toValueOptions(field);
113
+ const templateOptions = toTemplateOptions(formatMessage)(templates);
114
+ const fieldOptions = toFieldOptions(formatMessage)(fields);
115
+ const valueOptions = toValueOptions(formatMessage, filterName)(field?.values);
94
116
 
95
117
  return isSubset(events, CONCEPT_EVENTS) ? (
96
118
  <>
@@ -26,6 +26,7 @@ const fieldValue = (value, field) => {
26
26
  if (_.has("values.fixed")(field)) return value;
27
27
  if (_.has("values.fixed_tuple")(field)) return fromTuple(field, value);
28
28
  };
29
+
29
30
  export const SubscriptionHeader = ({ header, subheader }) => (
30
31
  <Grid>
31
32
  <Grid.Column width={12}>
@@ -56,30 +57,28 @@ export const Subscription = ({
56
57
  }) => {
57
58
  if (_.isEmpty(subscription) || loading) return null;
58
59
 
59
- const { type, identifier } = _.getOr({}, "subscriber")(subscription);
60
+ const { type, identifier } = _.propOr({}, "subscriber")(subscription);
60
61
  const subscriber =
61
62
  type === "user"
62
63
  ? _.flow(
63
64
  _.find({ id: parseInt(identifier, 10) }),
64
- _.get("full_name")
65
+ _.prop("full_name")
65
66
  )(users)
66
67
  : identifier;
67
- const resourceName = _.get("resource.name")(subscription);
68
- const resourceType = _.get("scope.resource_type")(subscription);
69
- const periodicity = _.get("periodicity")(subscription);
70
- const events = _.getOr([], "scope.events")(subscription);
71
- const status = _.getOr([], "scope.status")(subscription);
72
- const filters = _.prop("scope.filters")(subscription);
73
- const template = _.find(({ id }) => id === _.path("template.id")(filters))(
74
- templates
75
- );
68
+ const resourceName = subscription.resource?.name;
69
+ const periodicity = subscription.periodicity;
70
+ const events = subscription.scope?.events;
71
+ const status = subscription.scope?.status;
72
+ const filters = subscription.scope?.filters;
73
+ const template = _.find({ id: filters?.template?.id })(templates);
74
+ const templateLabel = template?.label;
76
75
  const field = _.flow(
77
76
  _.prop("content"),
78
77
  _.defaultTo([]),
79
- _.map("fields"),
80
- _.flatten,
81
- _.find(({ name }) => name === _.path("content.name")(filters))
78
+ _.flatMap("fields"),
79
+ _.find({ name: filters?.content?.name })
82
80
  )(template);
81
+ const fieldLabel = field?.label;
83
82
 
84
83
  return (
85
84
  <>
@@ -102,25 +101,27 @@ export const Subscription = ({
102
101
  </List.Description>
103
102
  </List.Item>
104
103
  ) : null}
105
- <List.Item>
106
- <List.Header>
107
- <FormattedMessage id="subscriptions.events" />
108
- </List.Header>
109
- <List.Description>
110
- {events.map((event, idx) => (
111
- <Label key={idx}>
112
- <FormattedMessage
113
- id={`subscriptions.events.${event}`}
114
- defaultMessage={event}
115
- />
116
- </Label>
117
- ))}
118
- </List.Description>
119
- </List.Item>
120
- {!_.isEmpty(status) && (
104
+ {_.isEmpty(events) ? null : (
105
+ <List.Item>
106
+ <List.Header>
107
+ <FormattedMessage id="subscriptions.events" />
108
+ </List.Header>
109
+ <List.Description>
110
+ {events.map((event, idx) => (
111
+ <Label key={idx}>
112
+ <FormattedMessage
113
+ id={`subscriptions.events.${event}`}
114
+ defaultMessage={event}
115
+ />
116
+ </Label>
117
+ ))}
118
+ </List.Description>
119
+ </List.Item>
120
+ )}
121
+ {_.isEmpty(status) ? null : (
121
122
  <List.Item>
122
123
  <List.Header>
123
- <FormattedMessage id={"subscriptions.status"} />
124
+ <FormattedMessage id="subscriptions.status" />
124
125
  </List.Header>
125
126
  <List.Description>
126
127
  {status.map((status, idx) => (
@@ -134,42 +135,46 @@ export const Subscription = ({
134
135
  </List.Description>
135
136
  </List.Item>
136
137
  )}
137
- {!_.isEmpty(filters) && (
138
+ {_.isEmpty(filters) ? null : (
138
139
  <List.Item>
139
140
  <List.Header>
140
- <FormattedMessage id={"subscriptions.filters"} />
141
+ <FormattedMessage id="subscriptions.filters" />
141
142
  </List.Header>
142
143
  <List.Description>
143
- <FormattedMessage id={"subscriptions.filters.description"} />{" "}
144
- <b>{_.prop("label")(template)}</b>
144
+ <FormattedMessage id="subscriptions.filters.description" />{" "}
145
+ <b>
146
+ <FormattedMessage
147
+ id={`templates.${templateLabel}`}
148
+ defaultMessage={templateLabel}
149
+ />
150
+ </b>
145
151
  </List.Description>
146
- {!_.isEmpty(field) && (
152
+ {_.isEmpty(field) ? null : (
147
153
  <List.Content>
148
154
  <List.Description>
149
155
  <Table celled>
150
156
  <Table.Header>
151
157
  <Table.Row>
152
158
  <Table.HeaderCell>
153
- <FormattedMessage
154
- id={"subscriptions.template.field"}
155
- />
159
+ <FormattedMessage id="subscriptions.template.field" />
156
160
  </Table.HeaderCell>
157
161
  <Table.HeaderCell>
158
- <FormattedMessage
159
- id={"subscriptions.template.field.value"}
160
- />
162
+ <FormattedMessage id="subscriptions.template.field.value" />
161
163
  </Table.HeaderCell>
162
164
  </Table.Row>
163
165
  </Table.Header>
164
-
165
166
  <Table.Body>
166
167
  <Table.Row>
167
- <Table.Cell>{_.prop("label")(field)}</Table.Cell>
168
168
  <Table.Cell>
169
- {fieldValue(
170
- _.path("content.value")(filters),
171
- field
172
- )}
169
+ {fieldLabel ? (
170
+ <FormattedMessage
171
+ id={`fields.${fieldLabel}`}
172
+ defaultMessage={fieldLabel}
173
+ />
174
+ ) : null}
175
+ </Table.Cell>
176
+ <Table.Cell>
177
+ {fieldValue(filters?.content?.value, field)}
173
178
  </Table.Cell>
174
179
  </Table.Row>
175
180
  </Table.Body>
@@ -1,7 +1,7 @@
1
1
  import _ from "lodash/fp";
2
2
  import React, { Suspense, useState, useEffect } from "react";
3
3
  import PropTypes from "prop-types";
4
- import { useIntl } from "react-intl";
4
+ import { useIntl, FormattedMessage } from "react-intl";
5
5
  import { useForm, useWatch, Controller } from "react-hook-form";
6
6
  import { Button, Form, Radio, Icon } from "semantic-ui-react";
7
7
  import { HistoryBackButton } from "@truedat/core/components";
@@ -183,7 +183,9 @@ export const SubscriptionForm = ({
183
183
  rules={{ required: true }}
184
184
  render={({ field: { onBlur, onChange, value } }) => (
185
185
  <Form.Field className="subscription-form-radio-group" required>
186
- <label>{formatMessage({ id: "subscriptions.subscriber" })}</label>
186
+ <label>
187
+ <FormattedMessage id="subscriptions.subscriber" />
188
+ </label>
187
189
  {SUBSCRIBER_TYPES.map((type, idx) => (
188
190
  <Radio
189
191
  role="radio"
@@ -193,9 +195,10 @@ export const SubscriptionForm = ({
193
195
  label={
194
196
  <label>
195
197
  <Icon name={subscriberIcon(type)} />
196
- {formatMessage({
197
- id: `subscription.subscriber_type.${type}`,
198
- })}
198
+ <FormattedMessage
199
+ id={`subscription.subscriber_type.${type}`}
200
+ defaultMessage={type}
201
+ />
199
202
  </label>
200
203
  }
201
204
  name={type}
@@ -275,7 +278,9 @@ export const SubscriptionForm = ({
275
278
  rules={{ required: true }}
276
279
  render={({ field: { onBlur, onChange, value } }) => (
277
280
  <Form.Field className="subscription-form-radio-group" required>
278
- <label>{formatMessage({ id: "subscriptions.resource" })}</label>
281
+ <label>
282
+ <FormattedMessage id="subscriptions.resource" />
283
+ </label>
279
284
  {RESOURCE_TYPES.map((type, idx) => (
280
285
  <Radio
281
286
  role="radio"
@@ -293,9 +298,10 @@ export const SubscriptionForm = ({
293
298
  label={
294
299
  <label>
295
300
  <Icon name={resourceIcon(type)} />
296
- {formatMessage({
297
- id: `subscriptions.resource.type.${type}`,
298
- })}
301
+ <FormattedMessage
302
+ id={`subscriptions.resource.type.${type}`}
303
+ defaultMessage={type}
304
+ />
299
305
  </label>
300
306
  }
301
307
  value={type}
@@ -391,9 +397,7 @@ export const SubscriptionForm = ({
391
397
  label={formatMessage({ id: "subscriptions.periodicity" })}
392
398
  onBlur={onBlur}
393
399
  onChange={(_e, { value }) => onChange(value)}
394
- placeholder={formatMessage({
395
- id: "subscriptions.periodicity",
396
- })}
400
+ placeholder={formatMessage({ id: "subscriptions.periodicity" })}
397
401
  value={value}
398
402
  required
399
403
  options={PERIODICITIES.map((periodicity, key) => ({
@@ -480,7 +484,10 @@ export const SubscriptionForm = ({
480
484
  color={color}
481
485
  />
482
486
  ) : null}
483
- {formatMessage({ id: `subscriptions.status.${name}` })}
487
+ <FormattedMessage
488
+ id={`subscriptions.status.${name}`}
489
+ defaultMessage={name}
490
+ />
484
491
  </label>
485
492
  ),
486
493
  }))}
@@ -1,6 +1,6 @@
1
1
  import _ from "lodash/fp";
2
2
  import React from "react";
3
- import { Form, Radio, Button } from "semantic-ui-react";
3
+ import { Form, Radio, Button, Icon } from "semantic-ui-react";
4
4
  import { FormattedMessage } from "react-intl";
5
5
  import PropTypes from "prop-types";
6
6
 
@@ -11,10 +11,9 @@ export const SubscriptionWatchForm = ({
11
11
  handleSubmit,
12
12
  handleDelete,
13
13
  subscriptionUpdating,
14
- children
14
+ children,
15
15
  }) => {
16
- const periodicity = _.prop("periodicity")(subscription);
17
- const subscription_id = _.prop("id")(subscription);
16
+ const periodicity = subscription?.periodicity;
18
17
 
19
18
  return (
20
19
  <Form>
@@ -32,9 +31,9 @@ export const SubscriptionWatchForm = ({
32
31
  </label>
33
32
  }
34
33
  value="minutely"
35
- checked={periodicity == "minutely"}
34
+ checked={periodicity === "minutely"}
36
35
  onChange={handleChange}
37
- ></Radio>
36
+ />
38
37
  </Form.Field>
39
38
  <Form.Field>
40
39
  <Radio
@@ -45,9 +44,9 @@ export const SubscriptionWatchForm = ({
45
44
  </label>
46
45
  }
47
46
  value="hourly"
48
- checked={periodicity == "hourly"}
47
+ checked={periodicity === "hourly"}
49
48
  onChange={handleChange}
50
- ></Radio>
49
+ />
51
50
  </Form.Field>
52
51
  <Form.Field>
53
52
  <Radio
@@ -58,9 +57,9 @@ export const SubscriptionWatchForm = ({
58
57
  </label>
59
58
  }
60
59
  value="daily"
61
- checked={periodicity == "daily"}
60
+ checked={periodicity === "daily"}
62
61
  onChange={handleChange}
63
- ></Radio>
62
+ />
64
63
  </Form.Field>
65
64
  {children}
66
65
  <div>
@@ -72,14 +71,12 @@ export const SubscriptionWatchForm = ({
72
71
  >
73
72
  <FormattedMessage id="actions.save" />
74
73
  </Button>
75
- {subscription_id && (
76
- <Button
77
- type="submit"
78
- onClick={handleDelete}
79
- icon="trash"
80
- content={<FormattedMessage id="ruleSubscription.actions.remove" />}
81
- ></Button>
82
- )}
74
+ {subscription?.id ? (
75
+ <Button type="submit" onClick={handleDelete}>
76
+ <Icon name="trash" />
77
+ <FormattedMessage id="ruleSubscription.actions.remove" />
78
+ </Button>
79
+ ) : null}
83
80
  </div>
84
81
  </Form>
85
82
  );
@@ -92,7 +89,7 @@ SubscriptionWatchForm.propTypes = {
92
89
  handleChange: PropTypes.func,
93
90
  handleSubmit: PropTypes.func,
94
91
  handleDelete: PropTypes.func,
95
- subscriptionUpdating: PropTypes.bool
92
+ subscriptionUpdating: PropTypes.bool,
96
93
  };
97
94
 
98
95
  export default SubscriptionWatchForm;
@@ -113,6 +113,7 @@ export const Subscriptions = ({
113
113
  <Icon name={subscriberIcon({ type })} />
114
114
  <FormattedMessage
115
115
  id={`subscription.subscriber_type.${type}`}
116
+ defaultMessage={type}
116
117
  />
117
118
  </label>
118
119
  }
@@ -146,6 +147,7 @@ export const Subscriptions = ({
146
147
  <Icon name={resourceIcon(type)} />
147
148
  <FormattedMessage
148
149
  id={`subscriptions.resource.type.${type}`}
150
+ defaultMessage={type}
149
151
  />
150
152
  </label>
151
153
  }
@@ -174,15 +176,15 @@ export const Subscriptions = ({
174
176
  <Table className="subscription-table" selectable>
175
177
  <Table.Header>
176
178
  <Table.Row>
177
- <Table.HeaderCell
178
- content={<FormattedMessage id={"subscriptions.subscriber"} />}
179
- />
180
- <Table.HeaderCell
181
- content={<FormattedMessage id={"subscriptions.resource"} />}
182
- />
183
- <Table.HeaderCell
184
- content={<FormattedMessage id={"subscriptions.periodicity"} />}
185
- />
179
+ <Table.HeaderCell>
180
+ <FormattedMessage id="subscriptions.subscriber" />
181
+ </Table.HeaderCell>
182
+ <Table.HeaderCell>
183
+ <FormattedMessage id="subscriptions.resource" />
184
+ </Table.HeaderCell>
185
+ <Table.HeaderCell>
186
+ <FormattedMessage id="subscriptions.periodicity" />
187
+ </Table.HeaderCell>
186
188
  </Table.Row>
187
189
  </Table.Header>
188
190
  <Table.Body>
@@ -198,15 +200,15 @@ export const Subscriptions = ({
198
200
  </Table.Cell>
199
201
  <Table.Cell>
200
202
  <Icon name={resourceIcon(scope.resource_type)} />
201
- {_.get("name")(resource)}
203
+ {resource?.name}
202
204
  </Table.Cell>
203
205
  <Table.Cell>
204
- {periodicity && (
206
+ {periodicity ? (
205
207
  <FormattedMessage
206
208
  id={`subscriptions.periodicity.${periodicity}`}
207
209
  defaultMessage={periodicity}
208
210
  />
209
- )}
211
+ ) : null}
210
212
  </Table.Cell>
211
213
  </Table.Row>
212
214
  )
@@ -73,15 +73,17 @@ exports[`<SubscriptionWatchForm /> matches the latest snapshot 1`] = `
73
73
  </Button>
74
74
  <Button
75
75
  as="button"
76
- content={
77
- <Memo(MemoizedFormattedMessage)
78
- id="ruleSubscription.actions.remove"
79
- />
80
- }
81
- icon="trash"
82
76
  onClick={[MockFunction]}
83
77
  type="submit"
84
- />
78
+ >
79
+ <Icon
80
+ as="i"
81
+ name="trash"
82
+ />
83
+ <MemoizedFormattedMessage
84
+ id="ruleSubscription.actions.remove"
85
+ />
86
+ </Button>
85
87
  </div>
86
88
  </Form>
87
89
  `;