@processmaker/screen-builder 2.5.28 → 2.5.30-PATCH4
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/dist/vue-form-builder.common.js +4627 -4614
- package/dist/vue-form-builder.common.js.map +1 -1
- package/dist/vue-form-builder.css +1 -1
- package/dist/vue-form-builder.umd.js +4627 -4614
- package/dist/vue-form-builder.umd.js.map +1 -1
- package/dist/vue-form-builder.umd.min.js +8 -8
- package/dist/vue-form-builder.umd.min.js.map +1 -1
- package/package-lock.json +164 -164
- package/package.json +3 -3
- package/src/.DS_Store +0 -0
- package/src/ValidationsFactory.js +76 -23
- package/src/components/renderer/file-download.vue +1 -1
- package/src/components/renderer/file-upload.vue +0 -19
- package/src/components/renderer/form-button.vue +0 -40
- package/src/components/renderer/form-record-list.vue +16 -1
- package/src/form-control-common-properties.js +2 -1
- package/src/mixins/ValidationRules.js +3 -0
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@processmaker/screen-builder",
|
|
3
|
-
"version": "2.5.
|
|
3
|
+
"version": "2.5.30-PATCH4",
|
|
4
4
|
"scripts": {
|
|
5
5
|
"serve": "vue-cli-service serve",
|
|
6
6
|
"build": "vue-cli-service build",
|
|
@@ -44,7 +44,7 @@
|
|
|
44
44
|
"@cypress/code-coverage": "^3.8.1",
|
|
45
45
|
"@fortawesome/fontawesome-free": "^5.6.1",
|
|
46
46
|
"@panter/vue-i18next": "^0.15.2",
|
|
47
|
-
"@processmaker/vue-form-elements": "0.18.4-
|
|
47
|
+
"@processmaker/vue-form-elements": "0.18.4-R",
|
|
48
48
|
"@vue/cli-plugin-babel": "^3.6.0",
|
|
49
49
|
"@vue/cli-plugin-e2e-cypress": "^4.0.3",
|
|
50
50
|
"@vue/cli-plugin-eslint": "^3.6.0",
|
|
@@ -84,7 +84,7 @@
|
|
|
84
84
|
},
|
|
85
85
|
"peerDependencies": {
|
|
86
86
|
"@panter/vue-i18next": "^0.15.0",
|
|
87
|
-
"@processmaker/vue-form-elements": "0.18.4-
|
|
87
|
+
"@processmaker/vue-form-elements": "0.18.4-R",
|
|
88
88
|
"i18next": "^15.0.8",
|
|
89
89
|
"vue": "^2.6.12",
|
|
90
90
|
"vuex": "^3.1.1"
|
package/src/.DS_Store
CHANGED
|
Binary file
|
|
@@ -34,7 +34,7 @@ class Validations {
|
|
|
34
34
|
isVisible() {
|
|
35
35
|
// Disable validations if field is hidden
|
|
36
36
|
let visible = true;
|
|
37
|
-
if (this.element.config.conditionalHide) {
|
|
37
|
+
if (!this.data.noData && this.element.config.conditionalHide) {
|
|
38
38
|
try {
|
|
39
39
|
visible = !!Parser.evaluate(this.element.config.conditionalHide, this.data);
|
|
40
40
|
} catch (error) {
|
|
@@ -51,7 +51,7 @@ class Validations {
|
|
|
51
51
|
class ArrayOfFieldsValidations extends Validations {
|
|
52
52
|
async addValidations(validations) {
|
|
53
53
|
for (const item of this.element) {
|
|
54
|
-
await ValidationsFactory(item, { screen: this.screen, data: this.data }).addValidations(validations);
|
|
54
|
+
await ValidationsFactory(item, { screen: this.screen, data: this.data, parentVisibilityRule: this.parentVisibilityRule}).addValidations(validations);
|
|
55
55
|
}
|
|
56
56
|
}
|
|
57
57
|
}
|
|
@@ -81,8 +81,9 @@ class FormNestedScreenValidations extends Validations {
|
|
|
81
81
|
return;
|
|
82
82
|
}
|
|
83
83
|
const definition = await this.loadScreen(this.element.config.screen);
|
|
84
|
+
let parentVisibilityRule = this.parentVisibilityRule ? this.parentVisibilityRule : this.element.config.conditionalHide;
|
|
84
85
|
if (definition && definition[0] && definition[0].items) {
|
|
85
|
-
await ValidationsFactory(definition[0].items, { screen: this.screen, data: this.data }).addValidations(validations);
|
|
86
|
+
await ValidationsFactory(definition[0].items, { screen: this.screen, data: this.data, parentVisibilityRule }).addValidations(validations);
|
|
86
87
|
}
|
|
87
88
|
}
|
|
88
89
|
|
|
@@ -112,8 +113,7 @@ class FormLoopValidations extends Validations {
|
|
|
112
113
|
set(validations, this.element.config.name, {});
|
|
113
114
|
const loopField = get(validations, this.element.config.name);
|
|
114
115
|
loopField['$each'] = {};
|
|
115
|
-
|
|
116
|
-
await ValidationsFactory(this.element.items, { screen: this.screen, data: {_parent: this.data, ...firstRow } }).addValidations(loopField['$each']);
|
|
116
|
+
await ValidationsFactory(this.element.items, { screen: this.screen, data: {_parent: this.data, noData: true}, parentVisibilityRule: this.element.config.conditionalHide}).addValidations(loopField['$each']);
|
|
117
117
|
}
|
|
118
118
|
}
|
|
119
119
|
|
|
@@ -126,7 +126,7 @@ class FormMultiColumnValidations extends Validations {
|
|
|
126
126
|
if (!this.isVisible()) {
|
|
127
127
|
return;
|
|
128
128
|
}
|
|
129
|
-
await ValidationsFactory(this.element.items, { screen: this.screen, data: this.data }).addValidations(validations);
|
|
129
|
+
await ValidationsFactory(this.element.items, { screen: this.screen, data: this.data, parentVisibilityRule: this.element.config.conditionalHide }).addValidations(validations);
|
|
130
130
|
}
|
|
131
131
|
}
|
|
132
132
|
|
|
@@ -167,20 +167,8 @@ class FormElementValidations extends Validations {
|
|
|
167
167
|
}
|
|
168
168
|
const fieldName = this.element.config.name;
|
|
169
169
|
const validationConfig = this.element.config.validation;
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
if (this.element.config.conditionalHide) {
|
|
173
|
-
let visible = true;
|
|
174
|
-
try {
|
|
175
|
-
visible = !!Parser.evaluate(this.element.config.conditionalHide, this.data);
|
|
176
|
-
} catch (error) {
|
|
177
|
-
visible = false;
|
|
178
|
-
}
|
|
179
|
-
if (!visible) {
|
|
180
|
-
return;
|
|
181
|
-
}
|
|
182
|
-
}
|
|
183
|
-
|
|
170
|
+
const conditionalHide = this.element.config.conditionalHide;
|
|
171
|
+
const parentVisibilityRule = this.parentVisibilityRule;
|
|
184
172
|
set(validations, fieldName, get(validations, fieldName, {}));
|
|
185
173
|
const fieldValidation = get(validations, fieldName);
|
|
186
174
|
if (validationConfig instanceof Array) {
|
|
@@ -203,7 +191,40 @@ class FormElementValidations extends Validations {
|
|
|
203
191
|
params.push(fieldName);
|
|
204
192
|
validationFn = validationFn(...params);
|
|
205
193
|
}
|
|
206
|
-
fieldValidation[rule] =
|
|
194
|
+
fieldValidation[rule] = function(...props) {
|
|
195
|
+
const data = props[1];
|
|
196
|
+
let dataWithParent = this.addReferenceToParents(data);
|
|
197
|
+
const nestedDataWithParent = this.addReferenceToParents(this.findParent(data));
|
|
198
|
+
if (nestedDataWithParent) {
|
|
199
|
+
dataWithParent = Object.assign(nestedDataWithParent, dataWithParent);
|
|
200
|
+
}
|
|
201
|
+
// Check Parent Visibility
|
|
202
|
+
if (parentVisibilityRule) {
|
|
203
|
+
let isParentVisible = true;
|
|
204
|
+
try {
|
|
205
|
+
isParentVisible = !!Parser.evaluate(parentVisibilityRule, dataWithParent);
|
|
206
|
+
} catch (error) {
|
|
207
|
+
isParentVisible = false;
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
if (!isParentVisible ) {
|
|
211
|
+
return true;
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
// Check Field Visibility
|
|
215
|
+
let visible = true;
|
|
216
|
+
if (conditionalHide) {
|
|
217
|
+
try {
|
|
218
|
+
visible = !!Parser.evaluate(conditionalHide, dataWithParent);
|
|
219
|
+
} catch (error) {
|
|
220
|
+
visible = false;
|
|
221
|
+
}
|
|
222
|
+
}
|
|
223
|
+
if (!visible) {
|
|
224
|
+
return true;
|
|
225
|
+
}
|
|
226
|
+
return validationFn.apply(this,props);
|
|
227
|
+
};
|
|
207
228
|
});
|
|
208
229
|
} else if (typeof validationConfig === 'string' && validationConfig) {
|
|
209
230
|
let validationFn = validators[validationConfig];
|
|
@@ -212,7 +233,40 @@ class FormElementValidations extends Validations {
|
|
|
212
233
|
console.error(`Undefined validation rule "${validationConfig}"`);
|
|
213
234
|
return;
|
|
214
235
|
}
|
|
215
|
-
fieldValidation[validationConfig] =
|
|
236
|
+
fieldValidation[validationConfig] = function(...props) {
|
|
237
|
+
const data = props[1];
|
|
238
|
+
let dataWithParent = this.addReferenceToParents(data);
|
|
239
|
+
const nestedDataWithParent = this.addReferenceToParents(this.findParent(data));
|
|
240
|
+
if (nestedDataWithParent) {
|
|
241
|
+
dataWithParent = Object.assign(nestedDataWithParent, dataWithParent);
|
|
242
|
+
}
|
|
243
|
+
// Check Parent Visibility
|
|
244
|
+
if (parentVisibilityRule) {
|
|
245
|
+
let isParentVisible = true;
|
|
246
|
+
try {
|
|
247
|
+
isParentVisible = !!Parser.evaluate(parentVisibilityRule, dataWithParent);
|
|
248
|
+
} catch (error) {
|
|
249
|
+
isParentVisible = false;
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
if (!isParentVisible) {
|
|
253
|
+
return true;
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
// Check Field Visibility
|
|
257
|
+
let visible = true;
|
|
258
|
+
if (conditionalHide) {
|
|
259
|
+
try {
|
|
260
|
+
visible = !!Parser.evaluate(conditionalHide, dataWithParent);
|
|
261
|
+
} catch (error) {
|
|
262
|
+
visible = false;
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
if (!visible) {
|
|
266
|
+
return true;
|
|
267
|
+
}
|
|
268
|
+
return validationFn.apply(this,props);
|
|
269
|
+
};
|
|
216
270
|
}
|
|
217
271
|
if (this.element.items) {
|
|
218
272
|
ValidationsFactory(this.element.items, { screen: this.screen, data: this.data }).addValidations(validations);
|
|
@@ -222,7 +276,6 @@ class FormElementValidations extends Validations {
|
|
|
222
276
|
return name.replace(/_\w/g, m => m.substr(1, 1).toUpperCase());
|
|
223
277
|
}
|
|
224
278
|
}
|
|
225
|
-
|
|
226
279
|
function ValidationsFactory(element, options) {
|
|
227
280
|
if (element instanceof Array) {
|
|
228
281
|
return new ArrayOfFieldsValidations(element, options);
|
|
@@ -110,7 +110,7 @@ export default {
|
|
|
110
110
|
listenRecordList(recordList, index, id) {
|
|
111
111
|
const parent = this.parentRecordList(this);
|
|
112
112
|
if (_.has(window, 'PM4ConfigOverrides.requestFiles') && parent === recordList) {
|
|
113
|
-
const prefix = (this.parentRecordList(this) === null) ? '' :
|
|
113
|
+
const prefix = (this.parentRecordList(this) === null) ? '' : this.prefix;
|
|
114
114
|
const fileDataName = prefix + this.name + (id ? '.' + id : '');
|
|
115
115
|
this.fileInfo = window.PM4ConfigOverrides.requestFiles[fileDataName];
|
|
116
116
|
this.loading = false;
|
|
@@ -94,8 +94,6 @@ export default {
|
|
|
94
94
|
(loop, removed) => this.listenRemovedLoop(loop, removed));
|
|
95
95
|
|
|
96
96
|
this.removeDefaultClasses();
|
|
97
|
-
|
|
98
|
-
this.checkIfInRecordList();
|
|
99
97
|
|
|
100
98
|
this.setPrefix();
|
|
101
99
|
if (this.$refs['uploader']) {
|
|
@@ -288,15 +286,6 @@ export default {
|
|
|
288
286
|
this.prefix = parent.loopContext + '.';
|
|
289
287
|
}
|
|
290
288
|
},
|
|
291
|
-
setFileUploadNameForChildren(children, prefix) {
|
|
292
|
-
children.forEach(child => {
|
|
293
|
-
if (_.get(child, '$options.name') === 'FileUpload') {
|
|
294
|
-
child.prefix = prefix;
|
|
295
|
-
} else if (_.get(child, '$children', []).length > 0) {
|
|
296
|
-
this.setFileUploadNameForChildren(child.$children, prefix);
|
|
297
|
-
}
|
|
298
|
-
});
|
|
299
|
-
},
|
|
300
289
|
addFile(file) {
|
|
301
290
|
if (this.disabled) {
|
|
302
291
|
file.ignored = true;
|
|
@@ -420,14 +409,6 @@ export default {
|
|
|
420
409
|
: null;
|
|
421
410
|
}
|
|
422
411
|
},
|
|
423
|
-
checkIfInRecordList() {
|
|
424
|
-
const parent = this.parentRecordList(this);
|
|
425
|
-
if (parent !== null) {
|
|
426
|
-
const recordList = parent;
|
|
427
|
-
const prefix = recordList.name + '.';
|
|
428
|
-
this.setFileUploadNameForChildren(recordList.$children, prefix);
|
|
429
|
-
}
|
|
430
|
-
},
|
|
431
412
|
},
|
|
432
413
|
};
|
|
433
414
|
</script>
|
|
@@ -5,7 +5,6 @@
|
|
|
5
5
|
</template>
|
|
6
6
|
|
|
7
7
|
<script>
|
|
8
|
-
import Mustache from 'mustache';
|
|
9
8
|
import { getValidPath } from '@/mixins';
|
|
10
9
|
|
|
11
10
|
export default {
|
|
@@ -19,45 +18,6 @@ export default {
|
|
|
19
18
|
['btn-' + variant]: true,
|
|
20
19
|
};
|
|
21
20
|
},
|
|
22
|
-
options() {
|
|
23
|
-
if (!this.tooltip || this.event === 'submit') {
|
|
24
|
-
return {};
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
let content = '';
|
|
28
|
-
try {
|
|
29
|
-
content = Mustache.render(this.tooltip.content || '', this.transientData);
|
|
30
|
-
} catch (error) { error; }
|
|
31
|
-
|
|
32
|
-
return {
|
|
33
|
-
title: content,
|
|
34
|
-
html: true,
|
|
35
|
-
placement: this.tooltip.position || '',
|
|
36
|
-
trigger: 'hover',
|
|
37
|
-
variant: this.tooltip.variant || '',
|
|
38
|
-
boundary: 'window',
|
|
39
|
-
};
|
|
40
|
-
},
|
|
41
|
-
valid() {
|
|
42
|
-
if (this.$attrs.validate) {
|
|
43
|
-
return !this.$attrs.validate.$invalid;
|
|
44
|
-
}
|
|
45
|
-
return true;
|
|
46
|
-
},
|
|
47
|
-
message() {
|
|
48
|
-
// eslint-disable-next-line vue/no-side-effects-in-computed-properties
|
|
49
|
-
this.errors = 0;
|
|
50
|
-
if (!this.valid) {
|
|
51
|
-
this.countErrors(this.$attrs.validate.vdata);
|
|
52
|
-
this.countErrors(this.$attrs.validate.schema);
|
|
53
|
-
let message = 'There are {{items}} validation errors in your form.';
|
|
54
|
-
if (this.errors === 1) {
|
|
55
|
-
message = 'There is a validation error in your form.';
|
|
56
|
-
}
|
|
57
|
-
return this.$t(message, {items: this.errors});
|
|
58
|
-
}
|
|
59
|
-
return '';
|
|
60
|
-
},
|
|
61
21
|
},
|
|
62
22
|
data() {
|
|
63
23
|
return {
|
|
@@ -73,6 +73,7 @@
|
|
|
73
73
|
:title="$t('Add')"
|
|
74
74
|
header-close-content="×"
|
|
75
75
|
data-cy="modal-add"
|
|
76
|
+
@shown="emitShownEvent"
|
|
76
77
|
>
|
|
77
78
|
<vue-form-renderer
|
|
78
79
|
:page="0"
|
|
@@ -85,6 +86,7 @@
|
|
|
85
86
|
debug-context="Record List Add"
|
|
86
87
|
:key="Array.isArray(value) ? value.length : 0"
|
|
87
88
|
:_parent="validationData"
|
|
89
|
+
@update="updateRowDataNamePrefix"
|
|
88
90
|
/>
|
|
89
91
|
</b-modal>
|
|
90
92
|
<b-modal
|
|
@@ -98,6 +100,7 @@
|
|
|
98
100
|
:title="$t('Edit Record')"
|
|
99
101
|
header-close-content="×"
|
|
100
102
|
data-cy="modal-edit"
|
|
103
|
+
@shown="emitShownEvent"
|
|
101
104
|
>
|
|
102
105
|
<vue-form-renderer
|
|
103
106
|
:page="0"
|
|
@@ -110,6 +113,7 @@
|
|
|
110
113
|
debug-context="Record List Edit"
|
|
111
114
|
:_parent="validationData"
|
|
112
115
|
:key="editFormVersion"
|
|
116
|
+
@update="updateRowDataNamePrefix"
|
|
113
117
|
/>
|
|
114
118
|
</b-modal>
|
|
115
119
|
<b-modal
|
|
@@ -162,6 +166,7 @@ export default {
|
|
|
162
166
|
props: ['name', 'label', 'fields', 'value', 'editable', '_config', 'form', 'validationData', 'formConfig', 'formComputed', 'formWatchers'],
|
|
163
167
|
data() {
|
|
164
168
|
return {
|
|
169
|
+
currentRowIndex: null,
|
|
165
170
|
editFormVersion: 0,
|
|
166
171
|
single: '',
|
|
167
172
|
plural: '',
|
|
@@ -257,6 +262,12 @@ export default {
|
|
|
257
262
|
},
|
|
258
263
|
},
|
|
259
264
|
methods: {
|
|
265
|
+
updateRowDataNamePrefix() {
|
|
266
|
+
this.setUploadDataNamePrefix(this.currentRowIndex);
|
|
267
|
+
},
|
|
268
|
+
emitShownEvent() {
|
|
269
|
+
window.ProcessMaker.EventBus.$emit('modal-shown');
|
|
270
|
+
},
|
|
260
271
|
isImage(field, item) {
|
|
261
272
|
const content = _.get(item, field.key);
|
|
262
273
|
return typeof content === 'string' && content.substr(0,11) === 'data:image/';
|
|
@@ -265,6 +276,7 @@ export default {
|
|
|
265
276
|
return field.key === '__filedownload';
|
|
266
277
|
},
|
|
267
278
|
setUploadDataNamePrefix(index = null) {
|
|
279
|
+
this.currentRowIndex = index;
|
|
268
280
|
let rowId = null;
|
|
269
281
|
if (index !== null && this.editItem) {
|
|
270
282
|
rowId = this.editItem.row_id;
|
|
@@ -336,7 +348,7 @@ export default {
|
|
|
336
348
|
// Reset edit to be a copy of our data model item
|
|
337
349
|
this.editItem = JSON.parse(JSON.stringify(this.value[pageIndex]));
|
|
338
350
|
this.editIndex = pageIndex;
|
|
339
|
-
// rebuild the edit screen to avoid
|
|
351
|
+
// rebuild the edit screen to avoid
|
|
340
352
|
this.editFormVersion++;
|
|
341
353
|
this.$nextTick(() => {
|
|
342
354
|
this.setUploadDataNamePrefix(pageIndex);
|
|
@@ -446,6 +458,9 @@ export default {
|
|
|
446
458
|
this.$root.$emit('removed-record', this, recordData);
|
|
447
459
|
},
|
|
448
460
|
},
|
|
461
|
+
mounted() {
|
|
462
|
+
this.updateRowDataNamePrefix = _.debounce(this.updateRowDataNamePrefix, 100);
|
|
463
|
+
},
|
|
449
464
|
};
|
|
450
465
|
</script>
|
|
451
466
|
|
|
@@ -95,7 +95,8 @@ export const keyNameProperty = {
|
|
|
95
95
|
config: {
|
|
96
96
|
label: 'Variable Name',
|
|
97
97
|
name: 'Variable Name',
|
|
98
|
-
|
|
98
|
+
// Update tests/e2e/specs/Builder.spec.js when changing this
|
|
99
|
+
validation: 'regex:/^([a-zA-Z]([a-zA-Z0-9_]?)+\\.?)+(?<!\\.)$/|required|not_in:' + javascriptReservedKeywords,
|
|
99
100
|
helper: 'A variable name is a symbolic name to reference information.',
|
|
100
101
|
},
|
|
101
102
|
};
|
|
@@ -21,6 +21,7 @@ import {
|
|
|
21
21
|
not,
|
|
22
22
|
or,
|
|
23
23
|
and,
|
|
24
|
+
type,
|
|
24
25
|
} from 'vuelidate/lib/validators';
|
|
25
26
|
|
|
26
27
|
export const ValidationMsg = {
|
|
@@ -55,6 +56,7 @@ export const ValidationMsg = {
|
|
|
55
56
|
invalid_default_value: 'Invalid default value',
|
|
56
57
|
customDate: 'Must be a valid Date',
|
|
57
58
|
regex: 'Invalid value',
|
|
59
|
+
type: 'Invalid type.',
|
|
58
60
|
};
|
|
59
61
|
|
|
60
62
|
export const custom_date = (date) => {
|
|
@@ -225,4 +227,5 @@ export const validators = {
|
|
|
225
227
|
notIn,
|
|
226
228
|
regex,
|
|
227
229
|
afterOrEqual: after_or_equal,
|
|
230
|
+
type,
|
|
228
231
|
};
|