saasufy-components 10.0.0 → 10.1.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.
- package/README.md +4 -2
- package/collection-adder-form.js +29 -13
- package/collection-adder.js +29 -11
- package/input-provider.js +20 -8
- package/model-input.js +19 -7
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -458,6 +458,7 @@ This component is a simplified version of the `collection-adder-form` component
|
|
|
458
458
|
- `autocorrect`: Can be set to `off` to disable auto-correction of input on mobile devices.
|
|
459
459
|
- `show-field-errors`: If this attribute exists on the element, then granular error messages will be shown above each corresponding input element instead of a single form-level error message.
|
|
460
460
|
- `trim-spaces`: If this attribute exists on the element, then leading and trailing spaces will be trimmed from each input element's value before submitting the form.
|
|
461
|
+
- `reset-status-on-submit`: If this attribute exists, then the current message and any field errors will be cleared as soon as the form is submitted, instead of when the outcome of the submit is known. By default, the previous status is kept on screen until the insert either succeeds or fails and is then replaced within a single frame; this avoids the form flickering (shrinking and then growing again) when the same error occurs on consecutive submits.
|
|
461
462
|
- `consumers`: This allows you to connect this `collection-adder` to other elements on your page. It should be used in conjunction with the `provider-template` attribute. The `consumers` attribute takes a list of selectors with optional attributes to target in the format `element-selector:attribute-name`. For example `.my-input:value` will find all elements with a `my-input` class and update their `value` attributes with the output of the `collection-adder` component on submit. You can specify multiple selectors separated by commas such as `.my-input,my-div`; in this case, because attribute names are not specified, values will be injected into the `value` attribute (for input elements) or into the `innerHTML` property (for other kinds of elements). The default attribute/property depends on the element type.
|
|
462
463
|
- `success-consumers`: Same as the `consumers` attribute but the target elements are only updated if insertion was a success.
|
|
463
464
|
- `error-consumers`: Same as the `consumers` attribute but the target elements are only updated if insertion was a failure.
|
|
@@ -499,6 +500,7 @@ This component is similar to the `collection-adder` component except that it req
|
|
|
499
500
|
- `show-field-errors`: If this attribute exists on the element, then granular error messages will be shown above each corresponding input element instead of a single form-level error message.
|
|
500
501
|
- `trim-spaces`: If this attribute exists on the element, then leading and trailing spaces will be trimmed from each input element's value before submitting the form.
|
|
501
502
|
- `auto-reset-hidden-inputs`: If this attribute exists, then `hidden` input elements which are inside the `collection-adder-form` will be cleared along with other input fields. By default, `hidden` input elements are not cleared when the form is reset.
|
|
503
|
+
- `reset-status-on-submit`: If this attribute exists, then the current message and any field errors will be cleared as soon as the form is submitted, instead of when the outcome of the submit is known. By default, the previous status is kept on screen until the insert either succeeds or fails and is then replaced within a single frame; this avoids the form flickering (shrinking and then growing again) when the same error occurs on consecutive submits.
|
|
502
504
|
- `disable-submit-on-enter-key`: If this attribute exists, then the form will not submit when the enter key is pressed.
|
|
503
505
|
- `greedy-refresh`: If this attribute exists, the component will refresh itself whenever an attribute is set, even if that attribute's value did not change.
|
|
504
506
|
- `consumers`: This allows you to connect this `collection-adder-form` to other elements on your page. It should be used in conjunction with the `provider-template` attribute. The `consumers` attribute takes a list of selectors with optional attributes to target in the format `element-selector:attribute-name`. For example `.my-input:value` will find all elements with a `my-input` class and update their `value` attributes with the output of the `collection-adder-form` component on submit. You can specify multiple selectors separated by commas such as `.my-input,my-div`; in this case, because attribute names are not specified, values will be injected into the `value` attribute (for input elements) or into the `innerHTML` property (for other kinds of elements). The default attribute/property depends on the element type.
|
|
@@ -667,7 +669,7 @@ Used for displaying and editing a single field of a model instance in realtime.
|
|
|
667
669
|
- `consumers`: This allows you to connect this `model-input` to other elements on your page. It takes a list of selectors with optional attributes to target in the format `element-selector:attribute-name`. For example `.my-input:value` will find all elements with a `my-input` class and update their `value` attributes with the value of the `model-input` component in real-time. You can specify multiple selectors separated by commas such as `.my-input,my-div`; in this case, because attribute names are not specified, values will be injected into the `value` attribute (for input elements) or into the `innerHTML` property (for other kinds of elements). The default attribute/property depends on the element type. Note that `model-input` elements of the `file` type are treated as write-only unless the `consumers` attribute is present.
|
|
668
670
|
- `provider-template`: A template string within which the `{{value}}` can be injected before passing to consumers.
|
|
669
671
|
- `show-error-message`: If this attribute is present, an error message will be displayed above the input if it fails to update the value.
|
|
670
|
-
- `options`: A comma-separated list of options to provide - This only works if the input type is `select`.
|
|
672
|
+
- `options`: A comma-separated list of options to provide - This only works if the input type is `select`. Each option is in the format `label:type=value`; the `:type` and `=value` parts are optional. If the value is not specified, the label is used as the value. The type can be `string` (default), `number` or `boolean` and determines the type which will be saved to the model field when the option is selected; for example `options="30 min:number=30,1 hour:number=60"` will save the number `30` or `60` instead of the string `'30'` or `'60'`.
|
|
671
673
|
- `height`: Allows you to set the height of the inner `input` element programmatically.
|
|
672
674
|
- `default-value`: A default value to show the user if the underlying model field's value is null or undefined. Note that setting a default value will not affect the underlying model's value.
|
|
673
675
|
- `value`: Used to set the model's value.
|
|
@@ -788,7 +790,7 @@ This component can be configured to provide its data to multiple components (con
|
|
|
788
790
|
- `consumers`: This allows you to connect this `input-provider` to other elements on your page. It takes a list of selectors with optional attributes to target in the format `element-selector:attribute-name`. For example `.my-input:value` will find all elements with a `my-input` class and update their `value` attributes with the value of the `input-provider` component in real-time. You can specify multiple selectors separated by commas such as `.my-input,my-div`; in this case, because attribute names are not specified, values will be injected into the `value` attribute (for input elements) or into the `innerHTML` property (for other kinds of elements). The default attribute/property depends on the element type.
|
|
789
791
|
- `provider-template`: A template string within which the `{{value}}` can be injected before passing to consumers.
|
|
790
792
|
- `debounce-delay`: The delay in milliseconds to wait before triggering a change event. This is useful to batch multiple updates together (as is common when user is typing). Default is 800ms.
|
|
791
|
-
- `options`: A comma-separated list of options to provide - This only works if the input type is `select`.
|
|
793
|
+
- `options`: A comma-separated list of options to provide - This only works if the input type is `select`. Each option is in the format `label:type=value`; the `:type` and `=value` parts are optional. If the value is not specified, the label is used as the value. The type can be `string` (default), `number` or `boolean` and determines the type of the value which will be passed to consumers when the option is selected; for example `options="30 min:number=30,1 hour:number=60"` will pass the number `30` or `60` instead of the string `'30'` or `'60'`.
|
|
792
794
|
- `height`: Allows you to set the height of the inner `input` element programmatically.
|
|
793
795
|
- `value`: Used to set the input's value.
|
|
794
796
|
- `computable-value`: If this attribute is present, it will be possible to execute expressions using the `{{expression}}` syntax inside the `value` attribute.
|
package/collection-adder-form.js
CHANGED
|
@@ -50,22 +50,15 @@ class CollectionAdderForm extends SocketConsumer {
|
|
|
50
50
|
throw new Error('Collection adder form is not ready to be submitted');
|
|
51
51
|
}
|
|
52
52
|
let successMessage = this.getAttribute('success-message');
|
|
53
|
-
let messageContainer
|
|
53
|
+
let messageContainer;
|
|
54
54
|
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
55
|
+
// By default, the previous status is only cleared once the outcome of the
|
|
56
|
+
// submit is known so that the status is replaced within a single frame; this
|
|
57
|
+
// avoids the form flickering when the same error occurs twice in a row.
|
|
58
|
+
if (this.hasAttribute('reset-status-on-submit')) {
|
|
59
|
+
this.clearStatus();
|
|
59
60
|
}
|
|
60
61
|
|
|
61
|
-
// Clear any existing field errors
|
|
62
|
-
let existingFieldErrors = this.querySelectorAll('.collection-adder-field-error-container');
|
|
63
|
-
existingFieldErrors.forEach(el => el.remove());
|
|
64
|
-
|
|
65
|
-
// Clear error classes from all inputs
|
|
66
|
-
let allInputs = this.querySelectorAll('input, textarea, select');
|
|
67
|
-
allInputs.forEach(input => input.classList.remove('error'));
|
|
68
|
-
|
|
69
62
|
let trimSpaces = this.hasAttribute('trim-spaces');
|
|
70
63
|
|
|
71
64
|
let inputElements = this.getAllInputElements();
|
|
@@ -133,6 +126,9 @@ class CollectionAdderForm extends SocketConsumer {
|
|
|
133
126
|
};
|
|
134
127
|
|
|
135
128
|
let resourceId = await this.collection.create(newModelData);
|
|
129
|
+
|
|
130
|
+
this.clearStatus();
|
|
131
|
+
|
|
136
132
|
let insertedModelData = {
|
|
137
133
|
...newModelData,
|
|
138
134
|
id: resourceId
|
|
@@ -162,6 +158,8 @@ class CollectionAdderForm extends SocketConsumer {
|
|
|
162
158
|
}
|
|
163
159
|
}
|
|
164
160
|
} catch (error) {
|
|
161
|
+
this.clearStatus();
|
|
162
|
+
|
|
165
163
|
messageContainer = this.shadowRoot.querySelector('slot[name="message"]').assignedElements()[0];
|
|
166
164
|
if (messageContainer) {
|
|
167
165
|
messageContainer.classList.add('error');
|
|
@@ -229,6 +227,24 @@ class CollectionAdderForm extends SocketConsumer {
|
|
|
229
227
|
updateConsumerElements.call(this, oppositeOutcomeConsumers, '', null, selfName);
|
|
230
228
|
}
|
|
231
229
|
|
|
230
|
+
clearStatus() {
|
|
231
|
+
let messageContainer = this.shadowRoot.querySelector('slot[name="message"]').assignedElements()[0];
|
|
232
|
+
|
|
233
|
+
if (messageContainer) {
|
|
234
|
+
messageContainer.classList.remove('success');
|
|
235
|
+
messageContainer.classList.remove('error');
|
|
236
|
+
messageContainer.textContent = '';
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
// Clear any existing field errors
|
|
240
|
+
let existingFieldErrors = this.querySelectorAll('.collection-adder-field-error-container');
|
|
241
|
+
existingFieldErrors.forEach(el => el.remove());
|
|
242
|
+
|
|
243
|
+
// Clear error classes from all inputs
|
|
244
|
+
let allInputs = this.querySelectorAll('input, textarea, select');
|
|
245
|
+
allInputs.forEach(input => input.classList.remove('error'));
|
|
246
|
+
}
|
|
247
|
+
|
|
232
248
|
getAllInputElements() {
|
|
233
249
|
return this.shadowRoot.querySelector('.input-slot')
|
|
234
250
|
.assignedElements()
|
package/collection-adder.js
CHANGED
|
@@ -55,17 +55,12 @@ class CollectionAdder extends SocketConsumer {
|
|
|
55
55
|
let successMessage = this.getAttribute('success-message');
|
|
56
56
|
let messageContainer = this.querySelector('.collection-adder-message-container');
|
|
57
57
|
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
existingFieldErrors.forEach(el => el.textContent = '');
|
|
65
|
-
|
|
66
|
-
// Clear error classes from all inputs
|
|
67
|
-
let allInputs = this.querySelectorAll('.collection-adder-input, .collection-adder-radio');
|
|
68
|
-
allInputs.forEach(input => input.classList.remove('error'));
|
|
58
|
+
// By default, the previous status is only cleared once the outcome of the
|
|
59
|
+
// submit is known so that the status is replaced within a single frame; this
|
|
60
|
+
// avoids the form flickering when the same error occurs twice in a row.
|
|
61
|
+
if (this.hasAttribute('reset-status-on-submit')) {
|
|
62
|
+
this.clearStatus();
|
|
63
|
+
}
|
|
69
64
|
|
|
70
65
|
let radioInputs = [ ...this.querySelectorAll('.collection-adder-radio') ];
|
|
71
66
|
let radioData = {};
|
|
@@ -131,6 +126,9 @@ class CollectionAdder extends SocketConsumer {
|
|
|
131
126
|
)
|
|
132
127
|
};
|
|
133
128
|
let resourceId = await this.collection.create(newModelData);
|
|
129
|
+
|
|
130
|
+
this.clearStatus();
|
|
131
|
+
|
|
134
132
|
let insertedModelData = {
|
|
135
133
|
...newModelData,
|
|
136
134
|
id: resourceId
|
|
@@ -156,6 +154,8 @@ class CollectionAdder extends SocketConsumer {
|
|
|
156
154
|
messageContainer.textContent = '';
|
|
157
155
|
}
|
|
158
156
|
} catch (error) {
|
|
157
|
+
this.clearStatus();
|
|
158
|
+
|
|
159
159
|
messageContainer.classList.add('error');
|
|
160
160
|
messageContainer.classList.remove('success');
|
|
161
161
|
|
|
@@ -213,6 +213,24 @@ class CollectionAdder extends SocketConsumer {
|
|
|
213
213
|
updateConsumerElements.call(this, oppositeOutcomeConsumers, '', null, selfName);
|
|
214
214
|
}
|
|
215
215
|
|
|
216
|
+
clearStatus() {
|
|
217
|
+
let messageContainer = this.querySelector('.collection-adder-message-container');
|
|
218
|
+
|
|
219
|
+
if (messageContainer) {
|
|
220
|
+
messageContainer.classList.remove('success');
|
|
221
|
+
messageContainer.classList.remove('error');
|
|
222
|
+
messageContainer.textContent = '';
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
// Clear any existing field errors
|
|
226
|
+
let existingFieldErrors = this.querySelectorAll('.collection-adder-field-error-container');
|
|
227
|
+
existingFieldErrors.forEach(el => el.textContent = '');
|
|
228
|
+
|
|
229
|
+
// Clear error classes from all inputs
|
|
230
|
+
let allInputs = this.querySelectorAll('.collection-adder-input, .collection-adder-radio');
|
|
231
|
+
allInputs.forEach(input => input.classList.remove('error'));
|
|
232
|
+
}
|
|
233
|
+
|
|
216
234
|
reset() {
|
|
217
235
|
let form = this.querySelector('.collection-adder-form');
|
|
218
236
|
if (form) {
|
package/input-provider.js
CHANGED
|
@@ -3,7 +3,8 @@ import {
|
|
|
3
3
|
renderTemplate,
|
|
4
4
|
updateConsumerElements,
|
|
5
5
|
convertStringToFieldParams,
|
|
6
|
-
convertStringToFieldTypeValues
|
|
6
|
+
convertStringToFieldTypeValues,
|
|
7
|
+
getTypeCastFunction
|
|
7
8
|
} from './utils.js';
|
|
8
9
|
|
|
9
10
|
const DEFAULT_DEBOUNCE_DELAY = 800;
|
|
@@ -135,15 +136,21 @@ class InputProvider extends HTMLElement {
|
|
|
135
136
|
elementType = 'input';
|
|
136
137
|
}
|
|
137
138
|
this.inputElement = document.createElement(elementType);
|
|
139
|
+
let optionValues = null;
|
|
138
140
|
if (type === 'select') {
|
|
139
141
|
if (options != null) {
|
|
140
142
|
let fieldTypeValues = convertStringToFieldTypeValues(options, true, true);
|
|
143
|
+
optionValues = new Map();
|
|
141
144
|
let optionElements = fieldTypeValues
|
|
142
145
|
.map((option) => {
|
|
143
146
|
if (option.field === placeholder) {
|
|
144
147
|
return `<option value="" selected class="select-default-option">${option.field}</option>`;
|
|
145
148
|
}
|
|
146
|
-
|
|
149
|
+
let Type = getTypeCastFunction(option.type);
|
|
150
|
+
let optionValue = Type(option.value ?? option.field);
|
|
151
|
+
let elementValue = String(optionValue);
|
|
152
|
+
optionValues.set(elementValue, optionValue);
|
|
153
|
+
return `<option value="${elementValue}">${option.field}</option>`;
|
|
147
154
|
})
|
|
148
155
|
.join('');
|
|
149
156
|
this.inputElement.innerHTML = optionElements;
|
|
@@ -189,7 +196,7 @@ class InputProvider extends HTMLElement {
|
|
|
189
196
|
this.updateInputClassList(value);
|
|
190
197
|
this.appendChild(this.inputElement);
|
|
191
198
|
|
|
192
|
-
let destroyHandlers = this.updateConsumerElementsOnEdit();
|
|
199
|
+
let destroyHandlers = this.updateConsumerElementsOnEdit(optionValues);
|
|
193
200
|
|
|
194
201
|
if (this.hasAttribute('force-init-change')) {
|
|
195
202
|
this.forceTriggerChange = true;
|
|
@@ -208,7 +215,14 @@ class InputProvider extends HTMLElement {
|
|
|
208
215
|
};
|
|
209
216
|
}
|
|
210
217
|
|
|
211
|
-
|
|
218
|
+
getTargetValue(inputValue, inputElement, optionValues) {
|
|
219
|
+
if (optionValues && optionValues.has(inputValue)) {
|
|
220
|
+
return optionValues.get(inputValue);
|
|
221
|
+
}
|
|
222
|
+
return inputElement.type === 'number' ? Number(inputValue) : inputValue;
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
updateConsumerElementsOnEdit(optionValues) {
|
|
212
226
|
let consumers = this.getAttribute('consumers');
|
|
213
227
|
if (!consumers) return () => {};
|
|
214
228
|
|
|
@@ -235,8 +249,7 @@ class InputProvider extends HTMLElement {
|
|
|
235
249
|
if (event.target.value === '') {
|
|
236
250
|
updateConsumerElements.call(this, consumers, '', providerTemplate, elementName);
|
|
237
251
|
} else {
|
|
238
|
-
let targetValue =
|
|
239
|
-
Number(event.target.value) : event.target.value;
|
|
252
|
+
let targetValue = this.getTargetValue(event.target.value, inputElement, optionValues);
|
|
240
253
|
updateConsumerElements.call(this, consumers, targetValue, providerTemplate, elementName);
|
|
241
254
|
}
|
|
242
255
|
}, debounceDelay);
|
|
@@ -256,8 +269,7 @@ class InputProvider extends HTMLElement {
|
|
|
256
269
|
if (event.target.value === '') {
|
|
257
270
|
updateConsumerElements.call(this, consumers, '', providerTemplate, elementName);
|
|
258
271
|
} else {
|
|
259
|
-
let targetValue =
|
|
260
|
-
Number(event.target.value) : event.target.value;
|
|
272
|
+
let targetValue = this.getTargetValue(event.target.value, inputElement, optionValues);
|
|
261
273
|
updateConsumerElements.call(this, consumers, targetValue, providerTemplate, elementName);
|
|
262
274
|
}
|
|
263
275
|
}, debounceDelay);
|
package/model-input.js
CHANGED
|
@@ -4,6 +4,7 @@ import {
|
|
|
4
4
|
updateConsumerElements,
|
|
5
5
|
convertStringToFieldParams,
|
|
6
6
|
convertStringToFieldTypeValues,
|
|
7
|
+
getTypeCastFunction,
|
|
7
8
|
formatError,
|
|
8
9
|
renderTemplate
|
|
9
10
|
} from './utils.js';
|
|
@@ -207,15 +208,21 @@ class ModelInput extends SocketConsumer {
|
|
|
207
208
|
}
|
|
208
209
|
this.inputElement = document.createElement(elementType);
|
|
209
210
|
let optionList = null;
|
|
211
|
+
let optionValues = null;
|
|
210
212
|
if (type === 'select') {
|
|
211
213
|
if (options != null) {
|
|
212
214
|
let fieldTypeValues = convertStringToFieldTypeValues(options, true, true);
|
|
215
|
+
optionValues = new Map();
|
|
213
216
|
let optionElements = fieldTypeValues
|
|
214
217
|
.map((option) => {
|
|
215
218
|
if (option.field === placeholder) {
|
|
216
219
|
return `<option value="" selected class="select-default-option">${option.field}</option>`;
|
|
217
220
|
}
|
|
218
|
-
|
|
221
|
+
let Type = getTypeCastFunction(option.type);
|
|
222
|
+
let optionValue = Type(option.value ?? option.field);
|
|
223
|
+
let elementValue = String(optionValue);
|
|
224
|
+
optionValues.set(elementValue, optionValue);
|
|
225
|
+
return `<option value="${elementValue}">${option.field}</option>`;
|
|
219
226
|
})
|
|
220
227
|
.join('');
|
|
221
228
|
this.inputElement.innerHTML = optionElements;
|
|
@@ -260,7 +267,7 @@ class ModelInput extends SocketConsumer {
|
|
|
260
267
|
this.appendChild(errorMessageContainer);
|
|
261
268
|
}
|
|
262
269
|
this.appendChild(this.inputElement);
|
|
263
|
-
let destroyInputSync = this.syncInputElementWithModel(this.inputElement, model, modelField, errorMessageContainer, optionList);
|
|
270
|
+
let destroyInputSync = this.syncInputElementWithModel(this.inputElement, model, modelField, errorMessageContainer, optionList, optionValues);
|
|
264
271
|
this.destroy = () => {
|
|
265
272
|
destroyInputSync();
|
|
266
273
|
this.isLoadedConsumer && this.isLoadedConsumer.kill();
|
|
@@ -302,13 +309,13 @@ class ModelInput extends SocketConsumer {
|
|
|
302
309
|
}
|
|
303
310
|
}
|
|
304
311
|
|
|
305
|
-
syncInputElementWithModel(inputElement, model, fieldName, messageContainerElement, optionList) {
|
|
312
|
+
syncInputElementWithModel(inputElement, model, fieldName, messageContainerElement, optionList, optionValues) {
|
|
306
313
|
if (model.isLoaded) {
|
|
307
314
|
let fieldValue = model.value[fieldName];
|
|
308
315
|
this.verifyValue(fieldValue, optionList, inputElement, messageContainerElement);
|
|
309
316
|
this.updateInputElement(inputElement, fieldValue);
|
|
310
317
|
}
|
|
311
|
-
let stopSaving = this.saveInputElementOnEdit(inputElement, model, fieldName, messageContainerElement);
|
|
318
|
+
let stopSaving = this.saveInputElementOnEdit(inputElement, model, fieldName, messageContainerElement, optionValues);
|
|
312
319
|
let changeConsumer = model.listener('change').createConsumer();
|
|
313
320
|
(async () => {
|
|
314
321
|
for await (let event of changeConsumer) {
|
|
@@ -325,7 +332,7 @@ class ModelInput extends SocketConsumer {
|
|
|
325
332
|
};
|
|
326
333
|
}
|
|
327
334
|
|
|
328
|
-
saveInputElementOnEdit(inputElement, model, fieldName, messageContainerElement) {
|
|
335
|
+
saveInputElementOnEdit(inputElement, model, fieldName, messageContainerElement, optionValues) {
|
|
329
336
|
let errorStyleClass = 'error';
|
|
330
337
|
let successStyleClass = 'success';
|
|
331
338
|
let showErrorMessage = (fieldName, errorMessage) => {
|
|
@@ -387,8 +394,13 @@ class ModelInput extends SocketConsumer {
|
|
|
387
394
|
updateConsumerElements.call(this, consumers, '', providerTemplate, this.getAttribute('name'));
|
|
388
395
|
await model.delete(fieldName);
|
|
389
396
|
} else {
|
|
390
|
-
let targetValue
|
|
391
|
-
|
|
397
|
+
let targetValue;
|
|
398
|
+
if (optionValues && optionValues.has(inputValue)) {
|
|
399
|
+
targetValue = optionValues.get(inputValue);
|
|
400
|
+
} else {
|
|
401
|
+
targetValue = inputElement.type === 'number' ?
|
|
402
|
+
Number(inputValue) : inputValue;
|
|
403
|
+
}
|
|
392
404
|
updateConsumerElements.call(this, consumers, targetValue, providerTemplate, this.getAttribute('name'));
|
|
393
405
|
await model.update(fieldName, targetValue);
|
|
394
406
|
}
|